【问题标题】:Data access patterns in SQLCLRSQLCLR 中的数据访问模式
【发布时间】:2010-12-04 18:54:34
【问题描述】:

我在我的项目中使用 SQLCLR,并且,我对此非常满意。但是,我找不到任何关于良好数据访问模式的良好信息来源。

通常我使用存储过程在 .net 和 SQL 之间进行通信,因为我总是想要一个用于我的数据库的 API。但是,在这种情况下,.net 代码是 API 的一部分,因此 SP 看起来很糟糕。

Linq2SQL 在 SQL server 中不存在(虽然它可以通过 DBA 不喜欢的方式安装),所以它不是一个选项。

我目前拥有的是我的代码与标准 ADO.NET 代码类似

using (SqlCommand cmd = c.CreateCommand()) {
    cmd.CommandText = "SELECT ... FROM ...";
    using (SqlDataReader rdr = cmd.ExecuteReader()) {
        DoSomething(rdr);
    }
}

虽然它有效,但它似乎非常像错误的方法。

其他人是怎么做到的?

【问题讨论】:

    标签: sql-server data-access-layer sqlclr


    【解决方案1】:

    我使用 XSLT 为 DAL 生成 C# 代码。我通常从数据库定义本身(例如某种形式的SELECT name, type, length, ... FROM sys.columns JOIN sys.tables JOIN sys.types FOR XML PATH)加载 XML,并且我已经及时开发了自定义 XSLT 转换以生成代码。我将它们添加为 Visual Studio 构建过程本身的一部分,类似于此博客:http://rusanu.com/2009/04/11/using-xslt-to-generate-performance-counters-code/(该博客是关于性能计数器生成的,但它也适用于 DAL 代码)。我还使用 XSLT 代码生成器为结果集构建类型。

    虽然在重型客户端上这种方法与 ORM 和 ADO 数据集功能重叠(我仍然在这些客户端上使用它,但这是我的问题...),但由于 SQLCLR 的特定限制,SQLCR 是最合适的。

    这种方法首先非常灵活,让我能够快速进行影响每个 DAL 入口点的全局更改,同时我对代码库保持绝对控制(没有外部依赖项,没有引入外部错误)。与 ADO 数据集相比,它非常轻量级。

    我只会为 LINQ 权衡这种方法,因为传递 IQueryable 对象的附加值。但如您所知,在 SQLCLR 中,这还不是一个可行的选择。

    【讨论】:

    • 实际上我自己在非 SQLCLR 中的做法几乎相同,但我的解决方案依赖于表达式树(在 System.Core 中定义)来生成 where 子句。你如何生成你的 where 子句?
    • 到目前为止,我从来不需要生成复杂的 where 表达式。我总是通过其中一个键来查找项目,并且从 XSLT 生成简单的查找方法(WHERE key@value)。从您对 Jonathan 的回答来看,您在运行时需要一些东西,而不是在编译时。
    • 不,在这种情况下,我对那些简单的查询感兴趣,以查找我在复杂逻辑中使用的元数据。
    • 这就是我最终要做的(嗯,不是 XSLT,而是 T4 模板)。我希望有一天我会开源我的解决方案。就目前而言,我想适当的回答是“没有好的、标准的方法”,这基本上就是这个答案所说的。
    【解决方案2】:

    对于 SQLCLR 实际上比基于适当集合的 TSQL 提供性能增益的有限地方,我完全按照您在上面显示的方式进行数据访问。您必须执行一些非常繁重的基于循环的处理,而这些处理无法基于集合、XML 解析或极其复杂的数学运算才能真正需要使用 SQLCLR。如果您仅将 SQLCLR 用于数据访问,那么您这样做是以牺牲性能为代价的。如果您想对此进行一些演示,请告诉我,我将从去年的演示文稿中提取 AdventureWorks 的示例。

    【讨论】:

    • 我对 SQLCLR 的主要用途是使用某些表中的元数据从 DSL 生成 SQL。这在 T-SQL 中会非常麻烦。我的问题与性能无关,而是与可维护性和一般良好风格有关。
    • 如果您在 SQLCLR 中动态构建生成的 TSQL,您可以在 TSQL 中执行相同操作,并使用 sp_executesql 在 TSQL 中通过参数化调用它。在这种情况下,对于相同的操作,sp_executesql 的性能将比等效的 SQLCLR 更快,并且代码应该同样易于管理。 SQLCLR 是一个很好的提高性能的工具,但它也很容易在只执行数据访问操作的任务上降低性能,尽管您可能认为“更友好”的代码可管理性明智。
    • 参见 Erland Sommarskog 的关于动态 SQL 的文章,其中介绍了如何在 TSQL 中使用动态代码来实现复杂性,例如:sommarskog.se/dynamic_sql.html
    • @Jonathan:如果你碰巧有一个 T-SQL 的 ANTLR 运行时,我或许可以考虑。
    猜你喜欢
    • 1970-01-01
    • 2016-07-24
    • 2020-01-09
    • 1970-01-01
    • 2012-08-17
    • 1970-01-01
    • 1970-01-01
    • 2015-02-27
    相关资源
    最近更新 更多