2

我是 EF 和 AutoMapper 的新手,我正在尝试使用它来创建 Web 服务。如果我尝试直接序列化 EF 实体,导航属性会抛出错误,因为它们无法被序列化。我想找到一种方法来抑制它们,我被告知最好的方法是创建 POCO 以用作数据传输对象。

(此时我想我不妨使用 ADO.NET 编写自己的 DTO——EF 不应该为我省去编写自己的类的麻烦吗?)

我已经向我推荐了 AutoMapper,作为一种将 EF 实体自动映射到 POCO 的方法,因此我尝试在以下过程中使用它,该过程会加载 POCO:

Public Sub Load(ByVal lngUserId As Long)

    Dim query = From u In db.Users
                Where u.UserID = lngUserId
                Select u

    AutoMapper.Mapper.Map(query.FirstOrDefault(), Me)

End Sub

问题是,它出现了一个与导航属性相关的错误,它似乎不会被 AutoMapper 自动忽略。

因此,我尝试添加此行以强制 AutoMapper 忽略 nav 属性:

Dim oMap = Mapper.CreateMap(Of User, UserDto).ForSourceMember(Sub(src) src.tblUserFarms, Sub(opt) opt.Ignore())

(tblUserFarms 是导航属性)

我从找到的 C# 示例中转换了它的语法,但似乎 .ForSourceMember 的第一个参数不应该是 Lambda 表达式,而且我找不到应该如何使用它的好例子。

我是在使用正确的方法,还是应该完全尝试其他方法?我是否应该简单地删除所有导航属性以解决问题并失去它们的好处?EF 甚至是适合这项工作的工具吗?

4

1 回答 1

3

Below is a code snippet of how I have been doing it. With the ignores in place I avoid getting the navigation property objects from being loaded (improve performance as well).

public domain.Entities.UserProfile GetUserProfile(string userName)
    {

        Mapper.CreateMap<Entities.UserProfile, domain.Entities.UserProfile>()
            .ForMember(dest => dest.BillingAddress, opt => opt.Ignore())
            .ForMember(dest => dest.ShippingAddress, opt => opt.Ignore())
            .ForMember(dest => dest.Orders, opt => opt.Ignore())
            .ForMember(dest => dest.ShoppingCartItems, opt => opt.Ignore());

        Entities.UserProfile storedProfile = db.UserProfiles.FirstOrDefault(x => x.UserName.Equals(userName));
        var profile = Mapper.Map<Entities.UserProfile, domain.Entities.UserProfile>(storedProfile);

        return profile;
    }

This is how I have defined my UserProfile

 public class UserProfile
{
    public virtual int UserId { get; set; }
    public virtual string UserName { get; set; }
    public virtual string Prefix { get; set; }
    public virtual string FirstName { get; set; }
    public virtual string MiddleName { get; set; }
    public virtual string LastName { get; set; }
    public virtual string EmailAddress { get; set; }
    public virtual string Company { get; set; }
    public virtual string PhoneNumber { get; set; }
    public virtual string FaxNumber { get; set; }

    private ICollection<ShoppingCartItem> _shoppingCartItems;
    private ICollection<Address> _addresses;
    private ICollection<Order> _orders;

    /// <summary>
    /// Default billing address
    /// </summary>
    public virtual Address BillingAddress { get; set; }

    /// <summary>
    /// Default shipping address
    /// </summary>
    public virtual Address ShippingAddress { get; set; }

    /// <summary>
    /// Gets or sets customer addresses
    /// </summary>
    public virtual ICollection<Address> Addresses
    {
        get { return _addresses ?? (_addresses = new List<Address>()); }
        protected set { _addresses = value; }
    }

    /// <summary>
    /// Gets or sets orders
    /// </summary>
    public virtual ICollection<Order> Orders
    {
        get { return _orders ?? (_orders = new List<Order>()); }
        protected set { _orders = value; }
    }

    /// <summary>
    /// Gets or sets shopping cart items
    /// </summary>
    public virtual ICollection<ShoppingCartItem> ShoppingCartItems
    {
        get { return _shoppingCartItems ?? (_shoppingCartItems = new List<ShoppingCartItem>()); }
        protected set { _shoppingCartItems = value; }
    }

}
于 2014-03-19T04:44:14.670 回答