如何在使用.net 2.0和c#执行sql脚本之前验证它们?
如果sql无效,我想返回错误行。
答案 0 :(得分:42)
答案 1 :(得分:16)
SSMS有办法做到这一点。
如果您使用SQL事件探查器,您将看到它执行SET PARSEONLY ON
,然后执行SQL,然后SET PARSEONLY OFF
,并且在不编译或执行查询的情况下会出现任何错误。
SET PARSEONLY ON;
SELECT * FROM Table; --Query To Parse
SET PARSEONLY OFF;
我从未尝试过使用c#,但我认为没有理由说它不起作用,毕竟它适用于SSMS。
正如Martin Smith在评论中指出的那样,您可以使用SET NOEXEC ON
当SET NOEXEC为ON时,SQL Server 编译每批Transact-SQL 语句但不执行它们。 当SET NOEXEC为OFF时,所有批次 在编译后执行。
当SET PARSEONLY为ON时,SQL Server仅解析该语句。什么时候 SET PARSEONLY为OFF,SQL Server 编译并执行声明。
这表明NOEXEC
也将编译PARSEONLY
不会的查询。因此NOEXEC
可能会发现PARSEONLY
没有的错误。用法是一样的。
SET NOEXEC ON;
SELECT * FROM Table; --Query To Parse
SET NOEXEC OFF;
答案 2 :(得分:5)
我知道问题是关于.NET 2.0的,但对某些人来说可能很有趣。在最新版本的Microsoft SQL Server中,查询验证略有变化。
名称空间为Microsoft.SqlServer.TransactSql.ScriptDom
,而不是Microsoft.Data.Schema.ScriptDom
。
在哪里可以找到这个库?
图书馆的路径是%programfiles(x86)%\Microsoft SQL Server\120\SDK\Assemblies
如果找不到此库并安装了Microsoft SQL Server,请尝试从120
更改为110
或100
并使用相应的解析器(TSql110Parser
或{{1}分别)。
如何使用?
我有两个扩展:第一个扩展检查输入字符串是否是有效的SQL查询,第二个扩展可用于从解析中获取错误。
TSql100Parser
另外,我检查输入的SQL查询不是null或为空,因为解析器认为空字符串是完全有效的(我不判断它)。
如何测试?
有三个NUnit测试,显示如何使用此扩展。
using Microsoft.SqlServer.TransactSql.ScriptDom;
using System.Collections.Generic;
using System.IO;
using System.Linq;
public static class SqlStringExtensions
{
public static bool IsValidSql(this string str)
{
return !str.ValidateSql().Any();
}
public static IEnumerable<string> ValidateSql(this string str)
{
if (string.IsNullOrWhiteSpace(str))
{
return new[] { "SQL query should be non empty." };
}
var parser = new TSql120Parser(false);
IList<ParseError> errors;
using (var reader = new StringReader(str))
{
parser.Parse(reader, out errors);
}
return errors.Select(err => err.Message);
}
}
答案 3 :(得分:0)
'有效'SQL是什么意思?语法或结果?
验证语法的唯一可靠方法是在SQL Server中执行SQL。您是否考虑在事务中运行SQL,然后在最后执行回滚?
Begin Transaction
--execute your code between the 'Begin Transaction' and the 'rollback' keywords.
...
--example
Insert into mytable(ID)Values(2)
...
Rollback
回滚时