web-dev-qa-db-ja.com

VS 2010 .net 4.0でエンティティフレームワークを使用する場合の「datetime2」エラー

このエラーの取得:

System.Data.SqlClient.SqlException:datetime2データ型からdatetimeデータ型への変換の結果、範囲外の値が発生しました。

私のエンティティオブジェクトはすべてDBオブジェクトに並んでいます。

Googleからこのエラーへの参照が1つだけ見つかりました。

Google結果

これを読んだ後、didが2つのフィールドを追加し、VS 2010からエンティティモデルを更新したことを思い出します。表示されません。

コードで行っているのは、エンティティオブジェクトにデータを入力して保存することだけです。 (コードに新しいフィールドも入力します)日付フィールドに_DateTime.Now_。を入力しました。

コードの重要な部分はこれです:ctx.SaveChanges(SaveOptions.AcceptAllChangesAfterSave);

データベースはSQL Server 2008です。

思考?

エラーの残り:

system.Data.Mapping.Update.Internal.UpdateTranslator.Update(IEntityStateManager stateManager、IEntityAdapter adapter)at System.Data.EntityClient.EntityAdapter.Update(IEntityStateManager entityCache)at System.Data.Objects.ObjectContext.SaveChanges(SaveOptions options)at SpeciesPost.svc.cs内のSafariAdmin.Site.WebServices.SpeciesPost.SaveOrUpdateSpecies(String sid、String fieldName、String authToken):SpeciesPostSVC_Tester.cs内のSafariAdmin.TestHarness.Tests.Site.WebServices.SpeciesPostSVC_Tester.SaveNewSpecies()の58行目:line 33-System.Data.SqlClient.SqlConnection.OnError(SqlException例外、ブール値breakConnection)でのSystem.Data.SqlClient.SqlInternalConnection.OnError(SqlException例外、ブール値breakConnection)でのSystem.Data.SqlClient.TdsParser.ThrowExceptionAndWarning()でのSqlException System.Data.SqlClient.TdsParser.Run(RunBehavior runBehavior、SqlCommand cmdHandler、SqlDataReader dataStream、BulkCopySimpleResultSet bulkCopyHandler、TdsParserStateObject stateOでbj)System.Data.SqlClient.SqlDataReader.ConsumeMetaData()at System.Data.SqlClient.SqlDataReader.get_MetaData()at System.Data.SqlClient.SqlCommand.FinishExecuteReader(SqlDataReader ds、RunBehavior runBehavior、String resetOptionsString)at System.Data .SqlClient.SqlCommand.RunExecuteReaderTds(CommandBehavior cmdBehavior、RunBehavior runBehavior、Boolean returnStream、Boolean async)at System.Data.SqlClient.SqlCommand.RunExecuteReader(CommandBehavior cmdBehavior、RunBehavior runBehavior、Boolean returnStream、String method、DbAsyncResult。) SqlClient.SqlCommand.RunExecuteReader(CommandBehavior cmdBehavior、RunBehavior runBehavior、Boolean returnStream、String method)at System.Data.SqlClient.SqlCommand.ExecuteReader(CommandBehavior behavior、String method)at System.Data.SqlClient.SqlCommand.ExecuteDbDataReader(CommandBehavior behavior) System.Data.Mapping.Update.Internal.DynamicUpdateCommaのSystem.Data.Common.DbCommand.ExecuteReader(CommandBehavior behavior) nd.Execute(UpdateTranslatorトランスレーター、EntityConnection接続、Dictionary _2 identifierValues, List_ 1 generatedValues)at System.Data.Mapping.Update.Internal.UpdateTranslator.Update(IEntityStateManager stateManager、IEntityAdapterアダプター)

60
KevinDeus

エンティティフレームワークは、すべての日付をDatetime2として処理するため、データベースのフィールドがDatetimeである場合、これは問題になる可能性があります。ここでも同じ問題があり、すべての日付フィールドにデータを入力し、データ型を変更することが、最も一般的なソリューションです

65
Tejo

Code Firstを使用している場合、オプションのDateTimeプロパティをDateTime?またはNullable<DateTime>として宣言する必要があります。 DateTimeオブジェクトの設定を解除すると、問題が発生する可能性があります。

プロパティがデータベースでNULL可能であり、コードで標準のDateTimeDateTime?ではない)である場合、ADO.NETは0001-01-01(NULLではなく)の日付で最小SQL DateTimeの挿入コマンドを送信します値は1753-01-01で、エラーが発生しています。コード内のDateTimeプロパティがNULL可能(たとえば、DateTime?またはNullable<DateTime>)の場合、挿入コマンドは範囲外の日付の代わりにNULLを挿入しようとします。

49
stepanZ

そのSQLスクリプトを使用して、すべての列をdatetimeからdatetime2に変換します。便宜上、「aspnet」を含むすべてのテーブルをスキップします。

DECLARE @SQL AS NVARCHAR(1024)
DECLARE @TBL AS NVARCHAR(255)
DECLARE @COL AS NVARCHAR(255)
DECLARE @NUL AS BIT

DECLARE CUR CURSOR FAST_FORWARD FOR
    SELECT  SCHEMA_NAME(t.schema_id)+'.'+t.name, c.name, c.is_nullable
    FROM    sys.tables AS t
    JOIN    sys.columns c ON t.object_id = c.object_id
    JOIN    information_schema.columns i ON i.TABLE_NAME = t.name 
                                        AND i.COLUMN_NAME = c.name
    WHERE   i.data_type = 'datetime' and t.name not like '%aspnet%'

    ORDER BY t.name, c.name

OPEN CUR
FETCH NEXT FROM CUR INTO @TBL, @COL, @NUL
WHILE @@FETCH_STATUS = 0
BEGIN
    SELECT @SQL = 'ALTER TABLE ' + @TBL 
        + ' ALTER COLUMN [' + @COL + '] datetime2' 
        + (CASE WHEN @NUL=1 THEN '' ELSE ' NOT' END) + ' NULL;'
    EXEC sp_executesql @SQL
    FETCH NEXT FROM CUR INTO @TBL, @COL, @NUL
END

CLOSE CUR;
DEALLOCATE CUR;

わたしにはできる!

13
Roman Pushkin

別の可能な解決策は、フィールドのsql列タイプをdatetime2に設定することです。これはfluentapiを使用して実行できます。

Property(x => x.TheDateTimeField)
   .HasColumnType("datetime2");

注:これは、datetime2がSQL Server 2005以下では使用できないため、SQL Server 2008以降のソリューションです。

8
InsI

私は同じ問題を抱えていたので、以下のサンプルのように[Column(TypeName = "datetime2")]属性を関連するプロパティに追加することで解決しました。

 [Column(TypeName = "datetime2")]
 public DateTime? PropertyName { get; set; }
7

私はそれが古い質問であることを知っていますが、私がここでグーグルで調べたように、他の誰かが同じことをすることができます;-) DateTimeからDateTime2への変更がオプションではないものについては空のままにしたフィールドに(DateTime)System.Data.SqlTypes.SqlDateTime.MinValueのようなものを入力する方が合理的です
DateTime.nowではなく、「擬似ヌル」値として認識しやすいため(および、親オブジェクトの部分クラスで実際のヌルに変換する必要がある場合)

5
ale.com

最初にEntityフレームワークコードを使用する場合、次のように宣言します。

public Nullable<System.DateTime> LastLogin { get; set; }
3
JoshYates1980

同じ問題がありました。これは、mssqlバージョンに関連していました。この方法ですべてのバージョンで動作するようにしました。

Xmlエディターでedmxファイルを開きますファイルの上部にあるこの行を見つけます

<Schema Namespace="XXXXX.Store" Alias="Self" Provider="System.Data.SqlClient" ProviderManifestToken="2008"

2008年を2005年に置き換えます。ファイルを保存し、プロジェクトを再コンパイルします。

それが将来の誰かを助けることを願っています。

私はこのソリューションをdbfirstアプローチでのみ試しました。

2
pix

エンティティにModifiedTimeプロパティがあり、データベース側でのみ更新されますか?その場合、DatabaseGeneratedOption.Computedを使用する必要があります(EF CodeFirstの場合)。こちらもご覧ください https://stackoverflow.com/a/9508312/131726

ありがとうございました。

2
eLVik

Datetimeに収まるものはdatetime2データ型に収まりますが、逆の場合も同様です。datetime2データ型に1500年1月の日付を付けることができますが、datetimeは1753にのみ戻り、datetime2列はすべて1年目までの方法1.渡す最小日付が何であるか、およびテーブルにdatetime2またはdatetimeデータ型の列があるかどうかを確認します。

1
SQLMenace

挿入/更新中に、DB(datetime)のnull以外のフィールドが除外されないようにしてください。同じエラーが発生し、それらの日時フィールドに値を挿入すると、問題は解決しました。これは、null以外の日時フィールドに適切な値が割り当てられていない場合に発生します。

1
vidya

この問題を数日間解決しようとした後、DateTimeの代わりにEntity Framework Code-Firstを使用して、モデルのデータ型としてDateTime?を使用しました。

1
jaminyah

ASP.Net MVCアプリケーションでも同じ問題が発生しました。

アプリケーションには、DateTimeプロパティを持つ2つのモデルクラスがありました。

調査すると、1つのモデルのDateTimeプロパティがnull可能であることに気づきました(つまり、誕生日のオプションプロパティにする)

もう一方のモデルには、必須データ注釈付きのDateTimeプロパティがありました(このモデルを保存するとエラーが発生します)

私のアプリはコードが最初なので、データ型をDateTime2として設定することで問題を解決しました

[Column(TypeName="datetime2")] 

その後、パッケージマネージャーコンソールで移行を実行しました。

1
Taha

シンプル。最初にコードで、DateTimeのタイプをDateTime?に設定します。そのため、データベースでnull許容のDateTime型を使用できます。

0
Ulisses Ottoni

これは、stepanZの回答から続きます... Entity Framework Code FirstAutoMapperとともに使用すると、このエラーが発生しました。

AutoMappingを設定するとき、public override int SaveChanges()関数で自動的に設定されるcreateddtupdateddtcreatedbyおよびupdatedbyフィールドがあります。これを行う場合、これらのフィールドがAutoMapperによって無視されるように設定する必要があります。そうしないと、nullから提供されない場合、データベースはViewで更新されます。

私の問題は、送信元と送信先を間違った方向に配置したため、ViewModelを設定するときではなく、Modelを設定するときにフィールドを無視しようとしたことです。

このエラーを受け取ったとき、Mappingはこのように見えました(注:2行目のcfg.CreateMap<Source, Destination>()ModelViewModelにマッピングし、Ignore()

cfg.CreateMap<EventViewModel, Event>();
cfg.CreateMap<Event, EventViewModel>()
    .ForMember(dest => dest.CreatedBy, opt => opt.Ignore())
    .ForMember(dest => dest.CreatedDt, opt => opt.Ignore())
    .ForMember(dest => dest.UpdatedBy, opt => opt.Ignore())
    .ForMember(dest => dest.UpdatedDt, opt => opt.Ignore());

ViewModelからModelへのマッピングでは、ソースと宛先を無視する必要があります(注:Ignore()ViewModelのマッピングに対して配置される場合、以下のコードは正しいです。 Model

cfg.CreateMap<Event, EventViewModel>();
cfg.CreateMap<EventViewModel, Event>()
    .ForMember(dest => dest.CreatedBy, opt => opt.Ignore())
    .ForMember(dest => dest.CreatedDt, opt => opt.Ignore())
    .ForMember(dest => dest.UpdatedBy, opt => opt.Ignore())
    .ForMember(dest => dest.UpdatedDt, opt => opt.Ignore());
0
Gwasshoppa