そもそもストアドって何?
ストアドプロシージャ(Stored Procedure)は、
「DBの中に保存しておくプログラム」
みたいなものです。
C#でいうメソッドを、
SQL Serverの中に置いておくイメージですね。
いつ使うのが効率的?
① 複雑なクエリを何度も使う場合
- JOINが多い
- 集計がある
- 条件分岐がある
- 更新+履歴登録など複数処理がある
こういうものを毎回アプリ側に書くと、散らかります。
👉 DB側にまとめておくとスッキリします。
② 複数のアプリから同じ処理を使う場合
例えば:
- Webアプリ
- バッチ
- 別システム連携
全部が同じSQLを書くと、修正時に地獄です。
ストアドにしておけば:
EXEC dbo.売上集計 @日付='2026-02-01'
これで済みます。
③ トランザクションをまとめたいとき
- 更新
- 履歴登録
- 在庫減算
- ログ保存
これを1つの処理として保証したい場合。
ストアド内で BEGIN TRAN / COMMIT を管理すると安全です。
④ セキュリティ制御したいとき
テーブルへの直接アクセスは禁止して、
- SELECT権限なし
- ストアド実行権限だけ付与
という設計も可能です。
逆に使わなくてもいいケース
- 単純なSELECT1発
- 一時的な開発用クエリ
- アプリ側で動的に組み立てたい処理
無理に全部ストアドにする必要はありません。
基本的な作り方
① シンプルな取得ストアド
CREATE PROCEDURE dbo.GetUserById
@UserId INT
AS
BEGIN
SET NOCOUNT ON;
SELECT *
FROM Users
WHERE UserId = @UserId;
END
実行:
EXEC dbo.GetUserById @UserId = 1;
② 更新+トランザクション例
CREATE PROCEDURE dbo.UpdateStock
@ItemId INT,
@Qty INT
AS
BEGIN
SET NOCOUNT ON;
BEGIN TRY
BEGIN TRAN;
UPDATE Stock
SET Quantity = Quantity - @Qty
WHERE ItemId = @ItemId;
INSERT INTO StockHistory(ItemId, Qty, UpdateDate)
VALUES(@ItemId, @Qty, GETDATE());
COMMIT;
END TRY
BEGIN CATCH
ROLLBACK;
THROW;
END CATCH
END
C# から呼び出す例
(C# example)
using (var conn = new SqlConnection(connectionString))
{
using (var cmd = new SqlCommand("dbo.GetUserById", conn))
{
cmd.CommandType = CommandType.StoredProcedure;
cmd.Parameters.AddWithValue("@UserId", 1);
conn.Open();
using (var reader = cmd.ExecuteReader())
{
while (reader.Read())
{
Console.WriteLine(reader["UserName"]);
}
}
}
}
ポイント:
cmd.CommandType = CommandType.StoredProcedure;
これ忘れる人、かなり多いです。
効率的に使うコツ(実務メモ)
① SET NOCOUNT ON は必須
余計な影響行数メッセージを出さないようにします。
パフォーマンス微改善+不具合防止。
② SELECT * はやめる
将来カラム追加されたときに壊れます。
③ ストアド内にビジネスロジックを書きすぎない
DB依存が強くなります。
「データ整形まで」にしておくのが無難。
④ パフォーマンス問題に注意
ストアドでも遅いものは遅いです。
- インデックス確認
- 実行計画確認
- パラメータスニッフィング対策
は必要です。
パラメータスニッフィング問題とは?
ストアドは最初の実行時のパラメータで実行計画を作ります。
これが:
- 少量データ用プラン
- 大量データ用プラン
どちらかに偏ると遅くなります。
対策例:
OPTION (RECOMPILE)
や
DECLARE @LocalId INT = @UserId
などがあります。
メリット・デメリット
メリット
- 処理の集中管理
- セキュリティ制御
- トランザクション制御が簡単
- アプリが軽くなる
デメリット
- バージョン管理が面倒
- DB依存が強くなる
- ロジック肥大化の危険
結論:どう使うのがよい?
個人的な実務感覚ですが:
✅ 更新系はストアドに寄せる
✅ 複雑な集計もストアド
✅ 単純SELECTはアプリ側でもOK
これがバランス良いです。
まとめ
ストアドは、
「DBをただのデータ置き場にするか」
「処理を持たせるか」
の設計思想の違いです。
全部をストアドにするのは極端ですが、
適材適所で使うとかなり効率的になります。

コメント