基本情報技術者 2015年 秋期 午前(科目A) 問42
問題文
SQLインジェクション攻撃を防ぐ方法はどれか。
選択肢
ア:入力中の文字がデータベースへの問合せや操作において、特別な意味をもつ文字として解釈されないようにする。(正解)
イ:入力にHTMLタグが含まれていたら、HTMLタグとして解釈されない他の文字列に置き換える。
ウ:入力に上位ディレクトリを指定する文字列(../)が含まれているときは受け付けない。
エ:入力の全体の長さが制限を超えているときは受け付けない。
SQLインジェクション攻撃を防ぐ方法はどれか。【午前2 解説】
要点まとめ
- 結論:SQLインジェクション防御は、入力をそのままSQL構文に組み込まない「文字を意味を持たせない処理」が有効です。
- 根拠:パラメータ化やプレースホルダは入力をデータとして扱い、SQL構文と混同させないため根本的に危険を排除します。
- 差がつくポイント:単なる長さ制限やHTMLエスケープ、ディレクトリの拒否は別の脅威対策であり、SQLi対策には不十分です。
正解の理由
ア(入力中の文字がデータベースへの問合せや操作において、特別な意味をもつ文字として解釈されないようにする。)が正解です。
この選択肢は「パラメータ化(プレースホルダ)、プリペアドステートメント、適切なエスケープ」を含む広い意味での対策を表しており、入力値をSQL構文と分離して扱うことでSQLインジェクションの根本原因を断ちます。プレースホルダを使えば攻撃文字列がSQL文の構造を書き換えることができなくなります。
この選択肢は「パラメータ化(プレースホルダ)、プリペアドステートメント、適切なエスケープ」を含む広い意味での対策を表しており、入力値をSQL構文と分離して扱うことでSQLインジェクションの根本原因を断ちます。プレースホルダを使えば攻撃文字列がSQL文の構造を書き換えることができなくなります。
よくある誤解
- 「HTMLエスケープでSQLインジェクションも防げる」は誤解です。HTMLエスケープは主にXSS対策で、SQL文の構造には影響しません。
- 「入力長制限すれば大丈夫」も不足です。長さ制限は攻撃の幅を減らすが、短い悪意ある文字列でも注入可能です。
- 「../を弾けば安全」も誤りで、ディレクトリトラバーサル対策はファイルアクセスの攻撃に対するもので、SQL注入には無関係です。
解法ステップ
- 問題文で問われている攻撃(SQLインジェクション)の対象と影響範囲を確認する。
- 各選択肢がどの脅威に対応するか(SQL、XSS、ファイルトラバーサル、入力検証)を照合する。
- SQLインジェクションに直接効くのは「入力をSQL構文として解釈させない」処理であると判断する。
- 最終的にアが該当するため正解とする。
選択肢別の誤答解説
- ア: 入力中の文字がデータベースへの問合せや操作において、特別な意味をもつ文字として解釈されないようにする。
→ 正解。パラメータ化やプリペアドステートメントに相当し、SQL文とデータを分離する根本対策を示す。 - イ: 入力にHTMLタグが含まれていたら、HTMLタグとして解釈されない他の文字列に置き換える。
→ 誤り。これはクロスサイトスクリプティング(XSS)対策であり、SQL文の構造を書き換える攻撃(SQLi)とは別次元の対策。 - ウ: 入力に上位ディレクトリを指定する文字列(../)が含まれているときは受け付けない。
→ 誤り。ディレクトリトラバーサル対策でファイルアクセス制御に関するもので、SQLインジェクション対策ではない。 - エ: 入力の全体の長さが制限を超えているときは受け付けない。
→ 誤り。長さ制限は補助的対策に過ぎず、短い悪意ある入力であれば容易に注入され得るため根本的な防御策ではない。
補足コラム
安全な実装の具体例として、プレースホルダ/パラメータ化クエリを使う方法が最も推奨されます。以下にPython(sqlite3)の例を示します。
# 危険(文字列連結でSQLを組み立てると注入される) user_input = "'; DROP TABLE users; --" sql = "SELECT * FROM users WHERE name = '" + user_input + "'" cursor.execute(sql) # 安全(プレースホルダを使用、入力はデータとして扱われる) sql = "SELECT * FROM users WHERE name = ?" cursor.execute(sql, (user_input,))
ポイント:
- 常にプリペアドステートメントやORMのパラメータ機能を使うこと。
- エスケープ処理はDBごとに挙動が異なりミスの原因になりやすいため、原則としてパラメータ化を優先すること。
- 追加対策として最小権限のDBユーザ、WAF、監査ログを組み合わせると安全性が向上します。
FAQ
Q1: 文字のエスケープだけで十分ですか?
A1: 場合によっては有効ですがヒューマンエラーやDB依存の違いで破られやすく、パラメータ化が第一選択です。
A1: 場合によっては有効ですがヒューマンエラーやDB依存の違いで破られやすく、パラメータ化が第一選択です。
Q2: ストアドプロシージャはSQLインジェクションを防げますか?
A2: パラメータを使うストアドプロシージャは有効ですが、内部で動的SQLを文字列連結していると安全とは言えません。
A2: パラメータを使うストアドプロシージャは有効ですが、内部で動的SQLを文字列連結していると安全とは言えません。
Q3: WAFだけで大丈夫ですか?
A3: WAFは有用な補助ですが、アプリ側でのパラメータ化など根本対策を置き換えるものではありません。
A3: WAFは有用な補助ですが、アプリ側でのパラメータ化など根本対策を置き換えるものではありません。
Q4: 入力検証(ホワイトリスト)は有効ですか?
A4: はい。期待される形式(数値だけ、特定の正規表現など)をホワイトリストで検査することは有効な補助策です。
A4: はい。期待される形式(数値だけ、特定の正規表現など)をホワイトリストで検査することは有効な補助策です。
関連キーワード: SQLインジェクション、パラメータ化クエリ、プリペアドステートメント、プレースホルダ、エスケープ、入力検証、ホワイトリスト、XSS、ディレクトリトラバーサル、WAF

\ せっかくなら /
基本情報技術者を
クイズ形式で学習しませんか?
クイズ画面へ遷移する→
すぐに利用可能!

