実行の最適化とパラメータ受け渡し

1. SqlConnection 接続状態の判定

プロパティ:conn.State

列挙型 ConnectionState

// 接続が開かれていない場合、接続をオープンする
if (conn.State != ConnectionState.Open)
{
    conn.Open();
}Code language: JavaScript (javascript)

備考:usingと併用する場合、接続が解放されると自動的に状態がClosedに変わります。
代表的な状態:Open / Closed / Connecting など。

2. ExecuteScalar における null 判定のポイント

ExecuteScalarの戻り値を検証し、nullによる例外を回避します

object obj = sqlCom.ExecuteScalar();

// null と DBNull.Value の両方を判定する必要があります
if (obj == null || obj == System.DBNull.Value)
{
    MessageBox.Show("実行結果がnullです");
}
else
{
    MessageBox.Show(obj.ToString());
}Code language: JavaScript (javascript)

違い:

  • null:1行もデータが返ってこなかった
  • DBNull.Value:行は取得できたが、対象フィールドのDB値がNULL

3. SqlCommand パラメータ機構(SQLインジェクション対策の核心)

1. 主要オブジェクト

SqlCommand.Parametersコレクションに複数のSqlParameterパラメータを格納します。パラメータ化クエリを使えばSQLインジェクションの脆弱性を根本的に防げます。

2. パラメータ作成サンプル
// パラメータ名、データ型、サイズ
SqlParameter paramSql = new SqlParameter("@Title", SqlDbType.NVarChar, 250);

// 値を代入
paramSql.Value = model.Title;

// コマンドオブジェクトへ追加
sqlCom.Parameters.Add(paramSql);Code language: JavaScript (javascript)
3. ParameterDirection(列挙型:パラメータの方向)
paramSql.Direction = ParameterDirection.Output;
列挙メンバー説明
Input1既定、入力パラメータ(SQLへ値を渡す)
Output2出力パラメータ、ストアドプロシージャ実行後に結果を受け取る
InputOutput3入力と出力の両方に対応

完全なコード例

private void button1_Click(object sender, EventArgs e)
{
    string connectionString = "Data Source=.;Initial Catalog=db;User ID=sa;Password=xxx";
    using (SqlConnection conn = new SqlConnection(connectionString))
    {
        // 安全に接続を開く
        if (conn.State != ConnectionState.Open)
        {
            conn.Open();
        }

        SqlCommand sqlCom = new SqlCommand();
        sqlCom.Connection = conn;
        sqlCom.CommandTimeout = 60;
        // 文字列連結は禁止、必ずパラメータ化SQLを使用
        sqlCom.CommandText = "SELECT [Title] FROM [dbo].[Article] WHERE Title = @Title";

        // パラメータを生成
        SqlParameter paramTitle = new SqlParameter("@Title", SqlDbType.NChar, 10);
        paramTitle.Value = "テストタイトル";
        sqlCom.Parameters.Add(paramTitle);

        object obj = sqlCom.ExecuteScalar();
        if (obj == null || obj == DBNull.Value)
        {
            MessageBox.Show("実行結果がnullです");
        }
        else
        {
            MessageBox.Show(obj.ToString());
        }
    }
}Code language: JavaScript (javascript)

重要な開発ルール

  1. SQL文字列を直接連結してはいけません。常にSqlParameterによるパラメータ化を行う;
  2. SqlConnectionSqlCommandは原則usingで記述しリソースを自動解放;
  3. ExecuteScalar実行後はnull + DBNull.Valueの両方をチェック;
  4. CommandTimeout(SQL実行タイムアウト)と接続文字列内のConnect Timeout(接続確立タイムアウト)を区別する。

実行の最適化とパラメータ受け渡し

コメントを残す

メールアドレスが公開されることはありません。 が付いている欄は必須項目です