エンティティフレームワークコードの最初の日付フィールドの作成


83

Entity Framework CodeFirstメソッドを使用してデータベーステーブルを作成しています。次のコードはDATETIMEデータベースにDATE列を作成しますが、列を作成したいと思います。

[DataType(DataType.Date)]
[DisplayFormatAttribute(ApplyFormatInEditMode = true, DataFormatString = "{0:d}")]
public DateTime ReportDate { get; set; }

DATEテーブルの作成中に、タイプの列を作成するにはどうすればよいですか?

回答:


22

DavidRothの回答のEF6バージョンは次のとおりです。

public class DataTypePropertyAttributeConvention 
    : PrimitivePropertyAttributeConfigurationConvention<DataTypeAttribute>
{
    public override void Apply(ConventionPrimitivePropertyConfiguration configuration, 
        DataTypeAttribute attribute)
    {
        if (attribute.DataType == DataType.Date)
        {
            configuration.HasColumnType("Date");
        }
    }
}

以前のようにこれを登録します:

protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
     base.OnModelCreating(modelBuilder);

     modelBuilder.Conventions.Add(new DataTypePropertyAttributeConvention());
}

これは、ジョブにEF基本クラスを使用していることを除いて、TylerDurdenのアプローチと同じ結果になります。


165

ColumnAttributefrom System.ComponentModel.DataAnnotations(EntityFramework.dllで定義)を使用してみてください:

[Column(TypeName="Date")]
public DateTime ReportDate { get; set; }

1
Sequence contains no matching element日付をサポートしていないDBをポイントしている場合、エラーが発生する可能性があります。SQL Server2014はそうします。
ジェス2015

8
EF6では必要ですusing System.ComponentModel.DataAnnotations.Schema;
JohnnyHK

11

私は以下を使用します

    [DataType(DataType.Time)]
    public TimeSpan StartTime { get; set; }

    [DataType(DataType.Time)]
    public TimeSpan EndTime { get; set; }

    [DataType(DataType.Date)]
    [Column(TypeName = "Date")]
    public DateTime StartDate { get; set; }

    [DataType(DataType.Date)]
    [Column(TypeName = "Date")]
    public DateTime EndDate { get; set; }

Entity Framework6およびSQLServer Express 2012-11.0.2100.60(X64)を使用。それは完全に機能し、SQLサーバーで時刻/日付の列タイプを生成します


あなたの解決策はうまくいきました。@YakoobHammouriは機能しませんでした。私は両方のアノテーションを使用していた[DataType(DataType.Date)][Column(TypeName = "Date")]あなたが示唆したように。しかし、この解決策は、として日付フォーマットを作成したyyyy-mm-ddとは対照的にMM-dd-yyyy
ナム

9

これはEF6でうまく機能することがわかりました。

データ型を指定するための規則を作成しました。この規則により、データベース作成のデフォルトのDateTimeデータ型がdatetimeからdatetime2に変更されます。次に、DataType(DataType.Date)属性で装飾したすべてのプロパティに、より具体的なルールを適用します。

public class DateConvention : Convention
{
    public DateConvention()
    {
        this.Properties<DateTime>()
            .Configure(c => c.HasColumnType("datetime2").HasPrecision(3));

        this.Properties<DateTime>()
            .Where(x => x.GetCustomAttributes(false).OfType<DataTypeAttribute>()
            .Any(a => a.DataType == DataType.Date))
            .Configure(c => c.HasColumnType("date"));
    }
}

次に、コンテキストでコンベンションを登録します。

protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
    modelBuilder.Conventions.Remove<PluralizingTableNameConvention>();
    modelBuilder.Conventions.Add(new DateConvention());
    // Additional configuration....
}

日付のみにしたいDateTimeプロパティに属性を追加します。

public class Participant : EntityBase
{
    public int ID { get; set; }

    [Required]
    [Display(Name = "Given Name")]
    public string GivenName { get; set; }

    [Required]
    [Display(Name = "Surname")]
    public string Surname { get; set; }

    [DataType(DataType.Date)]
    [Display(Name = "Date of Birth")]
    public DateTime DateOfBirth { get; set; }
}

1
本当に素晴らしい解決策です!完全に明確にするために追加したいことの1つは、これを使用するには、日付プロパティに属性を追加する必要があることです。例:[DataType(DataType.Date)] public DateTime IssueDate {get; セットする; }
Stephen Lautier 2014年

@StephenLautierはい、特定のDateTimeプロパティに対してのみこれを使用できるようにする場合は、属性を追加する必要があります。追加したコードでは、すべてのDateTime型に一般的なルールを適用してから、DataType(DataType.Date)装飾のあるものにさらに具体的なルールを適用できることを示しています。これで混乱が解消されることを願っています。
タイラーダーデン2014年

1
良い解決策ですが、EFはこの仕事をするための基本クラスを提供します-詳細については私の解決策を参照してください。
リチャード

@Richardあなたが正しいので、私はあなたの解決策に賛成票を投じました。ただし、ソリューションを作成した理由は、EFのデフォルトのDateTimeプロパティが、.NET DateTimeプロパティと互換性のあるdatetime2データ型ではなく、SQLServerのdatetimeデータ型を使用するためです。ありがたいことに、EFコアはこの問題を修正しました。
タイラーダーデン

5

クラスを属性で装飾したくない場合は、次DbContextOnModelCreatingように'sで設定できます。

public class DatabaseContext: DbContext
{
    // DbSet's

    protected override void OnModelCreating(DbModelBuilder modelBuilder)
    {
        base.OnModelCreating(modelBuilder);

        // magic starts
        modelBuilder.Entity<YourEntity>()
                    .Property(e => e.ReportDate)
                    .HasColumnType("date");
        // magic ends

        // ... other bindings
    }
}

4

使用ColumnAttributeする以外に、DataTypeAttribute:のカスタム属性規則を作成することもできます。

public class DataTypePropertyAttributeConvention : AttributeConfigurationConvention<PropertyInfo, PrimitivePropertyConfiguration, DataTypeAttribute>
{
    public override void Apply(PropertyInfo memberInfo, PrimitivePropertyConfiguration configuration, DataTypeAttribute attribute)
    {
        if (attribute.DataType == DataType.Date)
        {
            configuration.ColumnType = "Date";
        }
    }
}

OnModelCreatingメソッドに規則を登録するだけです。

protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
     base.OnModelCreating(modelBuilder);

     modelBuilder.Conventions.Add(new DataTypePropertyAttributeConvention());
}

これはEFに組み込まれている必要があります。共有してくれてありがとう!
tugberk 2013年

残念ながら、これはEF6で非推奨になり、無効になりました。
タイラーダーデン2014

1
EF6は、これを行うための新しい方法を提供しました。詳細については、私のソリューションを参照してください。
リチャード

3

これは、この質問に対する@LadislavMrnkaによる最も賛成票の回答の単なる拡張です。

Date列がたくさんある場合は、カスタム属性を作成して、いつでも使用できます。これにより、エンティティクラスでよりクリーンなコードが生成されます。

public class DateColumnAttribute : ColumnAttribute
{
    public DateColumnAttribute()
    {
        TypeName = "date";
    }
}

使用法

[DateColumn]
public DateTime DateProperty { get; set; }

-3

を使用する最良の方法

[DataType(DataType.Date)]
public DateTime ReportDate { get; set; }

ただし、EntityFramework v6.1.1を使用する必要があります

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.