实体框架存储过程 - 映射复杂属性

时间:2013-05-10 12:00:00

标签: c# .net entity-framework

我有一个edmx数据存储,我正在尝试对它执行存储过程:

.
.
.
CustomerDb.ExecuteStoreQuery<Customer>("GetCustomers", parameters).ToList();

客户类具有以下结构

class Customer {
    public int Id { get; set; }
    .
    .
    .
    public Address Address { get; set; }
}

class Address {
    public int Id { get; set; }
    .
    .
    .
    public string PostCode { get; set; }
}

现在无论我做什么,Address属性始终为null。我试图以不同的格式返回结果集,但无论我做什么,它总是为空。

E.g。

SELECT c.Id, ..., a.PostCode
FROM Customer AS c
INNER JOIN Address AS a ON c.CustomerId = a.CustomerId
WHERE c.CustomerId = @CustomerId

SELECT c.Id, ..., a.PostCode AS 'Address.PostCode'
FROM Customer AS c
INNER JOIN Address AS a ON c.CustomerId = a.CustomerId
WHERE c.CustomerId = @CustomerId

SELECT c.Id, ..., a.PostCode AS 'Address_PostCode'
FROM Customer AS c
INNER JOIN Address AS a ON c.CustomerId = a.CustomerId
WHERE c.CustomerId = @CustomerId

但是这些专栏从未被选中。

我做错了什么?

感谢。

2 个答案:

答案 0 :(得分:2)

我认为你不能这样做。根据{{​​3}}

  

该类型的每个属性:

     

•必须有一个制定者。

     

•必须与CSDL中的基本类型相对应。

     

•必须对应于生成的DbDataReader中的列名(   provider实现确定列是否具有相同的名称   作为财产)。如果类型属性的名称与a不匹配   在DbDataReader的字段中,实体框架实现了   属性的默认值(如果在conceptutal中定义)   模型。

您的地址是CSDL中的ComplexType。我认为你必须用可以用ExecuteStoreQuery实现的类型构造你的对象。

答案 1 :(得分:0)

为未来的读者。

http://msdn.microsoft.com/en-US/data/jj691402

多个结果可以填充此类对象层次结构。

注意:EF在使用Translate方法创建实体时不会考虑任何映射。它只会将结果集中的列名与类上的属性名匹配。

因此,选择查询(查询)中的属性名称和列非常“挑剔”。

这是一个旧学校Northwind查询,用于显示如何使用单个输入参数获取多个对象。

Use Northwind
GO

/*

Declare @OrderID int
select @OrderID = (select top 1 OrderID from dbo.[Order Details] )
EXEC dbo.uspOrderDetailsGetByKey @OrderID

*/


IF EXISTS 
    (
    SELECT * FROM INFORMATION_SCHEMA.ROUTINES  WHERE ROUTINE_TYPE = N'PROCEDURE' and ROUTINE_SCHEMA = N'dbo' and ROUTINE_NAME = N'uspOrderDetailsGetByKey'  
    )
BEGIN
    DROP PROCEDURE [dbo].[uspOrderDetailsGetByKey]
END


GO

CREATE Procedure dbo.uspOrderDetailsGetByKey (
@OrderID int
)
AS

BEGIN

    SET NOCOUNT ON

    /* Result #1 */
    SELECT 
        c.CustomerID, c.CompanyName,c.ContactName,c.ContactTitle,c.[Address],c.City,c.Region,c.PostalCode,c.Country ,c.Phone,c.Fax 
    FROM 
        dbo.Customers c 
        JOIN Orders o ON c.CustomerID = o.CustomerID 
    WHERE 
        o.OrderID = @OrderID

    /* Result #2 */ 
    SELECT o.OrderID,o.CustomerID,o.EmployeeID,o.OrderDate,o.RequiredDate,o.ShippedDate,o.ShipVia ,o.Freight,o.ShipName,o.ShipAddress,o.OrderID,o.CustomerID,o.EmployeeID,o.OrderDate 
    FROM 
        dbo.Orders o 
     WHERE 
        o.OrderID = @OrderID

    /* Result #3 */
     SELECT od.OrderID,od.ProductID,od.UnitPrice,od.Quantity,od.Discount 
     FROM 
        dbo.[Order Details] od 
     WHERE 
        exists (select null from dbo.Orders innerTable where innerTable.OrderID = od.OrderID and innerTable.OrderID = @OrderID )

    SET NOCOUNT OFF

END

GO