ウェブサイトからのローカルネットワークアクセスに制限をかける提案
引用元:https://news.ycombinator.com/item?id=44183799
ウェブサイトからローカルIPへのHTTPリクエストはヤバいと思うよ。企業アプリが壊れてもいい。企業は設定で戻せるし、普通の人は「ローカルデバイスを操作したいけど許可する?」みたいなポップアップで決められるようにすればいいんだよ。
これは誤解だよ。ローカルデバイスはCORSで結構前から守られてる。ただ、CORSはサーバーが「いいよ」って言わないとダメなんだ。今回の提案は、サーバーとウェブサイトがオッケーでも、ユーザーにも「いい?」って聞こうってこと。Facebookみたいに、ウェブサイトとローカルアプリが結託してヤバいことするかもしれないからね。
CORSって、ウェブページのJavaScriptが応答を見れるかだけ制限するんじゃないの?リクエスト自体は送られちゃうんでしょ?つまり、JavaScriptで脆弱なプリンターとかにヤバいリクエストを送って、コードを実行させちゃう攻撃ができるんじゃない?ウェブページは成功したかわからなくても、それは問題ないかもね。
いやいや、ブラウザは本物のリクエストの前にOPTIONSリクエストを送るんだよ。クライアントのブラウザがOPTIONSリクエストをURL以外で制御できるとは思えないけど、どうかな?タイミング攻撃でデバイスがあるかはわかるかもしれないけど、悪意のあるコードを送れるかはちょっと疑問だね。
「普通の人にポップアップで許可\拒否させればいい」って言うけどさ、MacOSってアプリごとに許可聞いてくるけど、みんな考えずに「はい」って押しちゃうんだよね。ウェブサイトごとになっても、そんなに変わらないんじゃないかな。
ポップアップ許可なんてセキュリティにならないって、まだそんなこと言ってる人がいるの?WindowsのUACを見ればわかるだろ。ユーザーは何も考えずに全部クリックするんだよ。それに、普通の人にはこの許可が何を意味するのか、どんな危険があるのか全然わからない。ウェブサイトが動かないから、言われた通りに盲目的に許可するだけだよ、毎回ね。
悪い奴は、OPTIONSがいらないGETとかPOSTの「シンプルリクエスト」で、デバイスを攻撃するコードを作ろうとするだろうね。でも、実際にそんな上手いこといく例はまだ見たことないんだ(論文で読んだけど、漠然とした話だった)。
このタグ
<img src=”http://192.168.1.1/router?reboot=1”>
を使えば、CORS関係なくローカルネットワークにGETリクエストを送れるんだよ。
ポップアップ許可は本当にダメだね。今のMacは「許可する?しない?」って聞きまくりで、さらに手動で設定開いてアプリ探したりしないといけない。どっちも結局ダメなんだよ。テクノロジーのこと全然わからない人が、色んな機能も使いつつ、ヤバい奴から完全に身を守るなんて、誰も方法を見つけられてない。全部の許可を禁止するような、ガチガチに固めたアカウントくらいしか無理なんじゃないかな。
Macって’許可/不許可’のポップアップだらけになったよね。
昔、AppleがMicrosoftのこれをバカにしてたCM知ってる?
これだよ → https://www.youtube.com/watch?v=DUPxkzV1RTc
これマジでやばいと思うんだけど。ウェブサイトがローカルネットワークにアクセスできるべきなの?
全然新しい脅威が出てくるじゃん、対策なんてないし。
これ、他に良い方法ないのに、どうしても必要なケースってあるの?
Windows Vistaはさ、デスクトップにショートカット作るみたいな全然たいしたことない時でも権限ポップアップ出したよね。
あの実装、Microsoftは本当にバカにされるべきだったよ。
ちょっと手間はかかるだろうけど、これがセキュリティのためなら仕方ないね。
俺らがアクセスしたウェブサイトが、localhost:8080で動かしてるセキュリティがゆるいテスト用ウェブサーバーにPingしたり攻撃したりできるなんて、マジででかいセキュリティリスクだよ。
’mode: ’no-cors’’を忘れてない?
あれを使うとレスポンスは見えなくなるけど、CORSの事前リクエストとかヘッダーチェックを全部すり抜けちゃうんだ。
それか、セキュリティが甘いルーターとかウェブカメラみたいな、ローカルネットワーク上の脆弱なHTTPサーバーを探し回ることもできる。
localhostだけじゃない、それはほんの一部だよ。
そうそう、POSTとかDELETEとかのフォームもトリガーできるんだ。
もしエンドポイントがリクエスト内のトークンを検証してなかったら、これはCSRFって呼ばれるやつだよ。
CORSは、権限のないXHRリクエストしか防げないんだ。
これ、全部何十年も前のOWASPの基本だね。
問題はね、これ許可しないとSynologyみたいなウェブUIが動かなくなることなんだ。
ああいうのってブラウザがローカルネットワークに接続する必要があるから…。
現状だと、あんまり良くないね。
’ローカルネットワーク’って定義できる?
多分無理だね。
大抵の大企業は社内用に公開ルーティング可能なIPアドレスを持ってるし、社内ネットワークが192.168.0.0/24とは限らない。
foo.corp.example.comが9.10.11.12に解決されてもローカルってことだってある。
IPv6は?
これ、コーナーケースだらけの無意味な議論だよ。
これも誤解だよ。
CORSはLayer 7の通信にしか適用されない。
それ以外のことは、タイミングを見れば色々わかる。
Websocketsみたいなブラウザの主要な機能には、こんな制限は全然ないんだ。
昔、ルームメイトのWindows 98にマルウェアが入ったことあるんだ。画像ファイルを全部VBScriptに書き換えるワームで、クリックや実行されるたびに増殖して感染を広げるやつ。VBS拡張子を隠して元の画像に見せかけてた。
Windowsでショートカットを作るのが必ずしも安全ってわけじゃないんだよ。ユーザーがソフトをインストールするのに慣れてたから、マルウェアを仕込む最初の手段としてよく使われたんだ。Windowsのショートカットって、変なパス名やコマンドライン引数、カスタムアイコンとか色々なものを隠せるし、いつでも変更できちゃうんだよね。
だから、UACが過剰だったとか邪魔だって言われたり、Microsoftがセキュリティ甘いって馬鹿にされたりしたけど、こういうやり口について注意喚起したのは間違ってなかったのかもね。
これ、大事な情報が抜けてるよ。preflightがスキップされるってのは正しいけど、このモードで動作する時はさらに制限があるんだ。サーバーの安全を保証するわけじゃないけど、“ safer”(より安全な)って言える動詞とヘッダーフィールドのサブセットで動かざるを得なくなるんだよ。
ブラウザはno-corsモードで送れるリクエストのヘッダーとメソッドを制限するんだ。(ヘッダーの場合はサイレント検閲、もっと具体的に言うとね)
GET、HEAD、POST以外のメソッドはブラウザでエラーになって送信されない。
CORS safelisted headers [0]以外のヘッダーは全部削除されるんだ。
それからContent-Typeはurlencoded、form-data、text-plainのどれかじゃないとダメ。それ以外を使おうとすると、ヘッダーがtext-plainに置き換えられるよ。
[0] https://developer.mozilla.org/en-US/docs/Glossary/CORS-safel…
お前のBitcoinノードにjson-rpcリクエストを送って、ウォレットを空にされちゃうかもしれないぜ。
昔は、フォーラムの署名に<img>
タグでhttp://someothersite.com/forum/ucp.php?mode=logout
とか埋め込んで、ウェブ上の皆のセッションをぶっ壊せたのを覚えてるよ。
ほとんどのユーザーが’はい’をクリックするっていう証拠、何かあるの?
私の親は非技術者だけど、何もかもデフォルトで’いいえ’ってクリックしてるよ。たまに何か動かないときに助けを求められるんだけど、多くの場合、アプリに必要な許可(例えばオーディオ通話アプリがマイクへのアクセスを拒否されたとか)を拒否してるからなんだ。
統計がないと、安易な仮定はできないと思うんだよね。
ユーザーが手動でショートカットを作るのは、権限プロンプトが必要なことじゃないだろ。
ユーザーにセキュリティプロンプトを無視することを教えたいなら、全く無意味な警告を出すのが一番だ。
HN(ソフトウェアやセキュリティへの関心が平均よりはるかに高い読者層)で高く評価されてるコメントが、こういうことを間違えるってことは、なぜこれらの問題がいつまでも解決しないのか、ちょっと説明がついちゃうな。
アプリからの権限プロンプトは、自分でそのアプリを意識的にダウンロードしたし、開発者やアプリが何をするか大体分かってるから受け入れやすいんだ。ソーシャルメディアアプリが写真への許可を求めても、音楽ストリーマーがスマートスピーカーに接続したいって言っても、その理由は簡単に理解できる。
でも、誰かがリンクしてきた見知らぬウェブサイトが、ローカルネットワークにアクセスしたいって?それは全然違うケースだね。ネットワークとか位置情報とかカメラとか、とにかくどんな種類のアクセスも、超極端な状況じゃない限りウェブサイトには絶対許可しないよ。
彼に完全に同意だ。お前の仕事のどこが難しくなろうが、プライバシーを不必要に侵害しないと動かないソフトが壊れようが、そんなの知ったこっちゃないね。インターネットが6ヶ月止まるって言われたって、俺は気にしないだろう。
ほとんどのユーザーを納得させるには、これが起こるべきではないという本当に強力な防御理由を考え出す必要があるだろうね。
ユーザーセッション中に実行されるプログラムは、しばしばそのユーザーとして動いているんだよ。
これに対する「正しい答え」は、おそらく良い答えなんてない、ってことだろうな。
セキュリティはマジで地雷原だ。しかも日々悪化してるし。
AppleとかMicrosoftとかGoogleとかさ、USBやBluetoothにもローカルネットワークみたいに制限つけてほしいな。
最近アプリ入れるとすぐBluetoothのスキャン許可求めてくるけど、全部見られたくないんだよ。
アプリ側が使いたい特定のデバイスID(短いリスト)を事前に宣言して、OSがそのデバイスだけ接続できるように制限してほしい。
例えばBoseアプリはBoseデバイスだけとかね。
OSがカメラやGPSみたいに「このアプリがデバイスABCに接続したいんだけど?」って聞いてくれるのがいいな。
そのデバイスIDは会社が登録したプレフィックスで識別する感じ。
これでアプリが勝手にネットワークとかUSB、Bluetoothをブラブラできなくなる。
もっとコメントを表示(1)
Appleがアプリに「偽の許可」を出す機能、いつか実現しないかなって密かに期待してるんだ。
「連絡先リストがないとダメ」っていうアプリには、ランダムな偽リストを渡すとかね。GPSも同じ。
WhatsAppは連絡先をFacebookに共有しないと、連絡先に名前をつけられないって聞いたことあるよ。
うん、俺もそうしてほしいよ。
俺の銀行アプリ、連絡先へのアクセスとか変な許可を求めてくるから使えないんだ。
なんで必要かわからないから拒否すると、アプリが動いてくれないんだよね。
iOSでは、アプリが連絡先の共有を強制するのは許されてないんだぜ。
もしそんな要求してくるアプリがあったら、それはApp Storeの規約違反だから報告した方がいいよ。
iOSではね、連絡先の一部だけ共有できる機能があるんだ。
これならWhatsAppでも、コメント3で話してたみたいにうまく使えると思うな。
>iOSでは連絡先の一部だけ共有できる
問題は、アプリがそれを尊重するかどうかだよ。
WhatsAppは色々言われるけど、ちゃんと尊重するんだ。
「プライバシー」重視って言われてるTelegramはダメだったね。
連絡先全部共有しないと動かなくて、一部だけ共有したら「全部共有しろ」って文句言いっぱなしだった。
それ、iOS版のTelegramだけじゃない?
Android版のTelegramは、連絡先へのアクセス拒否してもちゃんと動くし、アプリ内で完全に独立した連絡先リストを持てるんだ(PC版とか他の端末とも共有されるけど)。
スマホよりTelegram使い始めた方が古いんだけど、アプリ独自のリストがあって当然だと思ってる。
で、WhatsAppは連絡先へのアクセスなしじゃ使えないんだよね。
独自のWhatsApp専用連絡先は作らせてくれないし、許可しないと連絡先を保存するところがないって文句言う。
正直、俺はコミュニケーション手段ごとに連絡先リストが分かれてるのが好きで、電話アプリとGMailの連絡先が共有されるのだって嫌なんだ。
Telegramはその点いいんだけど、WhatsAppはダメだな。
俺はね、iOSのTelegramで連絡先もカメラもマイクも、一度もアクセス許可したことないけど、全然普通に使えてるけどな。
コメント7で言ってたTelegramの挙動、あれバグだったっぽいね。
連絡先アクセスを全部許可しないとアプリが完全に壊れてたけど、一部だけ許可したら(うっとうしい通知は出たけど)ちゃんと動いたよ。
Telegramが一部の連絡先しかアクセス許可されてないってどうやって知るの?
iOSはそんな情報アプリに漏らしちゃダメでしょ。
普通iOSはApp Storeの審査でこういうの対応するのに、Telegramがこれで通ったの驚きだよ。
「全連絡先アクセスしないと機能使えないようにしちゃダメ」みたいなルールないの?位置情報だとあるのにさ。
WhatsAppは電話番号必要だけど、共有する連絡先は選べても項目は選べない。
家族を共有すると電話番号だけじゃなく誕生日とか全部行っちゃうんだよ。
この機能って実装の仕方的に全然意味ないと思う。
あと、部分許可って分かってるからって、ずっとフル許可を求めてくるのもマジうざいんだよね。
カメラについても、ランダムなノイズとかユーザーが選んだ画像・動画をアプリにあげちゃえばいいじゃん。
GrapheneOSにはこの機能があるよ(GPS偽装は除くけど)。
GitHubのサードパーティ連携みたいに、「ABCはあなたのリポジトリ見たいんだけど、どれを共有したい?」って選ばせてくれるといいよね。
そのGitHubのUIって本当に自分で選べるの?
俺の経験だと、どの組織とリポジトリが共有されるか教えてくれるだけで、選ぶオプションはなかったんだけどな。
最近入れるアプリが全部Bluetoothアクセス求めてくるって?
それはAppleとかGoogleのひどいBLE APIのせいだよ。
RSSI(距離の代わりによく使われる、マジでダメなやつ)を取るには「全部許可!」ってしないといけないんだ。
みんな欲しいのは「時間差」なんだけど、なぜか全然サポートされてないんだよね。
Safariはこの(フィンガープリンティングの)理由でWeb MIDIをサポートしてないらしいんだけど、そのせいでどんなMIDIウェブアプリも使えなくなってて困るんだよね。
ウェブアプリ、モバイルアプリ、デスクトップアプリ、それともブラウザ拡張機能?
どれについて話してるの?
WebアプリはUSBとかBluetoothで許可が必要だと思うけど、WindowsやLinuxのデスクトップアプリは基本的に何でもできるよね。ファイル読んだり。パーミッションシステムで制限かけるのは大変な変更だろうな。
AppleはiOS 18でAccessorySetupKitっていうので、もうこれやってるらしいよ。
Webブラウザでローカルネットワークにアクセスし放題なのが信じられないよ。ファイルシステムへのアクセスはダメなのにね。セキュリティがサーバー任せなのが問題。開発マシンでテスト中の認証なしのWebアプリに、FacebookとかGoogleからアクセスされる可能性もあるし、ホームネットワークでCORSちゃんと設定してる人なんてほぼいないでしょ?
CS専攻してたのに、アクセスしたWebサイトがローカルネットワークにアクセスできるなんて全然知らなかったよ。マジか…。記事の提案以外に、このアクセスを制限する方法って何かあるのかな?
ブラウザ自体には、まだそういう機能はないんだよね。一番いいのは、OSの設定でブラウザ全体がローカルネットワークにアクセスできないようにしちゃうことかな。(ローカル用には別のブラウザを使うとか。)サンドボックス化の方法とか、ChatGPTに聞いてみるのもいいかもね。
ありがとう!VM向けにiptablesでローカルネットワークへのアクセスを拒否する設定は既にやってるんだ。今度はローカルアクセスにも同じ方法を使ってみようかな。
さらに驚きなのは、誰もこの問題を学ばないで、同じ構造的弱点を持つ新しいプロトコルが作られ続けてることだよね。MCP agentsのことなんだけど、もし知らなかったら調べてみて。
「みんなCORSちゃんと設定してるの?」って話だけど、たぶん0.1%より0%に近いと思うな。ほとんど誰もやってないんじゃない?
ローカルのサーバーが Access-Control-Allow-Origin: * を返さないと、この問題って起きないんじゃない?デフォルトでこれをやってる一般的なローカルWebサーバーとかサービスってあるの?心配じゃないわけじゃないけど、ちょっと気になった。
いやいや、簡単なリクエスト、例えばGETとかtext/plainのPOSTリクエストはCORSのプリフライトは起こさないんだよ。リクエストはそのまま飛んじゃって、必要なCORSレスポンスヘッダーがないとブラウザがJSコードにレスポンスを見せないだけ。でもその頃にはもうリクエストは送信済みなんだよね。だから、もし君のローカルサービスにhttp://localhost:8080/launch_rocketsみたいなGETエンドポイントがあったり、Content-Typeをちゃんと検証しないPOSTエンドポイントがあったりしたら、どんなウェブサイトからでもトリガーできちゃうんだよ。[1] https://developer.mozilla.org/en-US/docs/Web/HTTP/Guides/COR…
僕はレスポンスのデータ抜き出しのこと考えてたんだけど、まあ、確かにその/launch_rocketsエンドポイントは何か認証の裏に置いた方がいいね。
Internet Explorerがゾーンシステムでこれ解決してたよね?
https://learn.microsoft.com/en-us/previous-versions/troubles…
もっとコメントを表示(2)
皮肉にも、ChromeはWindows上でIEのセキュリティゾーンを部分的にサポートして利用してたんだよ、あんまりドキュメント化されてなかったけどね。
正直、今もそれに匹敵する機能があると思ってたんだ。それが無いなんてあり得ない。ローカルネットワークはカメラとかマイクみたいに特別な許可がいるべきだよね。
とはいえ、あれはたいていIntranet上のActiveXコントロールにローカルマシンへの自由なアクセスを与えるためにIT部門がグループポリシーで設定してたんだよね。楽しい日々だったよ。
これは多分、Metaがネイティブアプリとウェブサイト間でローカルホスト経由でコソコソ識別コードを共有するのを防ぐのに役立つだろうね、特にAndroidだと。
[0] https://www.theregister.com/2025/06/03/meta_pauses_android_t…
これはローカル接続をする必要のない多くのウェブサイトをブロックする役には立つけど、まだまだ大雑把だね。この許可が必要なほとんどのウェブサイトは、たった一つのローカルサーバーにアクセスできればいいんだ。全部に許可を与えちゃうのは最小権限の原則に違反する。ほとんどのユーザーは自分のローカルネットワークで何が動いてるか知らないから、リスクも理解できないだろうしね。
ユーザーはローカルネットワークのこと知らないから、リスクもわかんないんだよ。
ブラウザの許可メッセージも専門用語ばっかりだと「Yes」って押しちゃうだけ。
もっとわかりやすいメッセージがいいよね。
結局、攻撃者がうまく誘導すれば、どんなメッセージでもユーザーは「Yes」ってクリックしちゃうんだよね。
フィッシング詐欺みたいに、「大事な確認だから『Yes』を押して」って言われたら、意味わかんなくても押しちゃうでしょ。
結局、どこまで人を守れるかっていうと限界があるよ。
自己責任な部分も必要。
Google(多分ブラウザのこと)が全部決めちゃうような世界には住みたくないな。
理想を言えば、ブラウザがmDNSでローカルのサービスを見つけて、許可する時にその名前を表示できればいいんだけどね。
でも、現実にはmDNSのサービスなんてあんまり動いてないんだよね。
え、みんなmDNSとか切ってないの?
OS入れるたびに、よくわかんないからオフにしてたんだけど。
Avahiとかは違う話なのかな?
Avahiっていうのは、mDNSとかDNS-SDとかを扱うZeroconfっていうネットワーク技術のことだよ。
「ローカルネットワーク上のリソース」ってメッセージでも、ユーザーは結局意味わかんないで適当に「許可」しちゃうと思うな。
さっきのコメントと同じだけど。
スマホだったら、「このサイトから、このアプリに繋いでもいい?」みたいに聞くのがいいかも。
でも、ローカルネットワーク全体に対してやるのは難しいけどね。
完璧にやるならファイアウォールみたいなもんだよね。
どのネットワーク範囲とか、どのポートとかで制御する。
ブラウザ拡張機能でそういうの作れるAPIがあればいいな。
特定の機器とか、LAN全体とか、カテゴリ別に許可したり、localhostだけ許可したり。
ファイアウォールみたいなAPI、 Manifest V2にはあったんだけどね。
ChromeはManifest V3で削除しちゃったんだよ。
Firefoxにはまだあるよ。詳しくはここ見て→ https://developer.mozilla.org/en-US/docs/Mozilla/Add-ons/Web…
IPv6でサイトローカルかどうかって判定できるの?
難しいよね。
IoTアプリで困ったことあるんだけど、実際無理そう。
.localドメインもOSでバラバラだし、ローカルアドレスでHTTPS証明書使えないの、マジでイライラするんだよね。
HTTPSはドメイン名でIPは関係ないよ。
自分のドメインならローカルIPに向けられるしね。
NATのせいでRFC 1918=ローカルって勘違いしてる人多すぎ。
昔は公開IPでも自分にとってローカルだったんだ。
ルーター経由せず通信できればローカルなんだよ。
IPv6にもルーティング概念はあるよ。
リンクローカルはLAN用でAPIPAみたいなものね。
.localはDNSの話でIPとは関係ないよ。
Let’s EncryptとかでローカルIP向け証明書取るならDNS-01とかCNAME調べてみて。
ちょっと大変だけどね。
君、IPv4、IPv6、DNSとか、ちょっと分かってないみたいだから勉強しなよ。
IPv6でインバウンドが「ローカル」か判定?無理だよ。
IPv6はグローバルにルーティング可能が前提だから。
Googleの提案も完全にズレてる。
アプリは「ローカル限定」と思わず、公開前提でセキュリティ設計すべきだよ。
.localはmDNS用に予約されてるけど、みんな無視してるね。
Globally routableでも、間にファイアウォール置いてフィルタリングできるよ。
WANインターフェースとかで全部落とすこともできるしね。
SOHOルーターはNATとルーティングとファイアウォールをまとめてるけど、機能は別物だよ。
うちのSOHOルーターは、IPv4はNAT、IPv6はルーティング+ファイアウォールだけど、IPv6のファイアウォール設定は全くできないんだ。
できたとしても、家のIPv6アドレスは一時的で短命だから大変だろうね。
IPv6アドレスも永続的にできるんだ。
短命である必要はないよ。
MACアドレスでデバイスを識別して、アドレスが変わってもそれに紐付けてファイアウォールルールを設定できるホームファイアウォールもたくさんあるんだ。
IPv6アドレスってGUIDみたいで覚えにくいよね。
ランダムな文字列みたい。
IPv4は電話番号みたいでルールがなんとなく分かるんだけどね。
IPv6の設定とか分かりやすい入門書あるのかな?
あと、デバイスがアドレスを複数持つことが多いから管理が大変なんだ。