LRTKレフィクシア株式会社

点群OBJアップロード時のCORSエラーを解消する5設定

点群OBJアップロード時に起こるCORSエラーとは

点群OBJをWeb画面からアップロードしようとしたとき、ファイルの選択まではできるものの、送信を始めた直後に失敗したり、進捗表示が動かないまま処理が終了したりすることがあります。ブラウザの開発者向け画面に、異なるオリジンからの要求が許可されていないという趣旨のメッセージが表示されている場合は、CORS設定が原因になっている可能性があります。 CORSは、ブラウザ上で動作する画面が、異なるオリジンにあるサーバーへ通信するときの許可ルールです。オリジンは、通信方式、ホスト名、ポート番号の組み合わせによって判定されます。ホスト名が同じように見えても、通信方式やポート番号が異なれば、ブラウザからは別のオリジンとして扱われます。 たとえば、点群を管理する画面と、OBJファイルを保存する領域が異なるホスト名に分かれている場合、ブラウザは異なるオリジン間の通信として扱います。画面側がファイルを送信しようとしても、アップロード先から適切な許可情報が返されなければ、ブラウザは通信を止めるか、受信した応答を画面側の処理へ渡しません。 この制限は、利用者のデータを保護するためにブラウザが備えている仕組みです。そのため、ブラウザの設定を変更して強引に回避するのではなく、通信を受けるサーバー側で、許可する送信元、通信方法、ヘッダー、認証情報を正しく設定する必要があります。 点群OBJのアップロードでは、通常の文字情報を送る処理よりもCORS設定が複雑になりやすい傾向があります。OBJは容量が大きくなる場合があり、ファイル本体を別の保存領域へ直接送信したり、分割して送信したりすることがあるためです。さらに、OBJから参照されるMTLやテクスチャ画像を別のURLから取得する構成では、アップロード時だけでなく表示時の通信にもCORS設定が関係します。 実務システムでは、最初に認証済みのAPIへ問い合わせて一時的なアップロード先を取得し、そのURLへOBJ本体を送信し、送信完了後に別のAPIへ登録結果を通知する構成もあります。この場合、ひとつのアップロード操作に見えても、内部では複数の通信が行われています。どれか一つの経路だけCORS設定が不足していても、利用者にはアップロード全体が失敗したように見えます。 CORSエラーを解消するには、エラー文だけを見て設定を追加するのではなく、画面からどのURLへ、どのメソッドで、どのヘッダーを付けて送信しているかを整理することが重要です。そのうえで、許可するOrigin、OPTIONSへの応答、許可ヘッダー、認証情報、関連ファイルの配信設定という五つの観点から確認します。

CORSエラーと別のアップロード障害を切り分ける

点群OBJのアップロードが止まったとしても、原因が必ずCORSであるとは限りません。ファイル容量の上限、通信時間の超過、認証期限切れ、保存領域の不足、OBJ内の不正な記述、関連ファイルの欠落などでも、画面上では似た失敗として表示される場合があります。 最初に確認したいのは、ブラウザが本来のアップロード要求を送信しているかどうかです。アップロード前にOPTIONSというメソッドの通信が行われ、その通信が失敗している場合は、プリフライトと呼ばれる事前確認で止まっている可能性があります。この場合、OBJ本体のPOSTやPUTはまだ送信されていません。 一方、OBJ本体のPOSTやPUTが送信され、サーバーから状態コードが返っている場合は、CORS以外の問題も考えられます。ファイル容量が上限を超えた場合、認証情報が無効な場合、サーバー内部の処理に失敗した場合などです。ただし、こうしたエラー応答にCORS用のヘッダーが付いていないと、ブラウザは本来のエラー内容を画面側へ渡せず、結果としてCORSエラーのように表示することがあります。 したがって、CORSの調査では、成功時の応答だけでなく失敗時の応答も確認する必要があります。正常に保存できたときは許可ヘッダーが付いていても、容量超過や認証失敗を返す経路だけヘッダーが欠けていることがあります。アプリケーション本体ではなく、その手前の中継層がエラーを返している場合にも同じ現象が起こります。 ブラウザ以外の通信手段から同じアップロード先へ送信すると成功するのに、Web画面からだけ失敗する場合は、CORSを疑う材料になります。ブラウザ以外の通信手段には、通常、同一オリジンポリシーが適用されないためです。ただし、送信先URL、認証情報、Content-Type、ファイルの送り方が異なれば結果も変わるため、単純な成功と失敗だけで断定してはいけません。 アップロードの通信経路を確認するときは、画面を表示しているOrigin、アップロード先のURL、使用しているメソッド、送信ヘッダー、Cookieの有無、応答の状態コードを記録します。点群OBJを分割送信している場合は、開始要求、各分割データの送信、完了要求がそれぞれ異なるURLになっていないかも確認します。 また、OBJの送信自体は完了しているのに、アップロード後のプレビューだけ表示されないこともあります。この場合は、OBJ、MTL、テクスチャ画像、変換後データの読み込みに対するCORS設定が不足している可能性があります。アップロード処理と表示処理を分けて確認することで、修正すべき場所を絞り込めます。

設定1:許可するOriginを正確に指定する

一つ目の設定は、アップロードを許可する画面側のOriginです。ブラウザから送信された要求には、送信元を示すOriginヘッダーが含まれます。サーバーはその値を確認し、許可対象であれば、応答のAccess-Control-Allow-Originに許可するOriginを設定します。 ここで指定するのは、画面のページ全体のURLではありません。通信方式、ホスト名、必要に応じてポート番号までを含むOriginです。画面のパスやファイル名、問い合わせ文字列は含めません。設定値に余分なパスを加えると、正しい画面から送信していても一致せず、ブラウザに拒否されます。 開発環境では、同じ端末上で画面とAPIを別のポート番号で起動することがあります。ホスト名が同じでもポート番号が異なれば別のOriginになるため、開発用のOriginを明示的に許可する必要があります。また、文字列のホスト名と数値で表したループバックアドレスも、ブラウザ上では同一のOriginとは見なされません。 本番環境では、許可対象を明示的な一覧で管理する方法が適しています。本番画面、検証画面、社内確認画面などがある場合は、それぞれのOriginを環境ごとに登録します。受信したOriginが一覧に完全一致した場合だけ、その値を応答へ返す設計にすると、意図しない外部サイトからの通信を許可しにくくなります。 ドメイン名の一部だけを見て許可する実装には注意が必要です。たとえば、特定の文字列を含んでいれば許可する、特定の文字で終わっていれば許可するといった簡易判定では、似た名称の別ドメインが条件を満たす可能性があります。許可対象は正規化したうえで完全一致させることが基本です。 すべての送信元を表すワイルドカードは、公開情報の取得などでは利用される場合があります。しかし、点群OBJのアップロードはデータの作成や更新を伴い、認証済みの利用者だけが操作することも多いため、許可Originを限定する方が安全です。 特に、Cookieなどの認証情報を含む通信では、Access-Control-Allow-Originにワイルドカードを指定できません。認証情報を許可する設定とワイルドカードを同時に使うと、ブラウザが応答を拒否します。Cookieを使用する場合は、受信したOriginを許可一覧と照合し、許可された具体的なOriginを一つだけ返します。 複数のOriginを許可するときに、Access-Control-Allow-Originへ複数の値を並べてはいけません。応答に設定するのは、その要求を送信した一つのOriginです。サーバー内部で許可一覧を持ち、要求ごとに一致した値を返します。 Originによって応答内容が変わる場合は、キャッシュにもその違いを伝える必要があります。中継層や配信層が、あるOrigin向けの応答を別のOriginにも再利用すると、許可値が一致しなくなります。そのため、Originに応じて許可値を変える構成では、Vary: Originを応答へ付けることが重要です。 設定後は、本番用Origin、検証用Origin、許可していないOriginのそれぞれから確認します。許可対象では正常にアップロードでき、対象外では拒否されることまで検証すれば、単にエラーを消すだけでなく、意図した許可範囲を維持できます。

設定2:OPTIONSとアップロード用メソッドを許可する

二つ目の設定は、OPTIONSによるプリフライトと、実際のアップロードで使用するメソッドの許可です。ブラウザは、一定の条件に該当する異なるオリジン間通信を行う前に、OPTIONSメソッドで事前確認を送ります。 プリフライトでは、ブラウザが送信予定のメソッドとヘッダーをサーバーへ伝えます。サーバーがその条件を許可する応答を返した場合に限り、ブラウザはOBJ本体の送信を開始します。したがって、OPTIONSが失敗している状態では、アップロード処理の内部ロジックをいくら修正しても、OBJ本体はサーバーへ届きません。 サーバーは、Access-Control-Allow-Methodsに実際に使用するメソッドを含めます。フォーム形式でアップロードする場合はPOST、ファイル本体を直接送る場合はPUTが使われることがあります。分割アップロードの開始や完了に別のメソッドを使用する場合は、それぞれ必要なメソッドだけを許可します。 使用しないメソッドまで広く許可する必要はありません。点群の登録にPOSTとPUTだけを使うなら、不要な更新方法や削除方法を含めず、通信仕様に沿った最小限の許可にします。CORSで許可したからといって、サーバー側の認証や権限確認を省略してよいわけではありません。実際の本送信では、利用者が対象案件へデータを登録できるかを必ず検証します。 OPTIONSへの応答を、通常の認証処理より前に返す必要がある場合もあります。プリフライトには本送信と同じ認証情報が含まれないことがあるため、OPTIONS自体に通常のログイン認証を要求すると、事前確認で拒否される可能性があります。 ただし、OPTIONSを無条件に成功させればよいわけではありません。送信元Origin、要求予定のメソッド、要求予定のヘッダーを確認し、許可方針に合う場合だけ適切な応答を返します。本体のPOSTやPUTでは、通常どおり認証、権限、ファイル容量、形式などを検証します。 中継サーバーがOPTIONSを処理できない場合、アプリケーションまで要求が届きません。中継層から未対応を示す状態コードが返ったり、別URLへの転送が行われたりすることがあります。アプリケーション側にCORS設定を入れたのに改善しない場合は、OPTIONSがどの層で処理されているかを確認します。 URLの末尾に付くスラッシュの有無や、安全な通信方式への転送も影響します。通常の画面表示では問題にならない転送でも、プリフライトでは意図どおり処理されないことがあります。画面側から最終的なアップロードURLへ直接送信し、OPTIONSの途中で転送が発生しない構成が安定します。 分割アップロードでは、同じ条件のOPTIONSが何度も送られる場合があります。Access-Control-Max-Ageを設定すると、ブラウザがプリフライトの結果を一定時間保持でき、確認回数を減らせます。ただし、保持時間を長くすると、設定変更後も古い許可結果が残ることがあります。障害調査中は短めにし、設定が安定してから運用に適した値へ調整します。 設定後は、通信一覧でOPTIONSが正常に完了し、その直後にPOSTやPUTが送られていることを確認します。OPTIONSだけ成功して本送信が行われない場合は、許可ヘッダーや画面側の処理も併せて調べる必要があります。

設定3:送信ヘッダーとContent-Typeを一致させる

三つ目の設定は、画面が送信するヘッダーと、サーバーが許可するヘッダーを一致させることです。プリフライトでは、ブラウザがAccess-Control-Request-Headersによって、実際の送信で使用する予定のヘッダーを通知します。サーバーは許可するヘッダーをAccess-Control-Allow-Headersで返します。 点群OBJのアップロードでは、Content-TypeやAuthorizationのほか、分割番号、整合性確認用の値、案件識別子、アップロード識別子などの独自ヘッダーを使用する場合があります。ブラウザが送信しようとしているヘッダーのうち、一つでも許可応答に含まれていないと、本送信が始まらないことがあります。 画面側の更新で新しいヘッダーを追加した直後にCORSエラーが発生した場合は、サーバー側の許可一覧が更新されていない可能性があります。画面とサーバーを別々に更新する運用では、通信仕様の変更を双方の担当者が共有する必要があります。 Content-Typeの扱いも重要です。フォーム形式でファイルを送信する場合、ブラウザは複数の項目を区切る境界情報を含めてContent-Typeを設定します。画面側で境界情報を含まない値を固定すると、サーバーがファイル部分を正しく解析できなくなる可能性があります。フォーム形式では、特別な理由がない限りブラウザへ設定を任せる方が安全です。 OBJ本体をそのままPUTする構成では、ファイルの内容を示す形式や、汎用的なバイナリ形式を指定することがあります。アップロード先URLを事前に発行する構成では、URL発行時に想定したContent-Typeと、実際のPUTで送信する値が一致しないと、署名や条件の検証で拒否される場合があります。 このとき、プリフライト自体は成功しているのに、本送信が403などで失敗することがあります。さらに、そのエラー応答にCORSヘッダーが付いていなければ、画面にはCORSエラーとして表示されます。CORS設定とアップロード先の検証条件を分けて確認する必要があります。 認証用のAuthorizationヘッダーを使う場合は、Access-Control-Allow-Headersにも明示的に含めます。一時的なアップロードURLへファイルを直接送る場合は、APIへの認証とファイル送信時の認証方式が異なることがあります。不要な認証ヘッダーを付けるとプリフライト条件が増えるため、通信ごとに必要なヘッダーだけを送る設計にします。 ファイル名、座標系、測点名、撮影日時などの情報をすべて独自ヘッダーで送ると、通信仕様が複雑になります。業務上必要なメタデータは、フォーム本文へ含める方法や、アップロード完了後の登録APIで送る方法もあります。独自ヘッダーを減らすことだけが目的ではありませんが、送信仕様が単純なほどCORS設定の不一致は起こりにくくなります。 ヘッダー名は通常、大文字と小文字を区別せず扱われます。しかし、中継処理や独自の設定判定で表記揺れが影響することもあります。ブラウザがプリフライトで要求したヘッダー名と、実際の応答に含まれる許可ヘッダーを、開発者ツール上で直接比較することが確実です。 許可ヘッダーを無制限に広げる設定は、原因調査の一時的な切り分けには使えても、本番運用では慎重に扱う必要があります。使用しているヘッダーを把握し、必要なものだけを許可することで、通信仕様の変更にも気づきやすくなります。

設定4:Cookieや認証情報の扱いを統一する

四つ目の設定は、Cookie、セッション情報、認証ヘッダーなどの扱いを、画面側とサーバー側で統一することです。認証情報付きの異なるオリジン間通信は、設定の組み合わせが多く、開発環境では成功するのに本番環境では失敗する原因になりやすい部分です。 Cookieを使用する場合は、画面側の通信処理で認証情報を含める指定が必要です。指定がなければ、ブラウザは異なるオリジンへの要求にCookieを付けない場合があります。サーバー側では、Access-Control-Allow-Credentialsによって認証情報を含む通信を許可します。 認証情報を許可する場合、Access-Control-Allow-Originにワイルドカードは使用できません。許可一覧と照合した具体的なOriginを返す必要があります。画面側だけ認証情報を含める設定にしても、サーバーの応答が対応していなければ、ブラウザは応答を画面処理へ渡しません。 異なるサイト間でCookieを利用するときは、CORS以外のCookie属性も影響します。安全な通信方式で送信されているか、異なるサイト間での送信を認める属性が付いているか、対象ドメインとパスが適切かを確認します。CORS設定が正しくてもCookieが送信されなければ、サーバーは未認証として処理します。 未認証を示す応答にCORSヘッダーが付いていない場合、画面からは本来の認証エラーを読み取れません。その結果、利用者にはCORSエラーとして見える可能性があります。401や403などの認証・権限エラーにも、許可対象Origin向けのCORSヘッダーを付けることが重要です。 認証ヘッダーを利用する場合は、プリフライトでAuthorizationを許可する必要があります。認証情報の有効期限が切れたときは、画面側が状態コードや応答内容を読み取り、再認証へ誘導できるようにします。エラー応答をブラウザが読めなければ、利用者には原因の分からないアップロード失敗として表示されます。 一時的なアップロードURLを使う構成では、ファイル本体の送信にCookieや通常の認証ヘッダーを付けない場合があります。最初のAPIで利用者を認証し、許可されたファイルだけを送れる一時URLを発行する仕組みです。この場合、画面側がファイル送信にもCookieや認証ヘッダーを付けると、保管領域側のCORS設定と一致しないことがあります。 どの通信でどの認証情報を使用するかを明確にすることが大切です。アップロード先を取得するAPIには認証ヘッダーを付け、ファイル本体の直接送信には発行済みURLだけを使い、完了通知には再び認証ヘッダーを付ける、といったように経路ごとの仕様を整理します。 CORSはアクセス権限を判定する仕組みそのものではありません。許可されたOriginからの通信であっても、利用者が対象案件へ点群OBJを登録できるか、他者の保存先識別子を指定していないか、ファイル容量や形式が条件内かをサーバー側で確認する必要があります。 Originはブラウザからの読み取りを制御する材料であり、業務上の権限管理を置き換えるものではありません。CORS設定を広げることでエラーを解消するのではなく、認証と権限確認を維持したまま、必要な通信だけを通す設計にします。

設定5:応答ヘッダーと関連ファイルの配信設定をそろえる

五つ目の設定は、アップロード後の応答ヘッダーと、OBJに関連するファイルの配信設定をそろえることです。ファイル本体の送信が完了していても、画面が完了情報を取得できなければ、アップロード失敗として扱われる場合があります。 アップロード後に、保存されたデータの識別子、整合性確認値、追跡用の要求番号、保存位置などを応答ヘッダーで返す構成があります。ブラウザ上の処理から参照したい応答ヘッダーが標準で公開される範囲に含まれない場合は、Access-Control-Expose-Headersで公開対象を指定します。 サーバーの応答には値が入っていても、公開設定がなければ画面側のプログラムから取得できないことがあります。通信一覧では成功しているのに、画面上で「完了情報を取得できませんでした」といった扱いになる場合は、応答ヘッダーの公開範囲を確認します。 成功時だけCORSヘッダーを付ける実装も避けます。認証失敗、容量超過、形式不正、保存領域の不足、内部処理の例外など、どの状態コードでも共通のCORS処理を通すことが重要です。失敗応答にも許可ヘッダーがあれば、画面側は本来の原因を読み取り、利用者へ適切な案内を表示できます。 中継層が独自にエラーを返す場合もあります。たとえば、OBJの容量が中継層の上限を超えた場合、アプリケーションまで要求が届かず、中継層がエラー応答を返します。その応答にCORSヘッダーがなければ、ブラウザではCORSエラーに見える可能性があります。アプリケーションだけでなく、通信経路全体でエラー時のヘッダーを確認します。 Originごとに異なる許可値を返す場合は、キャッシュ設定も重要です。あるOrigin向けのAccess-Control-Allow-Originが付いた応答を中継層が保存し、別のOriginからの要求へ再利用すると、ブラウザが不一致として拒否します。Vary: Originを設定し、Originによって応答が変わることをキャッシュへ伝えます。 点群OBJの表示では、OBJ本体だけでなく、MTLやテクスチャ画像を読み込む場合があります。また、アップロード後にサーバーで軽量化や変換を行い、別形式の表示用データやサムネイルを生成することもあります。これらが画面と異なるオリジンから配信されるなら、それぞれに読み取り用のCORS設定が必要です。 アップロードAPIの設定だけを修正し、ファイル配信元の設定を見落とすと、送信は成功しても表示段階でエラーになります。利用者には「アップロードしたファイルが開けない」「テクスチャが表示されない」と見えるため、アップロード経路と閲覧経路を分けて確認します。 一時的な閲覧URLを発行する場合は、URLの有効期限にも注意します。期限切れの応答にCORSヘッダーがなければ、画面側は期限切れと判断できません。許可されたOriginに対しては、期限切れを示すエラー応答にもCORSヘッダーを付け、画面側でURLの再発行処理へ進めるようにします。

点群OBJ特有の複数ファイル構成を確認する

OBJは一つのファイルだけで扱える場合もありますが、外観情報をMTLへ分け、さらにMTLからテクスチャ画像を参照する構成があります。点群の頂点情報だけを格納したOBJと、面やテクスチャを含むOBJでは、アップロード後に必要となる関連ファイルが異なります。 OBJ内には、使用するMTLのファイル名が記述されることがあります。MTLには、材質情報やテクスチャ画像へのパスが書かれます。OBJだけをアップロードし、MTLや画像を送らなければ、形状は表示できても色や外観が再現されない場合があります。 反対に、関連ファイルは保存されているものの、配信先のCORS設定が不足している場合もあります。OBJ本体は読み込めても、MTLの取得が止まったり、テクスチャ画像の読み込みだけが拒否されたりします。画面上では全体が白く表示される、色が欠ける、読込中のまま進まないといった症状になります。 複数ファイルを圧縮して一括送信する構成では、ブラウザからのアップロード通信は一回で済む場合があります。しかし、サーバーで展開した後は、OBJ、MTL、画像が個別のURLで配信されます。表示画面が各ファイルを取得するため、展開後の配信経路にもCORS設定が必要です。 OBJとMTLの参照は、ファイル名や相対パスに依存します。アップロード後に保存名を変更したり、フォルダ階層を組み替えたりすると、参照切れが起こります。これはCORSとは別の問題ですが、ブラウザ上では関連ファイルの取得失敗として似た症状になることがあります。 ファイル名に空白、全角文字、記号などが含まれていると、URLへの変換方法や文字コードの違いによって取得に失敗する場合があります。アップロード前に命名規則を定め、OBJとMTL内の参照名も一致させることが重要です。 大文字と小文字の扱いにも注意します。利用者の端末上では区別されずに開けても、保存先では区別される場合があります。OBJに記述されたMTL名や、MTLに記述された画像名と、実際のファイル名が完全に一致しているかを確認します。 CORS調査では、ブラウザの通信一覧から、失敗しているURLがOBJ本体なのか、MTLなのか、テクスチャなのかを見分けます。関連ファイルのうち一つだけ異なる配信先になっていることもあるため、拡張子だけでなく完全なURLを確認します。

中継サーバーや保存領域で設定が変わっていないか確認する

Web画面とアップロード処理の間には、複数の中継層が存在することがあります。外部からの通信を受ける中継サーバー、負荷を分散する層、認証を処理する層、ファイルを保存する領域、閲覧用データを配信する層などです。 アプリケーション側でCORSヘッダーを付けていても、中継層が削除したり、別の値へ上書きしたりすると、ブラウザでは正しく認識されません。設定を変更したのに応答へ反映されない場合は、最終的にブラウザへ届いたヘッダーを基準に調査します。 よくある問題の一つが、同じCORSヘッダーの重複です。アプリケーションと中継サーバーの双方でAccess-Control-Allow-Originを追加すると、同じ名前のヘッダーが複数返されることがあります。異なる値や不正な形式で返された場合、ブラウザは応答を拒否します。 CORSをどの層で担当するかを決め、原則として一か所で一貫して生成することが重要です。中継層で統一する場合は、アプリケーション側の重複設定を避けます。アプリケーション側で制御する場合は、中継層がヘッダーを保持したまま転送するようにします。 OPTIONSだけを中継層が処理し、本送信はアプリケーションへ渡す構成もあります。この場合、プリフライトと本送信で許可Originや許可ヘッダーが一致していなければなりません。片方だけ設定を更新すると、OPTIONSは成功しても本送信の応答が拒否されることがあります。 点群OBJは容量が大きくなりやすいため、中継層の最大本文サイズにも注意が必要です。上限を超えると、アプリケーションに届く前に拒否されます。中継層が返す容量超過エラーにCORSヘッダーがなければ、ブラウザにはCORSの問題として表示される可能性があります。 送信時間が長い場合は、接続や転送の待ち時間設定にも影響します。アップロードの途中で中継層が接続を終了すると、画面には通信失敗として表示されます。CORSの修正だけでなく、最大容量、待ち時間、一時保存領域、分割送信の条件も併せて確認します。 開発環境ではアプリケーションへ直接接続している一方、本番環境では複数の中継層を通ることがあります。この違いにより、開発環境では正常でも本番環境だけ失敗する場合があります。環境ごとの通信経路を整理し、最終応答を比較することが重要です。

開発者ツールでCORSエラーを調査する手順

CORSエラーを調査するときは、ブラウザの開発者ツールにある通信確認画面を使用します。画面を開いた状態で既存の履歴を消し、点群OBJのアップロード操作を再現すると、対象の通信を見つけやすくなります。 最初に、アップロード先のURLへOPTIONSが送られているかを確認します。OPTIONSがある場合は、要求に含まれるOrigin、要求予定のメソッド、要求予定のヘッダーを確認します。これらがサーバー側の許可設定と一致している必要があります。 次に、OPTIONSへの応答を確認します。状態コードが正常か、Access-Control-Allow-Originが要求元と一致しているか、Access-Control-Allow-Methodsに本送信のメソッドが含まれているか、Access-Control-Allow-Headersに要求されたヘッダーが含まれているかを見ます。 Cookieなどを使う場合は、Access-Control-Allow-Credentialsも確認します。認証情報を許可しているのにOriginがワイルドカードになっていないか、画面側が認証情報を含める設定になっているかも調べます。 OPTIONSが失敗している場合、本送信のPOSTやPUTは通常送られません。通信一覧に本送信が存在しないなら、まずプリフライトを修正します。OPTIONSが成功しているのに本送信がない場合は、画面側の処理で例外が起きていないか、応答内容を正しく処理できているかも確認します。 本送信が行われている場合は、その状態コードと応答を調べます。認証エラー、容量超過、署名条件の不一致、サーバー内部エラーなどが返っていないかを確認します。応答にCORSヘッダーがなければ、画面側では本来のエラー内容を読み取れません。 アップロード本体が成功している場合は、その後に行われる完了通知やプレビュー用データの取得も確認します。ファイルの送信が成功した直後に別の要求が失敗している場合、画面全体ではアップロード失敗として表示されることがあります。 調査時には、要求URLを省略せず記録します。同じホスト名に見えても、通信方式、ポート番号、サブドメイン、末尾スラッシュ、問い合わせ文字列が異なる場合があります。一時URLを使う構成では、失敗した時点の完全なURLと要求番号を保存しておくと、サーバーログと照合しやすくなります。 サーバーログでは、OPTIONSが到達したか、本送信が到達したか、どのOriginから送られたか、どの条件で拒否されたかを確認します。機密情報や認証情報をそのまま記録しないよう配慮しつつ、画面とサーバーで共通の要求番号を持たせると調査が容易になります。 ブラウザのキャッシュが古いプリフライト結果を保持している可能性もあります。設定変更後の検証では、通信キャッシュを無効にする、別の検証用URLを使う、保持時間が経過してから再確認するといった方法を使います。利用者へ常にキャッシュ削除を求めるのではなく、運用開始後は適切な保持時間とVary設定で管理します。

大容量の点群OBJで起こりやすい関連エラー

点群OBJは、頂点数、面数、テクスチャ解像度、関連画像の枚数によって容量が大きくなります。CORSを正しく設定しても、容量や時間に関する制限でアップロードが失敗することがあります。 代表的なのは、アップロード先や中継層の容量上限です。ファイル選択時には問題がなくても、本体送信の途中や送信直後に拒否されます。このエラー応答にCORSヘッダーがなければ、画面にはCORSエラーのように見えることがあります。 待ち時間の上限も確認が必要です。低速な通信回線から大容量OBJを送ると、サーバー側が想定した時間内に送信が終わらない場合があります。接続待ち時間だけでなく、データ受信、保存処理、完了応答の待ち時間を経路ごとに確認します。 一時アップロードURLには有効期限が設定される場合があります。URLを発行してからファイル選択や確認に時間がかかると、送信中または送信開始時に期限切れになることがあります。大容量ファイルを扱う場合は、想定送信時間を考慮して期限を設定し、期限切れ時にはURLを再発行できるようにします。 分割アップロードは、大容量ファイルの安定送信に有効です。ただし、開始要求、各分割データ、完了確定で異なるメソッドやヘッダーを使うと、CORS設定も複数必要になります。分割番号や整合性確認値を独自ヘッダーに入れる場合は、そのヘッダーを許可一覧へ追加します。 再送処理にも注意します。通信が切れたときに最初から送り直すのか、完了していない分割だけ再送するのかを決めます。同じOBJが二重登録されないよう、アップロード識別子や完了状態をサーバー側で管理します。 OBJ自体の構文エラーも、アップロード後の処理失敗につながります。送信は成功していても、サーバー側の解析や変換で失敗し、その応答がCORS設定されていなければ、画面には原因が伝わりません。アップロード完了と解析完了を別の状態として管理し、どの段階で失敗したかを表示できる構成が望まれます。 ファイル名や関連パスの問題も、CORSと混同されやすい障害です。OBJ、MTL、テクスチャを一括で検査し、参照先が存在するか、ファイル名が一致するか、安全な文字で構成されているかをアップロード前後に確認します。

CORSエラーを再発させない運用方法

CORS設定を一度修正しても、画面の移行、ホスト名の変更、認証方式の更新、保存領域の変更などによって再発することがあります。再発防止には、現在の設定値だけでなく、アップロード通信の仕様を継続的に管理することが重要です。 まず、点群OBJのアップロードに関係する通信経路を整理します。画面のOrigin、アップロード先を取得するAPI、ファイル本体の送信先、完了通知先、閲覧時のOBJ配信先、MTLやテクスチャの配信先を明確にします。 それぞれの経路について、メソッド、送信ヘッダー、認証方法、必要なCORS応答、最大容量、待ち時間を記録します。開発、検証、本番で設定が異なる場合は、環境ごとの差を明示します。 画面側で新しいヘッダーを追加する変更や、送信方法をPOSTからPUTへ変更する更新は、サーバー側のCORS設定にも影響します。画面とサーバーの更新を別々に行う場合でも、通信仕様の変更を同じ変更管理の対象にします。 実際のブラウザを使ったアップロード試験も必要です。小さなOBJだけでなく、運用で想定する容量に近いファイル、MTL付きのデータ、テクスチャ付きのデータ、分割送信するデータなどを確認します。 正常系だけでなく、認証期限切れ、容量超過、不正なファイル形式、関連ファイルの欠落、保存処理の失敗も試験します。エラー時に本来の状態やメッセージを画面側が取得できれば、失敗応答にもCORSヘッダーが適用されていることを確認できます。 監視では、アップロード全体の失敗数だけでなく、OPTIONSの失敗、本送信の認証エラー、容量超過、サーバー内部エラー、完了通知の失敗を分けて集計します。プリフライトで止まった場合は本送信がサーバーへ届かないため、アプリケーションログだけでは把握できないことがあります。 中継層のアクセスログや、画面側で取得したエラー情報を組み合わせると、CORSとそれ以外の障害を切り分けやすくなります。ただし、認証情報や一時URLの機密部分をログへ残さないよう、記録範囲を設計します。 許可Originの一覧も定期的に見直します。終了した検証環境や使用していない開発用Originが残っていれば削除します。新しい画面を追加する場合は、必要性を確認したうえで明示的に登録します。 CORS設定を広くしてエラーを避けるのではなく、必要な通信条件を正確に保つことが安定運用につながります。アップロード経路を単純化し、どの層がCORSを担当するかを明確にすることで、設定の重複や環境差も減らせます。

まとめ

点群OBJアップロード時のCORSエラーを解消するには、Access-Control-Allow-Originを一つ追加するだけでは不十分な場合があります。画面とアップロード先がどのような経路で通信しているかを整理し、五つの設定を順番に確認することが重要です。 一つ目は、許可するOriginを通信方式、ホスト名、ポート番号まで正確に指定することです。認証情報を含む通信ではワイルドカードを使わず、許可一覧と完全一致した具体的なOriginを返します。 二つ目は、OPTIONSによるプリフライトと、本送信で使うPOSTやPUTなどのメソッドを許可することです。OPTIONSが中継層で拒否されていないか、別URLへ転送されていないかも確認します。 三つ目は、ブラウザが送信するヘッダーと、サーバーが許可するヘッダーを一致させることです。Content-Type、Authorization、分割送信用の独自ヘッダーなどを確認し、不要なヘッダーを増やさないようにします。 四つ目は、Cookieや認証ヘッダーの扱いを画面側とサーバー側で統一することです。認証情報を許可する場合は、具体的なOriginとAccess-Control-Allow-Credentialsを組み合わせます。 五つ目は、成功時と失敗時の応答ヘッダー、OBJから参照されるMTLやテクスチャの配信設定までそろえることです。ファイル送信だけ成功しても、完了情報や関連ファイルを取得できなければ、実務上のアップロード処理は完了しません。 調査時は、ブラウザの開発者ツールでOPTIONSと本送信を分けて確認します。本送信が行われていなければプリフライトを、本送信が失敗していれば状態コードとエラー応答を、送信後に表示できなければ関連ファイルの取得を調べます。 ブラウザの保護機能を無効にしたり、すべてのOriginやメソッドを無条件に許可したりする方法は、本番環境の解決策にはなりません。必要な送信元、メソッド、ヘッダーだけを許可し、認証と業務上の権限確認を別途維持することが安全な修正方針です。 現場で取得した点群をOBJとしてアップロードし、共有や確認まで一連の流れで扱う場合は、通信設定だけでなく、ファイル名、関連ファイル、容量上限、再送方法まで標準化する必要があります。LRTK Phoneを活用して点群データを取得する運用でも、アップロード先のCORS設定とデータ管理手順を整えておくことで、現場から確認工程までをより安定してつなげられます。

現場を3Dで残して、あとから測る。
実際の画面と動画で使い方を確認できます。

LRTK Phoneの使い方・実例を見る
資料請求導入相談
現場をスマホで3DスキャンLRTK Phone実例を見る