22

我有一个类,我想保留元数据——有几个交互场景,所以元允许我为不同的交互类型保留不同的元。

class Feed()
{
    Guid FeedId { get; set; }
    ObjectMetaDictionary Meta { get; set; }
}

我希望 EF 序列化此 ObjectMetaDictionary 并将其作为字符串/VarChar 存储在数据库中。当我检索记录时,我希望将其反序列化为 ObjectMetaDictionary。

英孚支持吗?我该怎么做?

我首先使用实体​​框架代码。

已解决:我在下面提供了一个答案,解决了我的问题。只要允许,我就会接受这个答案。

4

3 回答 3

24

显然这实际上很容易。多亏了这个以前的 SO answer的一些帮助,我才能让它工作。

流畅的配置OnModelCreating允许我们告诉 EF 使用什么作为值属性来序列化到数据库并再次退出。

这是我的解决方案:

public class Feed
{
    public virtual Guid FeedId { get; set; }

    public virtual FeedMetaData Meta { get; set; }

    public virtual string Title { get; set; }
    public virtual string Description { get; set; }

}

public class FeedMetaData
{
    public Dictionary<string, string> Data { get; set; }

    public string Serialized
    {
        get { return JsonConvert.SerializeObject(Data); }
        set
        {
            if(string.IsNullOrEmpty(value)) return;

            var metaData = JsonConvert.DeserializeObject<Dictionary<string, string>>(value);

            Data = metaData ?? new Dictionary<string, string>();
        }
    }

    // addl code removed...
}

public class FeedsDbContext : DbContext
{
    public DbSet<Feed> Feeds { get; set; }

    protected override void OnModelCreating(DbModelBuilder modelBuilder)
    {
        modelBuilder.ComplexType<FeedMetaData>()
                    .Property(p => p.Serialized)
                    .HasColumnName("Meta");
        modelBuilder.ComplexType<FeedMetaData>().Ignore(p => p.Data);

        base.OnModelCreating(modelBuilder);
    }
}
于 2013-02-09T06:21:25.127 回答
1

让您的 Entity Framework 对象简单,并为数据库中的列提供一个 String 属性。

class Feed()
{
    Guid FeedId { get; set; }
    String Meta { get; set; }
}

创建这样保存和加载属性的方法:(自从我使用 EF 以来已经有一段时间了,所以我不确定您是否可以使用这些 getter/setter 创建瞬态属性,或者您是否需要其他东西)

//Reading from string column Meta
(ObjectMetaDictionary) XamlServices.Load(new StringReader(someFeed.Meta));

//Saving to string column Meta
someFeed.Meta = XamlServices.Save(value);

不过,这会给您的项目带来另一个整体问题。更改您的ObjectMetaDictionary可能会导致它无法正确地从数据库中反序列化。您ObjectMetaDictionary基本上成为数据库架构的一部分,您将需要相应地处理版本控制或更改。

于 2013-02-08T19:30:13.667 回答
1

HasConversion功能挽救了我的生命。解锁所有 json 格式!好好享受!

public partial class Feed
{
    public int Id { get; set; }

    //this column will be mapped to a "nvarchar(max)" column. perfect!
    public Dictionary<string, string> Meta { get; set; }
}

public class FeedsDbContext : DbContext
{

    public FeedsDbContext(DbContextOptions<FeedsDbContext> options)
        : base(options)
    {
    }

    public virtual DbSet<Feed> Feed { get; set; }

    protected override void OnModelCreating(ModelBuilder builder)
    {
        base.OnModelCreating(builder);

        builder.Entity<Feed>(entity =>
        {
            entity.Property(p => p.Meta).HasConversion(
                x => JsonConvert.SerializeObject(x) //convert TO a json string
                , x => JsonConvert.DeserializeObject<Dictionary<string, string>>(x) //convert FROM a json string
            );
        });
    }

}
于 2018-09-30T20:52:07.897 回答