1

I'm using EntityFramework - Code First, DBContext with POCO classes.

At runtime, how can i detect properties belongs to fields that generated in the database, marked as .HasDatabaseGeneratedOption , .IsRowVersion (readonly?) etc.

I looked at var xxx = Entity.GetType().GetProperty("ID").Get... , no luck.

public partial class OnMuhasebeContext : DbContext
{   

    public bool IsDatabaseGeneratedProperty <?>(...)
    {
        // Parameters : 
        // We know all poco classes of course
        // also parameters can be instance type
    }
}

Update:
please read "database generated" as "field whose value generated by database" and marked in the model to reflect that. These properties are both belongs to database generated fields and marked as identity and RowVersion using Fluent API.

public class POCOMap : EntityTypeConfiguration<POCO>
{
    public POCOMap()
    {
        // Primary Key
        this.HasKey(t => t.ID);

        this.Property(t => t.RowVersion)
            .IsFixedLength()
            .HasMaxLength(8)
            .IsRowVersion();
     }
 }

Important point: How to get properties are marked in the model or code first model, using Fluent API or Data Annotions. Databases itself not important, like the philosophy behind the Entity Framework.

4

1 回答 1

0

好吧,我想我得到了你想要达到的目标。

可悲的是,您无法EntityTypeConfiguration开箱即用。但是,您还可以做其他事情。您可以使用自己的Attribute并将其放置在具有数据库生成值的属性上。

一个例子:

我们的自定义属性:

[AttributeUsage(AttributeTargets.Property)]
public class GeneratedByDatabaseAttribute : Attribute
{

}

一个使用属性的非常简单的 poco:

public class SimplePoco
{
    [GeneratedByDatabase]
    public int Id { get; set; }

    [GeneratedByDatabase]
    public int RowVersion { get; set; }

    public string Name { get; set; }
}

这就是魔法发生的地方。我GetPropertyInfo用来从 lambda 表达式中获取成员。到目前为止,这种方法是不完整的,但是在 stackoverflow 周围有足够的样本。简而言之:我得到PropertyInfo给定属性的 并检查它是否具有我们的自定义GeneratedByDatabaseAttribute属性。

public class MyContext : DbContext
{
    public bool IsDatabaseGeneratedProperty<TSource>(Expression<Func<TSource, object>> propertyExpression)
    {
        var property = GetPropertyInfo(propertyExpression);
        var attribute = property.GetCustomAttribute<GeneratedByDatabaseAttribute>();
        return attribute != null;
    }

    public PropertyInfo GetPropertyInfo<TSource>(Expression<Func<TSource, object>> propertyLambda)
    {
        var member = propertyLambda.Body as MemberExpression;
        if (member == null)
        {
            var ubody = (UnaryExpression)propertyLambda.Body;
            member = ubody.Operand as MemberExpression;
        }
        return member.Member as PropertyInfo;
    }
}

这就是我用 LinqPad 测试它的方式:

void Main()
{
    var context = new MyContext();
    var result = context.IsDatabaseGeneratedProperty<SimplePoco>(poco => poco.Id);
    // result: True
    Console.WriteLine(result);

    result = context.IsDatabaseGeneratedProperty<SimplePoco>(poco => poco.Name);
    // result: False
    Console.WriteLine(result);
}
于 2013-08-14T08:59:10.290 回答