So finden Sie alle ausgewählten Abfragen aus einem gespeicherten Prozedur-Skript in C #

Ich habe eine list von Prozeduren in meinem SQL-server, und ich möchte alle select * -statement mit select (alle Spaltennamen) dieser Tabelle replace. Um dies zu tun, muss ich alle ausgewählten Aussagen des Proceudure-Skripts identifizieren. Hier ist mein aktueller Code.

foreach (StoredProcedure myproc in SelectedProcedures) { StringBuilder builder = new StringBuilder(); ScriptingOptions scriptOptions = new ScriptingOptions(); StringCollection tableScripts = myproc.Script(); foreach (string script in tableScripts) { if (script.ToUpper().Contains("CREATE PROCEDURE")) { string x = script.ToUpper().Replace("CREATE PROCEDURE", "ALTER PROCEDURE"); builder.Append(x + "\n"); if (script.ToString().ToUpper().Replace(" ", " ").Contains("SELECT * FROM ")) { string u = script.ToString().ToUpper().Replace(" ", " "); List<string> values = u.Split(new string[] { "SELECT * FROM " }, StringSplitOptions.RemoveEmptyEntries).ToList(); List<string> tablenames = new List<string>(); values.RemoveAt(0); foreach (string t in values) { if (!t.Trim().StartsWith("#") && !t.Trim().StartsWith("@")) { tablenames.Add(t.Split(' ')[0].Replace("[", "").Replace("]", "").ToUpper().Trim()); } } tablenames.OrderBy(xx => xx); List<Table> tables = SourceDB.Tables.Cast<Table>().Where(t => tablenames.Contains(t.ToString().Replace("[", "").Replace("]", "").ToUpper())).Select(t => t).ToList(); foreach (var t in tablenames) { try { Table mytable = SourceDB.Tables[t.Split('.')[1], t.Split('.')[0]]; if (mytable != null) { StringBuilder builder1 = new StringBuilder(); builder1.Append("SELECT "); foreach (Column column in mytable.Columns) { builder1.Append("[" + column.Name.ToUpper() + "], "); } builder1.Remove(builder1.ToString().LastIndexOf(", "), 1); builder1.Append(" from "); builder1.Append(mytable.ToString()); GeneratedScripts["Procedures"].Add(builder1); string k = builder.ToString().ToUpper(); string n = k.Replace(" ", " ").Replace("SELECT * FROM " + mytable.ToString().ToUpper(), builder1.ToString()); n = n.Replace(" ", " ").Replace("SELECT * FROM " + t, builder1.ToString()); builder = new StringBuilder(n); } } catch (Exception) { continue; } } } } } 

Allerdings läßt dies Fälle wie ausgesucht werden B. * aus Tabelle Eine innere Verknüpfungstabelle BI kann zusätzliche Logik wie Regex verwenden, um diese Dinge zu behandeln, aber ich möchte eine passendere Weise, damit ich alle ausgewählten Abfragen eines Prozedurskripts in einer list abrufe von String, und dann kann ich meine benutzerdefinierte Logik über alle Abfragen eins nach dem anderen verwenden.

Vielen Dank

Es ist ganz einfach, wenn Ihre database von SSDT entwickelt wird, die standardmäßig nach Visual Studio 2013 enthalten ist. In SSDT, klicken Sie einfach mit der rechten Maustaste auf Projektknoten und wählen Sie Refactor -> Expand Wildcards. SSDT intern build ein model der database Schema, so ist es sehr schlau, um genaue Spalten.

Mit diesem Tool (ich glaube, andere Werkzeuge), müssen Sie immer noch Aufmerksamkeit auf Abfrage wie EXISTS (SELECT * FROM ODER SELECT COUNT(*) zu zahlen. Ersetzen sie macht nicht viel Sinn. Bildbeschreibung hier eingeben

Ich würde das mit einigen Annahmen machen:

searchn Sie nach einem Regex-Match, wo ein * zwischen einem SELECT und einem FROM auftritt. Ein möglicher Ausschluss wäre, wenn dem SELECT unmittelbar ein 'EXISTS (', der Leerzeichen oder Tabs enthalten kann, vorangestellt ist.

Andere Alternativen wäre, nur einen Blick auf die Ausführung Plan Cache und suchen Sie nach den am häufigsten verwendeten Abfragen.

Eine weitere großartige (oder bessere) Alternative ist es, mit der Codeanalyse zu beginnen, die hierfür Regeln enthalten könnte.