Shikata Ga Nai

Private? There is no such things.

一括代入(Mass Assignment)脆弱性 – 隠れたパラメータが引き起こす危険

Hello there, ('ω')ノ

Mass Assignment(マスアサインメント)脆弱性とは、Webアプリケーションがユーザーからのリクエストに含まれるデータを自動的に内部オブジェクトにマッピング(バインド)する際、開発者が意図していないフィールドまで書き換え可能になる脆弱性です。

この仕組みにより、隠れたパラメータ(非公開のフィールド)が存在する場合、それをリクエストに含めることで不正操作が可能になります。


🔧 Mass Assignmentの仕組み

多くのWebフレームワーク(例:Ruby on Rails, Laravel, Express.jsなど)は、次のような「自動マッピング機能(Auto-binding)」を持っています:

POST /api/user/update
{
  "name": "taro",
  "email": "taro@example.com"
}

このリクエストが来ると、サーバー側で以下のようなUserオブジェクトに自動で値が入ります:

user.name = "taro"
user.email = "taro@example.com"

❗️問題点:意図しないフィールドも代入されてしまう

例えば、role, isAdmin, balance, password, isVerified などの 本来ユーザーが操作すべきでないフィールド が存在した場合、それをリクエストに含めることで変更できてしまうことがあります。

{
  "name": "taro",
  "role": "admin"
}

👉 これだけで一般ユーザーが管理者になれる可能性!


🔍 Mass Assignment脆弱性の発見方法

APIでPOST/PUT/PATCHを受け付けるエンドポイントを探す

  • 例:/api/user/update, /api/profile, /api/register など

推測されるフィールド名を追加してリクエストを送信する

{
  "name": "taro",
  "isAdmin": true,
  "isVerified": true,
  "role": "admin",
  "balance": 999999
}

📌 レスポンスの内容が変わるか?DBの変更が反映されるか?を観察する

Burp IntruderやParam Minerでフィールド名を自動で挿入して試す

  • isAdmin, role, permissions, account_type, verified, status, tier, scope などが狙い目。

🧠 典型的なMass Assignment攻撃例

リクエストの追加パラメータ 効果
"role": "admin" 管理者権限の取得
"isAdmin": true 管理者フラグの強制
"isVerified": true 本人確認バイパス
"balance": 999999 所持金の不正加算
"email_verified": true メール検証バイパス
"subscription": "premium" 有料プランへの昇格

防御策(開発側)※参考情報

  • 許可されたフィールドだけを指定する(ホワイトリスト制御)
    例:User.update(request.only(['name', 'email']))
  • 自動バインド機能を無効にする
  • テストで不正なフィールドが処理されないか確認する

🔚 まとめ

✅ Mass Assignmentは、「隠れたフィールド」×「自動バインド」 の組み合わせで発生する脆弱性
✅ JSONボディに余計なパラメータを追加するだけで深刻な影響を与える可能性あり
✅ POST/PUT/PATCHのAPIには積極的にこのテストを行うべき
✅ Burp IntruderやParam Minerを活用して、より多くのフィールド名を自動で試す

この脆弱性はシンプルですが、アプリのロジックを丸ごと乗っ取ることができるほど深刻なケースもあります。APIテストの際には必ずチェックしましょう!

Best regards, (^^ゞ