2009-01-14 70 views
1

我需要一個正則表達式(在c#中運行),它將包含Sql Update語句的字符串作爲輸入,並將返回要更新的列的列表。它應該能夠處理括號或不括號的列。從SQL語句中提取更新列的正則表達式

// Example Sql Statement 
Update Employees 
Set FirstName = 'Jim', [LastName] = 'Smith', CodeNum = codes.Num 
From Employees as em 
Join CodeNumbers as codes on codes.EmployeeID = em.EmployeeID 

最後,我想返回一個IEnumerable或含列表:

  1. 名字
  2. CodeNum

任何人有執行什麼好的建議?

更新:sql是用戶生成的,所以我必須解析Sql,因爲它是給定的。在我的情況下提取列名的目的是驗證用戶有權更新查詢中包含的列。

回答

3

你正在做倒退。將數據以分解形式存儲,並更新表格,列名稱和表達式以生成全部分開的新值。從這個規範表示中,生成SQL(當你需要它時)和列更新列(當你需要時)。

如果您絕對必須從SQL語句中取出列名稱,我不認爲正則表達式是正確的方式。例如,在一般情況下,您可能需要跳過包含任意嵌套括號的新值表達式。您可能需要一個完整的SQL解析器。 The book Lex & Yacc作者:Levine,Mason和Brown撰寫了關於解析SQL的章節。

回覆更新: 你是爲了一個受傷的世界。做你想做的事情的唯一方法是完全解析SQL,因爲你還需要確保你沒有任何執行未授權操作的子表達式。

我非常非常強烈地建議您想出另一種方法去做任何你正在做的事情。也許可以將可修改的字段分解爲單獨的表並使用訪問控制?也許想出另一個界面供他們用來指定他們想做什麼?無論你在做什麼,幾乎肯定有更好的方法來做到這一點。在那條路上有龍。

+0

我絕對必須把我們的sql語句的列名稱(請參閱上面的更新)。 爲什麼你不認爲正則表達式是要走的路?我不是僅僅匹配在查詢中的單詞SET後面開始的以逗號分隔的「=」語句的左邊部分嗎? – 2009-01-14 18:44:49

+0

我的回覆太長而無法發表評論,所以我把它作爲上面的修改。 – Glomek 2009-01-14 18:55:52

2

正則表達式無法完成此任務,因爲SQL不是regular language

你可以這樣做,但不能用正則表達式。你需要一個全面的解析器。

您可以使用ANTLR在C#中生成解析器,並且有用於解析ANTLR中的SQL的免費文法available

但是,我同意Glomek允許用戶提供的SQL針對您的系統運行,即使在您嘗試驗證它沒有包含「未經授權的操作」後,也是愚蠢的。有太多情況可能會繞過你的驗證。

相反,如果您只有一個文本字段,則應該定義一個簡化的Domain-Specific Language,它允許用戶只指定他們有權執行的操作。從這個輸入中,你可以自己構建SQL。

0

SQL有一個複雜的遞歸語法,並且總會有一些子選擇,分組依據或文字,這些會破壞基於正則表達式的解析器。

爲什麼不使用sql語法分析器來實現你所需要的,這裏是an article向你展示瞭如何在3分鐘內達到你所需要的。