セイコーマートの不正アクセスは、1件の不正退会が発覚の端緒だった。公表文の「アプリのサーバーを経由して」を三層構成で読み、Kia・GitHub・Drupal・phpMyAdmin・T-Mobileの過去事例から「呼んだらできた」型の認可不備を整理する。過去の失敗を検出ルールに変えるSASTと、文脈を読むAutoTriage・Code Security Audit・AI Pentestの役割を解説。
57万アカウントの情報が閲覧された可能性。その発覚の端緒は、たった1件の不正退会だった。
セイコーマートは2026年9月29日、スマートフォンアプリのサーバーを経由し、会員情報を保有するサーバーに第三者が不正にアクセスしたと公表した。
9月24日22〜23時に1件の不正退会が発生し、28日17時過ぎに会員サーバーへの不正アクセスの可能性が判明。同日20時に接続を停止し、入会・会員情報変更・退会・マイページへのログインなどを停止した。24日の時刻は、即時検知した時刻とは限らない。
閲覧された可能性があるのは約57万アカウントの氏名、住所、連絡先、生年月日、入退会年月日など。パスワードは漏えいしていないとし、クレジットカード情報は保有していない。ペコママネーの不正利用も確認されていないという。[1]
公表文の「アプリのサーバーを経由して」という説明は重要だ。通常のAPIが悪用されたのか、アプリサーバー自体が侵害されたのかは分からない。だが、アプリの先にあるサーバーと、会員情報を保有するサーバーの間を考える手掛かりになる。
この1件には、金銭目的で大量の情報を盗むプロの攻撃とは違う印象を受ける。狙いは情報の売買ではなく、特定の会員を退会させること、あるいは「この操作は通るのか」を試すことだったのではないか。
ここでは、その仮説から考えてみたい。
仮に、専門的な攻撃技術を持つ人物の仕業ではなかったとしたら。穴も、一般のWebエンジニアがブラウザの通信やJavaScript、アプリの構造を調べれば気づく程度のものだった可能性がある。
正規にログインして得た自分のトークンでAPIを呼び、操作対象の会員を変えると、退会処理が通ってしまう。サーバーは「ログイン済みか」を確認していても、「その会員を操作してよいか」までは確認していなかった――そんな、コード上の確認漏れだ。
不正退会1件の調査から、閲覧機能にも同じ種類の穴が見つかったのかもしれない。そうなら、57万アカウントという数字は、大量取得の実績ではなく、確認漏れが及ぶ範囲だったとも読める。
原因も攻撃者像も未公表であり、これは一つの仮説だ。退会と閲覧の不備も別々に確認する必要がある。しかし、こうした「仕組みを読んで、呼んだらできた」という問題は、過去にも実際に起きている。
問いたいのは、単純な不備が、なぜ広い影響につながるのか。そして、その不備を公開前にどう見つけるかだ。
過去の事例をたどると、確認すべきコードの場所が見えてくる。本人と対象データの照合、管理機能の利用権限、変更を許す項目、入力からSQLへ至る処理。その知見を検出ルールや解析に落とし込むのがSASTであり、検出結果にコードの文脈を加えて、実際の危険性や誤検知を判断するところにAIの役割がある。
ログインは「誰であるか」を確認する。その人が「誰の情報に、何をしてよいか」は、別の確認だ。
Aさんのトークンが有効でも、Bさんを退会させる権限があるとは限らない。
ところが、APIがログイン済みかだけを確認し、リクエストで指定された会員をそのまま処理していたらどうなるか。画面では自分の会員情報しか選べなくても、API側では他人の情報を指定できてしまう。
こうした対象データ単位の認可不備が、IDOR/BOLAだ。[2]
APIのURLがJavaScriptから分かることや、ブラウザがトークンを保持すること自体が問題なのではない。APIは、画面を介さないリクエストにも、同じ権限確認を実施しなければならない。
DBのパスワードを盗む必要もない。Webアプリは、業務のためにDBを読み書きする権限を持っている。許されない依頼をアプリが受け入れれば、アプリ自身がその権限で処理してしまう。
2024年に公表されたKiaの事例では、研究者がWebのJavaScriptから、販売店向けの車両照会・登録・登録解除などの呼び出しを見つけた。
登録・認証の不備を通じて取得したトークンで販売店向けAPIにアクセスし、所有者情報の取得や車両との紐付け変更を実証した。研究者による検証で、修正確認後に公開された事例だ。[3]
今回考えている「Webから呼び出し方が分かり、トークンを使ったら本来許されない操作が通った」に近い。一般利用者と販売店、利用者と操作対象という権限の境界が重要になる。
Kiaの調査はWebのJavaScriptが手掛かりだったが、スマホアプリにも同じ観点が当てはまる。
AndroidのAPKなど、端末に配布されるアプリのコードやリソースは解析対象になり得る。APIの接続先や送信項目が読み取れる場合があり、端末上での実行や通信の解析から、サーバーとのやり取りが分かる場合もある。
すべてが簡単に読めるわけではない。難読化は解析を難しくし、証明書ピンニングは通信の傍受・改変を難しくする。ただし、いずれも「この利用者が、この会員を操作してよいか」というサーバー側の認可を代替しない。[13][14]
アプリの内部を読まれても、呼び出し方を知られても、許されない操作はサーバー側で拒否する。その前提で設計する必要がある。
2012年、GitHubでは公開鍵の更新フォームの不備を使い、利用者がRails組織に自分の公開鍵を追加し、ファイルをpushした。
原因は、入力パラメーターを適切に制限しないMass Assignmentだった。GitHubは後の説明で、調査の結果、この利用者に悪意はなかったと判断したとしている。[4][5]
「金銭目的の攻撃者でなくても、実際に不正な変更を起こせる」ことを示す例だ。同時に、画面に入力欄がないことは、サーバーがその項目を変更できないことを意味しない。
Drupalの2014年のCVE-2014-3704は、DB抽象化APIの不備により、未認証のリクエストから任意のSQLを実行できる問題だった。公開後の実悪用も公式に報告されている。[6]
認可不備とは入口が違う。利用者の入力をデータとして扱うべきところで、SQLの意味を変えられてしまう。
2019年のCVE-2019-12616では、CSRFにより、利用者のブラウザを介して不正なSQL操作を実行させ得た。[7]
誰でも管理画面に入れる問題ではない。利用者が持つ権限を、その本人が意図しない操作に使わせる問題だ。
T-Mobileは2023年、単一のAPIを通じ、約3,700万アカウントの情報が不正に取得されたと公表した。取得された情報には氏名や住所、連絡先などが含まれたが、そのAPIはパスワードや決済カード情報を提供しないと説明している。[8]
公表内容から原因をIDORと断定することはできない。それでも、APIから返る情報だけで、影響が大規模になり得ることは分かる。
これらは、セイコーマートの原因を証明する事例ではない。自社で確認すべき失敗の型を示している。
権限不備は、管理画面の設定を一つ変えれば済むとは限らない。コードの中で、次の確認を実装する必要がある。
| 確認する境界 | 必要な確認 | 抜けたときに起こること |
|---|---|---|
| 認証 | トークンは有効か。誰のものか | 未認証・無効な認証でも操作できる |
| 対象データ | この人が、この会員を操作してよいか | 他人の情報を閲覧・変更できる |
| 機能 | この人が、この管理機能を使ってよいか | 一般会員が管理者向け処理を呼べる |
| 項目 | この操作で、どの項目を変更してよいか | 通常の情報変更から会員状態や権限まで変わる |
| DB権限 | このアプリに必要なテーブル・操作はどこまでか | 一つの不備が不要な情報や操作にまで及ぶ |
例えば、会員情報を取得するとき、「指定された会員IDが存在するか」だけでは足りない。「ログイン者に参照が許されている会員か」まで確認する。
DB接続ユーザーを最小権限にすることは重要だが、そのユーザーを全会員の処理で共用している場合、DBへの接続許可だけでは会員間の分離にならない。
ここで、公表文の「アプリのサーバーを経由して」を、一般的な三層構成に当てはめて考える。利用者のアプリ、その依頼を受けるアプリサーバー、会員情報を保有するサーバーだ。これは公表文を考えるためのモデルであり、実際の物理構成やAPIの分担を確認したものではない。
仮に、アプリサーバーがサービス共通の資格情報で会員情報サーバーを呼び、会員全体を扱う権限を持っていたとする。背後のサーバーが「正規のアプリサーバーから来た」という理由だけで依頼を受け入れるなら、会員Aの依頼で会員Bを操作してよいかの判断は、手前のコードに依存する。
その確認が抜けると、正規のアプリサーバーが正規の権限を使って、不正な依頼を通してしまう。
防御を置けるのは、手前だけではない。会員情報サーバー側でも、検証可能な利用者情報や操作範囲を受け取り、対象との関係を確認できる。DBの行単位制御などで補強する設計もある。
重要なのは、「誰の依頼か」が途中で失われていないか、そして「どの層が何を確認するか」が明確かどうかだ。会員IDを単に転送するだけでは、本人の依頼であることの保証にはならない。
今回も、この真ん中のアプリサーバー、または背後への権限の渡し方に問題があったのではないか。公表文から考える仮説として、ここに注目したい。
また、SQLインジェクション対策と認可対策は別だ。SQLを安全に組み立てても、Bさんの情報をAさんへ返してよいかの判断は残る。会員IDを推測しにくくしても、認可確認の代わりにはならない。[2]
過去の事例や研究から分かった危険な実装を、検出ルールや解析手法として蓄積し、自社のソースコードに同じ種類の問題がないか調べる。これがSASTの重要な役割だ。
例えば、外部入力がSQLの組み立てに届く経路、任意の入力項目をデータモデルへ反映する処理などを調べる。単なる文字列検索にとどまらず、入力から危険な処理までのデータの流れや条件分岐を追う。
SASTは、過去の被害企業と同じコードだけを探すものではない。失敗の構造を一般化して、新しいコードにも適用する。
ただ、ここで難しいのが文脈だ。
ある処理に権限確認が見えなくても、共通の前処理で確認済みかもしれない。反対に、ログイン確認があっても、対象会員の確認は抜けているかもしれない。
「怪しく見える箇所」と「実際に悪用できる箇所」を分けなければ、誤検知への対応で開発者の時間が消えてしまう。[9]
AikidoのAutoTriageは、SASTの検出結果を起点に、入力が利用者に制御されるか、途中の検証が有効か、問題の処理まで届くかなどを評価する。誤検知、つまりFPを減らし、残る問題の優先順位を判断するためにAIを活用する。[10]
例えば、SQLインジェクションの疑いが出ても、入力元や途中の制約によっては悪用できない。一方、入力が外部から届き、有効な防御もなければ、修正すべき指摘として残る。
ただし、IDORのように「本来誰に何を許すべきか」の理解が必要な問題では、SASTの指摘を精査するだけでは足りない場合もある。
Aikidoは、ソースコード全体の権限確認やデータの流れを分析するCode Security Auditと、動作中のアプリで実際の越権アクセスを検査するAI Pentestも提供している。[11][12]
| 検査 | 主に確かめること |
|---|---|
| SAST | 既知の危険な実装パターンやデータの流れがあるか |
| AutoTriage | その指摘は、このコードの文脈でも悪用可能か。FPか。優先度はどうか |
| Code Security Audit | 複数の処理を通して、所有者確認や権限の境界が欠けていないか |
| AI Pentest | 許可されたテスト環境で、実際に他人の情報へアクセス・操作できるか |
AIの判断にも、与えられるコードや仕様、テスト用の権限に限界がある。「FPと判定されたから終了」ではなく、どの防御が、どの経路で有効だから除外したのか、その根拠を確認できることが重要だ。
今回の攻撃者が、プロだったかどうかは分からない。だが、守る側が想定すべき相手は、高度な技術を持つ集団だけではない。
自分のアカウントでログインし、ブラウザやアプリの通信を調べ、操作を少し変えた人。それだけで他人の情報に届くコードを残さない。
自分のトークンで、自分以外の会員を指定したとき、アプリサーバーのどのコードが止めるのか。背後の会員情報サーバーには、誰の依頼として届くのか。
その答えを、実装と検査結果で示せるだろうか。
Aikido Community Japan
公開日: 2026/9/29
最終更新: 2026/9/30
セキュリティの最新情報をお届けします。