質問: 私はしばらくの間正常に動作しているアプリケーションを持っていますが、機会に邪魔になるアイテムがあります。 たとえば、OracleDataReaderやMySQLDataReaderなどのオブジェクトを使用して、データをsqlbulkcopyオブジェクトに渡して挿入するとします。すべての列が正しくマップされていると仮定しましょう。ほとんどの場合、すべてがうまくいきます。 確かに、私はソースアプリケーションまたはデータベース(MySQLまたはOracleのいずれか)を制御できません。だから、いくつかのばかは別のアプリケーションに入り、5/31/0210の請求書テーブルに日付を入れます。彼は実際に2010年5月31日を付けようとしていましたが、彼が使用しているアプリケーションはデータをきちんと検証しておらず、Oracleデータベースもそれを受け入れています。すべての集中的な目的で、2002年5月31日のデータは、Oracleデータベースの有効な日付です。それはデータ入力の点ではばかばかしいかもしれませんが、それは今のところです。 今度はOracleDataReaderが提供され、SQLBulkCopyを介してこの請求書テーブルをSQL Serverに転送しています。これは、データを完全に一致するテーブルに、正しい列名とデータ型で渡しています。あなたは何が起こるかを見ることができます。 DATETIMEフィールドでは、1995年1月1日から12月31日までの日付のみが許可されるため、Oracleの05/31/0210のこの日付はSQL Serverデータベースエンジンでは受け入れられません。 このレコードに遭遇すると、単に失敗し、オーバーフローエラーが発生します。それはレコードをスキップしません、それはフィードを殺す。だから100万レコードテーブルに1000レコードがある場合、残っている999,000レコードは得られません。 フィードが続行されるようにこの問題を回避する方法はありますか? 理想的には、受け取るSQL Serverデータベースを2008年に移動し、DATETIME2を使用してこれらの奇妙な日付を使用したいと思いますが、残念ながらすべてのクライアントがこのバージョンに移行する準備ができていないため、DATETIME SQL 2000/2005/2008。 どのようにSQLを変更せずにこれを回避するための任意のアイデア?理想的には、レコードをスキップしても大丈夫です。私はdatarederのためにSQLでこれを行うことができることを知っていますが、これは1つのクエリで20の日付フィールドがあると非常に複雑になります。それはメンテナンスの悪夢だろう。 いかなる考えも認められるだろう。
回答: 1つのオプションは、datetime列の型をvarcharに変更することです。次に、文字列をdatetimeに変換するための派生列を追加します。このトリックは、派生列の関数を使用して日付を検証し、変換が失敗すると任意の日時を設定することです。大量の日付比較を行う場合は、計算列を保持し、インデックスを作成します。 私はsqlbulkcopyが変換を行うことができないという印象の下で、このすべてを言います。たぶんあなたはできる。うまくいけば、誰かが方法でチャイムします。 このような状況では、変換を実行し、一括更新ロックのパフォーマンス上の利点を得ることができるため、SSISは優れています。