背景
Visual Studio无法部署数据库项目。它尝试删除已经引用的函数(例如,在检查约束中),而不是仅添加新函数并更新现有函数,因此部署总是失败。
因此,我正在编写自己的代码来更新程序集并添加/更新任何函数。
我假设编译器/部署者使用SqlFunction属性的反射和属性,所以我也使用反射来收集具有SqlFunction属性的静态方法的MethodInfo列表。
问题/任务:
我需要知道如何将SqlFunctionAttribute的属性(例如IsDeterministic,DataAccess,Name,IsPrecise等)和函数的方法签名转换为适当的T-SQL“CREATE FUNCTION”语句。
我发现的现有信息无效:
“创建函数”的documentation令人困惑且不完整。接下来,它最后提到了一些像IsDeterministic这样的SqlFunction属性,但是它说它们就像它们是C#属性,而不是T-SQL参数,所以我不知道如何在create function语句中使用它们。
//CLR Functions
CREATE FUNCTION [ schema_name. ] function_name
( { @parameter_name [AS] [ type_schema_name. ] parameter_data_type
[ = default ] }
[ ,...n ]
)
RETURNS { return_data_type | TABLE <clr_table_type_definition> }
[ WITH <clr_function_option> [ ,...n ] ]
[ AS ] EXTERNAL NAME <method_specifier>
[ ; ]
我希望clr_function_option
参数能够处理像IsDeterministic这样的东西,但它没有作为选项列出。
与此同时,在IBM DB2的文档中,我看到如下语句,MSDN文档中没有任何类似的语句:
CREATE FUNCTION countUp(INTEGER)
RETURNS INTEGER
LANGUAGE CLR
PARAMETER STYLE SQL
SCRATCHPAD 10
FINAL CALL
NO SQL
FENCED
THREADSAFE
NOT DETERMINISTIC
EXECUTION CONTORL SAFE
EXTERNAL NAME 'gwenUDF.dll:bizLogic.empOps!CountUp' ;
答案 0 :(得分:2)
我意识到拥有程序集本身的SQL Server可以访问SqlFunctionAttribute的属性值后,最终解决了这个问题。在这种情况下,不需要(并且没有语法)在“CREATE FUNCTION”T-SQL语句中指定这些属性。
我构建了一个实用程序来自动枚举和部署函数和检查约束,其工作方式如下:
它通过使用反射搜索具有SqlFunction属性的函数来枚举我指定的类中的所有可部署静态方法。它还运行一个查询来枚举已部署的所有现有标量和表值汇编函数。然后,它将这些列表合并到一个列表中,其中每个函数都存在或不存在。有一个按钮来更新组件,还有一个按钮来切换每个功能的存在,使添加/删除/更新功能成为BREEZE。
此外,我在界面中添加了第二个选项卡来创建/启用/检查/禁用检查约束。我创建了一个名为SqlFunctionCheck的新属性,可以多次应用于函数。该属性具有“Table”属性和“Field”属性,这有助于实用程序构建检查约束。它按表聚合所有检查,为名为“CK_”+ table_name的每个表创建一个检查,并创建一个约束表达式,将所有方法调用与“和”一起传递给该函数。如果约束已存在,它将显示生成的约束表达式以及从sql server查询的约束表达式。
IMO,这是使用SQL CLR集成来强制管理工作室中的数据类型约束,代码中的SQL查询以及整个代码本身从集中数据(约束)类中使用的数据的最终解决方案。