静的サイトホスティングは万能か?
WEBサイトって一般的にブラウザがHTMLやCSS、Js、その他画像などのファイルを読み込んで描写されているものを言うよね?一方Webサイトを作成するには、Webサーバーが必要という。特に有名なCMSであるWordPressではサーバーでPHPやデータベースが動作してサイトが構築 …
前回の記事で書いたとおり、全くユーザーが動作させる機能がないようなコーポレートサイトやLPサイトは静的サイトで作成するほうが、あらゆる面でメリットがある。ところがそれら以外の普通のWEBシステムでは、バックエンドでの動的な処理が必要なはずだ。今回はそのセキュリティの話。
今回考えたいのは以下のようなことだ。これは静的サイトだけでなく普通のSSRサイト(.NetとかRailsとかlaravelで作ったシステム)でも起こりうることだ。ちなみにクライアントはブラウザやアプリのことを意味する。
つまり、特定のクライアント以外からAPIを悪い人がたたきまくれる状態って非常に怖いよねってこと。ある程度対策が存在するけど、特に静的サイトではこういう対策がお粗末なサイトがたくさん存在する。
まず、適切なユーザー認証を行うこと、そしてCORSの許可ドメインをガバガバにしない、CSRFトークンを送信するなどの対策は当たり前にやってほしい。CORSとかCSRF、XSSなどでググるとSSRサイト、SPAサイトそれぞれの対策方法が出てくるので、よくわからない人はチェック。
で、私が今回書きたいのは、 CSRFとかCORSの話じゃない! 認証があろうがなかろうが、アクセスオリジンをみてチェックしてようが、CookieをHTTPOnlyにしてようが、cURLなどのブラウザ経由でないリクエストで簡単にAPIをたたけてしまうなら、それは多少の不正操作リスクが存在してしまうってこと。ユーザー認証がある場合であっても適当に作成した自分の認証トークンを取得して利用されたら直接APIコールできてしまう。また、CORSとかCookieの制限ってあくまでブラウザでの話だからね。
同時にスマホアプリやデスクトップアプリからの通信も当該アプリ内からのリクエストのみ許可するようしたい。(難読化が必要)
日本に住む人は一度は以下のサイトを利用したことがあるのではないだろうか。行政の粗大ごみ受付センターのサイトだ。このサイトがいい例になる。
調べてみたらシステム自体は多くの市区町村で同じものが多く(私が見たのは4自治体程度だが)、ドメインやWEBサーバーはそれぞれ分かれているみたいだ。またサイトのデザインは自治体ごとに少し異なる。
この行政の粗大ごみ受付センターのフローは次のようなものだ。
注目してほしいのは、ユーザー認証などはなく、メールアドレスを任意に入力できるってことだ。しかもこの時点で氏名や住所の入力は不要ってことだ。つまり「誰でも」「どの市区町村のセンター」にも、「どんなメールアドレス」でも送信できるってこと。
もし乗っ取った踏み台サーバーなどから、機械的にこのメールアドレス送信のPOST先にアクセスできたら、特定のメールアドレスに対して何万通も粗大ごみ回収のメールを送信できてしまうってことになる。粗大ごみどんだけ回収するねんッ!ってことになるけど、送られてきた側からするとたまったもんじゃない。
もちろんこの記事のようにロボットでブラウザを起動して操作すればなんでもできてしまうけど、これを行うにはサーバー上の制約が多いし、そんなに容易ではない(踏み台サーバーの権限などの制約を考えると)。なので普通にcURLなどのコマンドでPOSTできてしまうかどうかが問題となる。
結論からいうとcURLで連続送信可能だった。つまりガバシステムってこと。日本の自治体のシステムなのにどういうこった?念のためリクエストの詳細までは書かないことにするが、このシステムのセキュリティ対策を軽く紹介。
どうやらメールアドレス送信画面より前の画面でSessionIDが発行されてCookieにセットされるようだ。だが、ブラウザのインスペクターで楽勝で確認できる。このSessionIDがないと、メールアドレス送信画面でエラーになる。
メールアドレス送信画面のURLに謎のクエリパラメータ(te-uniquekey)が付いているが、見た瞬間何を表しているかすぐに分かった。
この16進数を10進数に変換してみると、完全にUNIXタイムスタンプのミリセカンドを表しているっぽい。これによって時間等を制御しているのかもしれないが、クエリパラメータなのでこちらからいくらでも作成して送信可能だ。てかタイムスタンプなのに、“uniquekey”(ユニークキー)っていう名前がバカっぽいよね。
そしてこれが重要なんだけど、メールアドレス送信画面のhiddenタグにトークンらしきものが見当たるんだ。
これは完全な推測なんだけど、SessionIDとシークレットキー(または上記のUNIXタイムスタンプ)の暗号値かハッシュ値だと思われる。なのでリロードしても画面遷移し直しても、このトークンの値は変わらないわけ。つまりこの値も抜き出して使用することが簡単にできてしまう。
これは対してこの記事に関係ないことなんだけど、このWEBシステム、海外のIPからもアクセスできるんだよね。行政は外国にまで粗大ごみを回収しにいってくれるわけもないので海外IP制限かけた方が良くないか?
ハワイ旅行中の日本人:「あ!家のラック古いから粗大ごみ出すか。。ポチポチ」
いや、日本帰ってからやれや。粗大ごみ券はハワイでは売ってないぞ。一概には言えないけど、セキュリティの観点から、この日本の自治体の粗大ごみサイトは国内IPのみ可の方が良い気がする。
ここまでの調査で十分コール可能なことがわかる。実際にごにょごにょしてリクエストを作成すると簡単にPOST成功した。そして実際に粗大ごみセンターからメールが届いた。ちなみに迷惑がかからないように10分程度の間隔は空けてテストしている。
このシステムの問題はこれだけでは終わらない。なんと!一度使用したトークンは何度でも利用できるの!しかも制限時間はほぼ存在しないと思われる。次の日になっても同一のリクエストが成功してしまうことを確認済みだ。いや、前述のタイムスタンプのクエリパラメータは何やってん。。
もし何らかの方法でリクエスト元を隠ぺいできる悪い人たちが、この粗大ごみセンターのPOST先に大量にリクエストを送信したら、特定のメールアドレスに何通もメールが飛んでしまう。例えばそれにより、対象のメールサーバーをパンパンにするといういたずらを行うこともできるかもしれない。
今回見た粗大ごみセンターのシステムはお国のシステムなのに、この程度なんだよね。で何が言いたいかというと、サーバーへのデータの送信に関する不正対策はやりすぎってくらいやった方がいいってこと。前述の通りCORSとかCSRF対策、XSS対策は当然のこと、以下の対策もやっておくと完璧だ。
この粗大ごみセンターのシステムなんて、私ごときでも数分ザーッとみただけで何となく不正対策を理解できるし、簡単に突破できることがわかってしまう。メール送信程度のことだから不正に操作されても問題ないと考えているのかもしれない。また非常に短い時間での連続でPOSTを制限しているかもしれない。が、せめてトークンはワンタイムにしてほしいところ。次の日になっても有効なトークンは問題だ。
特定のサイト、または特定のアプリなどのクライアント以外のところからのHTTPリクエストに対して、遮断またはエラーレスポンスできるのが理想だ。しかし、100%でこのような不正行為を防ぐことはできない。悪いハッカーたちは時間をかければ、どうにかしてセキュリティ対策とその突破方法をつきとめることができるだろうからね。ただ、何重にも施された対策があると、ハッカー側も突破するのにコストが見合わなくなりあきらめるってこと。特にSPAサイトに対応するWebAPI、とりわけ、ユーザー認証なしでコールできるようなAPIの不正アクセス対策はいろいろ考えた方がいいって話。
WEBサイトって一般的にブラウザがHTMLやCSS、Js、その他画像などのファイルを読み込んで描写されているものを言うよね?一方Webサイトを作成するには、Webサーバーが必要という。特に有名なCMSであるWordPressではサーバーでPHPやデータベースが動作してサイトが構築 …
今回からはWebAPIを作ってみようと思う。このサイトのコンセプトに沿って、作成するためのサンプルコードを上げるのではなく思考のプロセスを中心に書いていく。完全な初心者、または、なかなか上達出来ずに悩んでいるエンジニア向けの記事なのであしからず。 前回の記事でネットワークについて …