2

我正在尝试使用 Dapper 进行数据访问(在 ASP.NET MVC3 FWIW 中)。我有一个 T-SQL 视图(在 SQL Server 中),它是这样的:

SELECT s.*, c.CompanyId AS BreakPoint c.Name AS CompanyName
FROM tblStaff AS s
INNER JOIN tblCompanies AS c ON c.CompanyId = s.CompanyId

非常简单。本质上是一个员工列表,每个员工都有一个公司。

我遇到的问题是我正在尝试将此查询的输出映射到我的 POCO,但是因为视图中的每个字段都必须是唯一的(即 CompanyName 而不是 tblStaff 中已经存在的 Name)映射到 POCO不工作。

这是代码:

var sql = @"select * from qryStaff";
var people = _db.Query<Person, Company, Person>(sql, (person, company) => {person.Company = company; return person;}, splitOn: "BreakPoint");

有什么建议我可以如何解决这个难题?我愿意改变我的观点,因为现在我对如何进步感到困惑。

4

1 回答 1

0

您应该明确列出从您的视图返回的所有字段(没有星号!)并且字段名称不是唯一的,使用别名进行重复数据删除。例如:

SELECT 
    s.CompanyName as CompanyName1, 
    s.BreakPoint as BreakPoint1,
    ...
    c.CompanyId AS BreakPoint,
    c.Name AS CompanyName
FROM tblStaff AS s
INNER JOIN tblCompanies AS c ON c.CompanyId = s.CompanyId

当然,列出的字段和您可能使用的别名完全取决于您的代码。通常,您调整查询中的别名以匹配 POCO 的属性名称。

此外,作为一般经验法则,最好远离 SQL 查询中的通配符,因为引入了此类问题。这是一篇关于 SQL 查询最佳实践的不错的文章。

摘抄:

在代码中的 SELECT 语句中使用明确的列名称有许多优点。首先,SQL Server 只返回您的应用程序需要的数据,而不是您的应用程序不会使用的一堆附加数据。通过只返回您需要的数据,您可以优化 SQL Server 收集您需要的所有信息列所需的工作量。此外,通过不使用星号 (*) 命名法,您还可以最大限度地减少将与您的 SELECT 语句关联的数据发送到应用程序所需的网络流量(字节数)。

此外,通过显式命名列,您可以使应用程序免受与某些数据库架构更改相关的潜在故障的影响,这些更改可能发生在您在 SELECT 语句中引用的任何表上。如果您要使用星号 (*) 命名法并且有人要向表中添加一个新列,您的应用程序将开始接收此附加数据列的数据,即使不更改您的应用程序代码。如果您的应用程序只希望返回特定数量的列,那么一旦有人向您引用的表之一添加了额外的列,它就会失败。因此,通过在 SELECT 语句中显式命名列,您的应用程序将始终返回相同数量的列,

于 2012-04-18T16:05:06.723 回答