Upgrade to Pro
— share decks privately, control downloads, hide ads and more …
Speaker Deck
Features
Speaker Deck
PRO
Sign in
Sign up for free
Search
Search
クロスオリジンの話 / Cross-Origin-202201
Search
Sponsored
·
Ship Features Fearlessly
Turn features on and off without deploys. Used by thousands of Ruby developers.
→
unarist
January 28, 2022
Programming
220
0
Share
クロスオリジンの話 / Cross-Origin-202201
どこかでゆるゆる話したやつです。CORSとか同一オリジンポリシーとかその辺。
unarist
January 28, 2022
More Decks by unarist
See All by unarist
MODいろいろ / tokaidolug-nagoya-201812
unarist
0
92
Mastodonの話 / osc18-kyoto-closing
unarist
2
800
自分自身を再インストール / osc18-nagoya-tokaidolug
unarist
1
220
UserScriptを直した話 / tokaidolug-nagoya-201803
unarist
0
190
Other Decks in Programming
See All in Programming
L’IA au service des devs : Anatomie d'un assistant de Code Review
toham
0
250
第3木曜LT会 #28
tinykitten
PRO
0
100
AI-DLC Deep Dive
yuukiyo
8
3.7k
Xdebug と IDE による デバッグ実行の仕組みを見る / Exploring-How-Debugging-Works-with-Xdebug-and-an-IDE
shin1x1
0
380
KagglerがMixSeekを触ってみた
morim
0
380
SREに優しいTerraform構成 modulesとstateの組み方
hiyanger
1
120
Mastering Event Sourcing: Your Parents Holidayed in Yugoslavia
super_marek
0
150
Make GenAI Production-Ready with Kubernetes Patterns
bibryam
0
120
JOAI2026 1st solution - heron0519 -
heron0519
0
130
Kubernetes上でAgentを動かすための最新動向と押さえるべき概念まとめ
sotamaki0421
3
490
Cache-moi si tu peux : patterns et pièges du cache en production - Devoxx France 2026 - Conférence
slecache
0
220
AI時代のエンジニアリングの原則 / Engineering Principles in the AI Era
haru860
0
200
Featured
See All Featured
How to train your dragon (web standard)
notwaldorf
97
6.6k
Discover your Explorer Soul
emna__ayadi
2
1.1k
The B2B funnel & how to create a winning content strategy
katarinadahlin
PRO
1
330
Odyssey Design
rkendrick25
PRO
2
570
Fantastic passwords and where to find them - at NoRuKo
philnash
52
3.6k
Navigating Team Friction
lara
192
16k
Fashionably flexible responsive web design (full day workshop)
malarkey
408
66k
Code Review Best Practice
trishagee
74
20k
The Pragmatic Product Professional
lauravandoore
37
7.2k
Why Our Code Smells
bkeepers
PRO
340
58k
Building Adaptive Systems
keathley
44
3k
AI: The stuff that nobody shows you
jnunemaker
PRO
6
570
Transcript
クロスオリジンの話 unarist
微妙にふわっとしたタイトルやな…
今日話すこと • オリジンとかクロスオリジンとかなんやねん • 同一オリジンポリシーやCORSの話 • 発展的トピック 以下には重点を置いていません。 • Webアプリの脆弱性の網羅的な説明
→ 徳丸本を読みましょう • 最近流行りの攻撃 → OWASPとか徳丸チャンネルを見ましょう
今日覚えて帰ってほしいこと • ありません!!! • バスツアーぐらいの感じでお楽しみください。
Q. 以下の言葉知ってますか? • オリジン • クロスオリジン • 同一オリジンポリシー / Same-Origin
Policy • CORS / Cross-Origin Resource Sharing
None
Origin = scheme + hostname + port の組 例: http://example.com:8080/~username/index.html
リクエスト元・先のOriginが等しい → Same-Origin / 同一オリジン
リクエスト元・先のOriginが等しい → Same-Origin / 同一オリジン さまざまな操作を同一オリジン間に制限する仕組み → Same-Origin Policy /
同一オリジンポリシー
リクエスト元・先のOriginが異なる → Cross-Origin / クロスオリジン
リクエスト元・先のOriginが異なる → Cross-Origin / クロスオリジン 同一オリジンポリシーの制限を緩和する仕組み → CORS (Cross-Origin Resouce
Sharing), etc.
同一オリジンポリシーとCORS • Webの世界は昔からオリジン境界で色々守ってきた • オリジンを越えて許されていたことの例: ◦ リンクなどによるページ遷移 ◦ フォーム送信 ◦
リソース埋め込み(img/script/video/etc.) ▪ よくできているので、埋め込まれたimgをcanvasに描画してそれを持ち出す、とかもで きない(taint=汚染)される
Web園児猫「もうちょっと色々したいんじゃ…!」
同一オリジンポリシーとCORS • (多分)JS芸とかが広がってきて、ブラウザ内でインタラクティブにやるの が流行ってきた ◦ (Ajaxとか)(GoogleMapとか話題になったよね) • 同一オリジンはXMLHttpRequestさえあれば簡単 • クロスオリジンは……は……
◦ 古のハック、JSONP…… ◦ scriptタグで埋め込んでJSONを受け取れる。 var script = document.createElement(“script”); script.src = “http://example.com/api/jsonp?callback=hoge document.body.appendChild(script); function hoge(resp) { console.log(resp); }
CORS「待たせたな!!」
CORS (Cross-Origin Request Sharing) • これまで同一オリジンポリシーで制限されていたリクエストを、サーバー側 の明示的な許可のもと制限を緩和する仕組み • サーバー側の明示的な許可 =
Access-Control-ほげほげ HTTP/1.1 200 OK Content-Length: 0 Connection: keep-alive Access-Control-Allow-Origin: https://foo.bar.org Access-Control-Allow-Methods: POST, GET, OPTIONS, DELETE Access-Control-Allow-Credentials: true Access-Control-Expose-Headers: X-Foo, X-Bar Access-Control-Max-Age: 86400
CORS (Cross-Origin Request Sharing) 肝心なのは「同一オリジンポリシーを緩和するもの」ということ。 いままでできたことは変わらずできる ◦ リンクでの遷移、フォーム送信、リソース埋め込み: できる ◦
これらと同等のリクエスト: できる (単純リクエスト) できなかったことは許可されればできる ◦ 単純リクエストのレスポンスをJSで読み取る: 読み取り前にCORSでの許可が必要 ▪ リクエストはできるが、レスポンスにCORSヘッダがないと読み取れない ◦ メソッドやヘッダーを自由に設定したリクエスト: リクエスト前にCORSでの許可が必要 ▪ リクエスト前にプリフライトリクエストが飛ぶ
プリフライトリクエスト 許可がないとリクエストしていいかもわからない時に、先にお伺いを立てる。 OPTIONS /doc HTTP/1.1 Host: bar.other Connection: keep-alive Origin:
https://foo.example Access-Control-Request-Method: POST Access-Control-Request-Headers: X-PINGOTHER, Content-Type HTTP/1.1 204 No Content Access-Control-Allow-Origin: https://foo.example Access-Control-Allow-Methods: POST, GET, OPTIONS Access-Control-Allow-Headers: X-PINGOTHER, Content-Type Access-Control-Max-Age: 86400 Vary: Accept-Encoding, Origin 👦こういうリクエスト投げたいっす! 👨この条件ならええやで。
ところで Failed to fetch という 言葉に聞き覚えは?
忌しき Failed to fetch
忌しき Failed to fetch CORSで許可されていない場合、リクエスト結果はJSに対して開示できない ◦ 成功時のレスポンス、失敗時のレスポンス、リクエストに失敗した理由、etc. ◦ 全てをオブラートに包んだエラー「Failed to
fetch」 ◦ 開発者ツールでコンソールを確認するとかしないと、なんもわからん CORS設定しているはずなのに出るんだけど……🤔 ◦ 例えばエラーレスポンスにCORSヘッダがないと、やっぱり Failed to fetch 行き ◦ 忘れがちなケースとして、リバースプロキシやWAFが弾いているとか……
CORSとの付き合い方
レスポンスヘッダーにあれこれ詰める ◦ 最低限必要なのは Access-Control-Allow-Origin ◦ シンプルリクエストに該当しないメソッドやリクエストヘッダーを使う場合、 プリフライト リクエストに対応しつつ、Access-Control-Allow-Methods や Access-Control-Allow-Headers
も返す ◦ CookieやBASIC認証とかも送ってほしい場合は Access-Control-Allow-Credentials ▪ この場合 Access-Control-Allow-Origin 等でワイルドカードは使えない ◦ 追加でレスポンスヘッダを公開したい時は Access-Control-Expose-Headers リクエスト側はそんなにオプションいらない ◦ fetch() でいうと { mode: “cors” } というオプションがあるが、これがデフォルト ◦ 資格情報を送る場合は { credentials: “include” } 等が必要 CORSの設定
同一オリジンポリシーで防げないものは防げない 単純リクエストで副作用が起きるケース ◦ 「ぼくははまちちゃん! こんにちはこんにちは!!」 ◦ 📰https://www.itmedia.co.jp/enterprise/articles/0504/23/news005.html ◦ いわゆる CSRF/XSRF
(Cross-Site Request Forgeries) ▪ fetchでも { mode: "no-cors", credentials: "include" } とかでやれるぞ ◦ 対策: CSRFトークンをつける、単純リクエストにしない、後述の SameSite 属性、etc. ◦ もちろん、GETリクエストで副作用を起こしたりしてないですよね? 埋めこまれるのも困るケース ◦ 現実的な具体例が浮かばないが…… ◦ 対策としては Cross-Origin-Resource-Policy ヘッダとか……?
CORSで解決
なにこれ
ネットワーク通信以外のクロスオリジン ブラウザのタブ間・ウィンドウ間で通信できるもの ◦ postMessage API ▪ 送り手・受け手どちらもoriginをチェックしような! ◦ window.open /
window.parent / iframe.contentWindow / etc. ▪ windowオブジェクトが触れたり触れなかったりする ストレージ系 ◦ Cookie: サイト単位の管理 ▪ サブドメインがまとめられたり、オリジンとはまた違う単位… ◦ IndexedDB / WebStorage / etc.: オリジン単位の管理 ▪ 📰最近別オリジンのIndexedDBがチラ見えするバグがWebKitで話題でしたね? ▪ GoogleのユーザーIDとかが見えるので、特にプライバシー観点でまずい
ネットワーク通信以外のクロスオリジン この辺は既に緩めだったので、制限を厳しくするオプションが生えがち ◦ Cross-Origin-Opener-Policy / Cross-Origin-Embedder-Policy / iframe sandbox ◦
Spectre👻騒動で一部APIにこれらが必須になったりした 場合によってはデフォルト・強制で制限を厳しくされたりもしている ◦ Cookie: SameSite属性, 3rd-party Cookie の制限, ITP ◦ 📰SameSite=Lax はChromeやFirefoxがデフォルトにして話題になっている ▪ SameSite=None をつけないとCORSが設定されていてもCookieが送られなくなる ◦ Cookieに関してはプライバシー観点の話題が絶えないのもある
おまけ: CSP (Content-Security-Policy) クロスオリジンに限らず、Webページで扱うリソースに制限をかける仕組み ◦ 主に XSS (Cross-Site Scripting) の被害を低減したり報告するのに使われる
◦ img / script / style / (i)frame など、様々なリソースの出所を制限することができる ◦ つまり、XSS で変なリソースを読み込まされそうになっても、ブロックできる! ◦ ベタ書きされた style や script もブロックできる! ◦ (ブラウザにもよるが、UserScript / UserStyle もブロックされたりする) # 現在のオリジンからの取得とインライン指定のみ許可。他所やevalは禁止。 Content-Security-Policy: default-src self ‘unsafe-inline’ # https スキームのみを許可 Content-Security-Policy: default-src https:
おしまい