web-dev-qa-db-ja.com

C#を使用してSQLデータベースに日時値を挿入する

列の型がdatetimeであるSQLデータベーステーブルにdatetime値を挿入するにはどうすればよいですか?

31
sama

以下が機能するはずであり、私の推奨事項です(パラメーター化されたクエリ)。

DateTime dateTimeVariable = //some DateTime value, e.g. DateTime.Now;
SqlCommand cmd = new SqlCommand("INSERT INTO <table> (<column>) VALUES (@value)", connection);
cmd.Parameters.AddWithValue("@value", dateTimeVariable);

cmd.ExecuteNonQuery();
82
 DateTime time = DateTime.Now;              // Use current time
 string format = "yyyy-MM-dd HH:mm:ss";    // modify the format depending upon input required in the column in database 
 string insert = @" insert into Table(DateTime Column) values ('" + time.ToString(format) + "')"; 

クエリを実行します。 DateTime.Nowは、現在の日時を挿入します。

17
Reshma

yyyy-mm-dd hh:mm:ss(IE:2009-06-23 19:30:20))

これを使用すると、日付の形式(MM/DD/YYYYまたはDD/MM/YYYY)を心配する必要はありません。それらのすべてで動作します。

8
Andrea
using (SqlConnection conn = new SqlConnection())
using (SqlCommand cmd = conn.CreateCommand())
{
    cmd.CommandText = "INSERT INTO <table> (<date_column>) VALUES ('2010-01-01 12:00')";
    cmd.ExecuteNonQuery();
}

私がこのようなものを書いてからしばらく経ったので、これは完璧ではないかもしれません。しかし、一般的な考え方はそこにあります。

警告:これは不衛生です。パラメータを使用して、インジェクション攻撃を回避する必要があります。

編集:ジョンが主張するので。

3
Joel

これは適切な回答( パラメータ化されたクエリを使用してください )が付いた古い質問であり、タイムゾーンの議論で拡張したいと思います。私の現在のプロジェクトでは、datetime列がタイムゾーンをどのように処理するかに興味があり、この質問は私が見つけたものです。

結局のところ、そうではありません。

datetime列には、指定されたDateTimeがそのまま変換されずに保存されます。指定された日時がUTCかローカルかは関係ありません。

あなたは自分で見ることができます:

using (var connection = new SqlConnection(connectionString))
{
    connection.Open();
    using (var command = connection.CreateCommand())
    {
        command.CommandText = "SELECT * FROM (VALUES (@a, @b, @c)) example(a, b, c);";

        var local = DateTime.Now;
        var utc = local.ToUniversalTime();

        command.Parameters.AddWithValue("@a", utc);
        command.Parameters.AddWithValue("@b", local);
        command.Parameters.AddWithValue("@c", utc.ToLocalTime());

        using (var reader = command.ExecuteReader())
        {
            reader.Read();

            var localRendered = local.ToString("o");

            Console.WriteLine($"a = {utc.ToString("o").PadRight(localRendered.Length, ' ')} read = {reader.GetDateTime(0):o}, {reader.GetDateTime(0).Kind}");
            Console.WriteLine($"b = {local:o} read = {reader.GetDateTime(1):o}, {reader.GetDateTime(1).Kind}");
            Console.WriteLine($"{"".PadRight(localRendered.Length + 4, ' ')} read = {reader.GetDateTime(2):o}, {reader.GetDateTime(2).Kind}");
        }
    }
}

これが何を印刷するかは、もちろんあなたのタイムゾーンに依存しますが、最も重要なことには、読み取り値はすべてKind = Unspecified。最初と2番目の出力行は、タイムゾーンオフセットによって異なります。 2番目と3番目は同じです。 "o"フォーマット文字列(往復) を使用すると、読み取り値のタイムゾーン指定子は表示されません。

GMT + 02:00からの出力例:

a = 2018-11-20T10:17:56.8710881Z      read = 2018-11-20T10:17:56.8700000, Unspecified
b = 2018-11-20T12:17:56.8710881+02:00 read = 2018-11-20T12:17:56.8700000, Unspecified
                                      read = 2018-11-20T12:17:56.8700000, Unspecified

また、データが10ミリ秒のように切り捨てられる(または丸められる)方法にも注意してください。

1
joonas