SOPとは?初心者にもわかる同一オリジンポリシーの基本解説

Web開発

はじめに

皆さんはWebサイトを作る際に、セキュリティ面で不安を感じることはないでしょうか?

特に初めてプログラミングを学ぶ方にとっては、何が安全対策になっているのか、どのようにブラウザが保護してくれるのか、分からないことが多いかもしれません。

ここでは SOP (Same Origin Policy) というルールについて解説します。

Webブラウザが標準で実装している安全対策のひとつで、JavaScriptを学び始めた段階でもよく耳にするものです。

もしこの仕組みを知らないと、APIを使ったデータ取得や別のドメインからの情報取得の際に、思わぬエラーに直面するかもしれません。

そんなトラブルを避けるためにも、まずはSOPの基本を理解すると安心ですね。

それでは、実務でも役立つ具体例に触れながら、SOPの仕組みやメリットを紹介していきます。

SOPとは何か

SOPは Same Origin Policy の略称です。

日本語では「同一オリジンポリシー」と呼ばれ、ブラウザがWebページを開くときに適用されるセキュリティルールを指します。

簡単に言うと、あるWebページに読み込まれたスクリプト(JavaScriptなど)が、意図しない別のドメインやプロトコル、ポートにアクセスできないようにする仕組みです。

「オリジン(origin)」という言葉には、「プロトコル(httpsなど)」「ドメイン名(example.comなど)」「ポート番号(通常は80や443など)」の3要素が含まれています。

この3つがすべて同じ場合を「同一オリジン」と呼びます。

SOPはこの条件を満たさない(つまり、少しでも違う要素がある)他のオリジンから情報を自由に取得したり、操作したりできないように制限します。

こう聞くと少し息苦しく感じる方もいるかもしれません。

しかし、このルールがあることで、悪意のあるサイトから個人情報が勝手に読み取られるような事態を防ぐことができます。

Web全体の安全性を確保するうえで不可欠な考え方だと言えるでしょう。

なぜSOPが重要なのか

一方で、SOPがないとどうなるかを考えてみると、あちこちのサイトから勝手に情報を抜き取るスクリプトが動く可能性があります。

たとえば銀行のサイトにログインした状態で、別の不審なサイトを開いたとします。

もしSOPが存在しなければ、その不審サイトから銀行のサイトにアクセスし、利用者の口座情報を盗み取るコードを実行できてしまうかもしれません。

こうした攻撃を防ぐためのブラウザの基本ルールがSOPです。

少し抽象的に聞こえるかもしれませんが、実務ではとても重要です。

ネットショッピングやSNS、オンラインバンキングなど、あらゆるサービスがこの仕組みに守られていると言えます。

実際の活用例と仕組み

SOPが適用される具体的な状況をイメージしてみましょう。

ここではJavaScriptを使ったデータ取得の例を挙げます。

// 仮のサンプルとして、他のドメインにリクエストを送る状況を想定
fetch("https://api.example.com/data")
  .then((response) => response.json())
  .then((data) => {
    console.log("取得したデータ:", data);
  })
  .catch((error) => {
    console.error("エラー:", error);
  });

同一オリジンであるページから同じドメインにあるエンドポイントに対して fetch を行う場合は、SOPの制限にひっかかることはありません。

しかし、もしこのコードをホストしているドメインが mydomain.com だとすると、 api.example.com は別オリジンです。

その場合、 CORS (Cross-Origin Resource Sharing) と呼ばれる仕組みを使わないと、ブラウザは「セキュリティ上の理由により実行をブロックしました」というメッセージを返します。

このようにSOPは、別ドメインに対するリクエストやレスポンスの受信を基本的に遮断します。

ただし、サーバー側が適切な設定を行い、CORSヘッダーを返すようにすれば、開発者が意図的に許可した範囲の通信は通るようになります。

CORSとの違い

SOPとセットで語られることが多いのが、今お話しした CORS です。

CORSは Cross-Origin Resource Sharing の略で、SOPが「同一オリジンのみOK」という安全策を基本としているのに対し、「特定の別オリジンからのアクセスを許可する」仕組みを提供します。

CORSを使うときは、サーバー側でアクセスを許可する設定を入れます。

たとえばレスポンスヘッダーに Access-Control-Allow-Origin: https://mydomain.com のような情報を追加すると、指定したオリジンだけは通信を許可できるようになります。

もし別のオリジンがアクセスしてきた場合は許可されないので、不特定多数のサイトから勝手にアクセスされるのを防げます。

SOPとCORSは、どちらもWeb開発における安全管理のための仕組みだと捉えると理解しやすいでしょう。

SOPが「原則ブロック」で、CORSが「必要に応じた解放」というイメージですね。

セッションやクッキーとSOP

Webブラウザを使うとき、クッキーやセッション情報を使ってログイン状態を維持している方は多いでしょう。

SOPはこうしたクッキーにも大きく関わっています。

同一オリジン上で発行されたクッキーは、基本的に同じオリジンのWebページからのみ読み取れます。

もし別オリジンから自由にクッキーが読み取れるとしたら、ログイン状態の乗っ取りにつながってしまう可能性があるからです。

ここでもSOPがセキュリティを保つ上で役立っていることが分かりますね。

一方で、クッキーの設定によっては例外的に別ドメインで使用できる場合もあります。

しかし、そうした設定をするときはより慎重に行う必要があります。

実務でどのように活かされるか

SOPの存在を知っていると、以下のような場面で迷わなくなります。

  • 他社のAPIを利用するときにCORSエラーが起こった場合、なぜブロックされるのかを理解できる
  • フロントエンドとバックエンドを別々のドメインで運用する際、サーバー側でCORSの設定が必要だと分かる
  • 自作のWebサービスを公開したあと、ユーザーのブラウザでエラーが起こったときに原因を早く特定できる

これらはどれも実務につながるポイントです。

SOPを知らずにいると、「なぜリクエストがブロックされるのか分からない」「どうしてクッキーが渡らないんだろう」といった悩みに直面します。

しかし、SOPやCORSをあらかじめ理解していれば、原因の切り分けがスムーズになるでしょう。

よくある疑問と誤解

別のサブドメインでもブロックされるのか

「同じプロトコル、同じドメインだけど、サブドメインが違う」というケースは一見同じオリジンに感じるかもしれませんが、 サブドメインも別オリジン とみなされるのが基本です。

例えば、 example.comapi.example.com は同一オリジンではありません。

SOPによってブロックされるため、CORSの設定がないとアクセスが制限される可能性があります。

ポート番号が違うだけでもブロック対象なのか

SOPでチェックされる項目に「ポート番号」も含まれます。

そのため、 https://example.com:3000https://example.com:443 はオリジンが異なると判断されます。

HTTPとHTTPSは別のオリジンなのか

プロトコルが異なるため、 http://example.comhttps://example.com は別のオリジンとなります。

httpsのサイト内では、セキュリティ上の理由から特に厳しく扱われるため、混在コンテンツ(httpsページ内にhttpの要素が混ざる状態)も避けるようにしたいですね。

実際のコード例:CORSエラーが起きるケース

ここでは簡単な例として、同一サーバーではなく別のサーバーにデータを送ろうとしてブロックされる状況を見てみましょう。

このコードは擬似的に書かれたものなので、実際の環境に合わせて読み替えてください。

// フロントエンドのJSコードが動くオリジン: https://frontend.mydomain.com
// データを送信しようとするAPIのオリジン: https://api.someotherdomain.com

fetch("https://api.someotherdomain.com/submit", {
  method: "POST",
  headers: {
    "Content-Type": "application/json"
  },
  body: JSON.stringify({ message: "テストデータ" })
})
  .then((res) => res.json())
  .then((result) => {
    console.log("サーバーの応答:", result);
  })
  .catch((error) => {
    console.error("CORSエラーが発生しました:", error);
  });

このように別オリジンへリクエストを送ると、ブラウザのコンソールには「CORSによりブロックしました」というようなエラーが表示されることがあります。

サーバーが Access-Control-Allow-Origin: https://frontend.mydomain.com などのCORS設定をしていれば問題なく動作する場合もありますが、その設定がないとSOPによりブロックされるというわけです。

ブロックが発生したときの対処方法

SOPによるブロックが発生したら、「サーバー側のCORS設定が正しいか」をまず確認する と良いでしょう。

もし許可されていないオリジンからのアクセスであれば、サーバー側に明示的な許可設定が必要です。

ただしセキュリティを軽視するのは危険です。

むやみに「Access-Control-Allow-Origin: *」のようにワイルドカードで全オリジンを許可すると、意図しない悪意あるサイトからもアクセスされる恐れがあります。

そのため、基本的には「どのオリジンをどのメソッド(POSTやGETなど)で許可するか」を厳密に設定する必要があります。

注意点

SOPはブラウザレベルで強制されるセキュリティルールです。

サーバー側でどうこうできるものではなく、あくまでブラウザが勝手に(つまり自動的に)ブロックする仕組みだと考えてください。

このため、クライアントサイドで「なんとかしてSOPを回避しよう」というアプローチは基本的にNGです。

もし回避できるとしたら、それは安全性が失われることとほぼ同義になるからです。

また、ローカル環境でのテスト中に特殊な開発ツールを使うケースもあるかもしれませんが、それはあくまで一時的な方法に留めましょう。

本番運用で利用者のブラウザがSOPを無効化するようなケースはありませんので、正攻法でCORS設定を整えるしかありません。

フロントエンド開発との関係

最近のWebアプリ開発では、フロントエンドとバックエンドを分けて作るケースが増えてきました。

バックエンドはAPIを提供し、フロントエンドはReactやVue.jsなどのフレームワークで実装するイメージですね。

こうした構成だと、フロントエンドのドメインとバックエンドのドメインが異なる場合も珍しくありません。

そのような場合、SOPの制限でCORSの設定を意識する必要があります。

APIを構築するときにフロントエンドのオリジンをホワイトリストに登録する方法を採用したり、開発環境だけはオリジンを広く許可する設定を入れたりといった運用が一般的です。

最初は戸惑うかもしれませんが、「SOPによって基本はブロックされる、それをCORSで必要最小限だけ許可する」という流れが分かっていると、スムーズに対応できるでしょう。

セキュリティが高まるメリット

SOPは、ユーザーのデータやアプリケーションを守るうえで重要な役割を担っています。

SOPによってブラウザが自動的にブロックしてくれるので、悪意のあるスクリプトが別オリジンから機密情報を盗み取るリスクが大幅に下がります。

皆さんが普段使っている銀行やSNSも、SOPに守られていると思うと少し安心感がありますよね。

ただし、SOPに守られているからといって、すべてが安全というわけではありません。

サーバーの設定ミスや、ユーザー自身のブラウザ環境、さらにはフィッシング詐欺など、さまざまな角度での攻撃が存在します。

SOPはあくまで大事な1つの防御策です。

他のセキュリティ対策と組み合わせることで、より安全なWebサービスを構築していくことができます。

まとめ

ここまでSOP(同一オリジンポリシー)について見てきました。

これからプログラミングを学ぶ皆さんにとって、SOPという言葉は最初は聞き慣れないかもしれませんが、Web開発を進めるうえで必ず直面する概念です。

特にAPI連携を行うフロントエンド開発では「突然通信がブロックされる」という現象に出会う可能性が高いでしょう。

しかし、それはブラウザが皆さんを守るために行っていることでもあります。

SOPを理解するメリットは、エラーや不具合に直面したときにすぐに原因を推測できるようになることです。

「どこでブロックされているのか」「どのように許可すればいいのか」を把握していれば、開発のスピードも上がります。

さらにSOPの根本にある「安全第一」の考え方は、どんな開発手法を選ぶときにも役立ちます。

皆さんがこれからWebアプリを作る際に、SOPのおかげで安心してインターネットを活用できるよう祈っています。

今後の学習に向けて

SOPを知ったら、合わせて CORSCookieのセキュリティ などを深掘りするのもおすすめです。

これらはどれもWebセキュリティの基礎に該当し、初心者のうちから理解を進めておくと実務でのトラブルシューティングが楽になるでしょう。

複雑に感じる部分もあるかもしれませんが、開発していくうちに必ず必要になる知識です。

少しずつでも手を動かしながら試してみて、Webブラウザがどのようにセキュリティを維持しているのか、体感的に理解を深めていくと良いですね。

JavaScriptをマスターしよう

この記事で学んだJavaScriptの知識をさらに伸ばしませんか?
Udemyには、現場ですぐ使えるスキルを身につけられる実践的な講座が揃っています。