Azure Logic Apps Standard の実行履歴で、トリガーやアクションの Inputs/Outputs が読み込めず「CORS ポリシーにより読み込みできません」と表示されることがあります。本記事では、この現象がなぜ起こるのかを整理し、企業環境で現実的に使える対処パターンを詳しく解説します。
Logic Apps Standard の実行履歴で I/O が表示されない問題とは
まずは今回の典型的なシナリオを整理します。
- Logic Apps Standard(HTTP トリガー)で社内バックエンド API を呼び出している
- インターネット経由の呼び出しは API Management(APIM)経由のみ許可 したい
- そのため Logic App に Access Restriction(受信アクセス制限) を設定し、APIM の送信元 IP のみ Allow にしている
- 以後、Azure ポータルの「実行履歴」でトリガー/アクションの Inputs / Outputs が読み込めない
- 画面には次のようなメッセージが出る
CORS ポリシーにより読み込みできません。https://portal.azure.com を CORS 許可に追加してください。
指示どおり CORS 設定に https://portal.azure.com を追加しても改善せず、Access Restriction を一時的に外すと表示できる──という挙動になります。
多くの方がここで「CORS が原因なのでは?」と考えて CORS 設定を調整しがちですが、実際の原因は Access Restriction(ネットワークレベルのアクセス制御) にあります。
構成イメージ
| 要素 | 内容 |
|---|---|
| Logic App の種類 | Logic Apps Standard(App Service プランベース) |
| トリガー | HTTP トリガー(APIM から呼び出し) |
| ネットワーク | VNet 統合済み、受信 Access Restriction を設定 |
| 許可している送信元 | APIM(および一部のシステム IP)のみ Allow |
| 問題の現象 | Azure ポータルの実行履歴で Inputs / Outputs が読み込めない |
根本原因:CORS ではなく Access Restriction でブロックされている
ポイントは次の 2 点です。
- 実行履歴の I/O は、ポータル(ブラウザ)から Logic App へ「直接」取りに行く
- Access Restriction は CORS より先に評価される
この 2 つが組み合わさると、「CORS エラーのように見えるが、実はネットワークでハネられている」状態になります。
実行履歴のデータ取得フロー
実行履歴の一覧自体はポータルから管理 API 経由で取られますが、各アクションの Inputs / Outputs の詳細 はそうではありません。
画面の「アクションをクリック → Inputs / Outputs タブを開く」という操作を行うと、ブラウザは次のような流れで通信します。
- ユーザーのブラウザから Logic Apps Standard のランタイム(App Service)に対して HTTPS リクエストが飛ぶ
- そのレスポンスとして、該当実行インスタンスの入出力 JSON が返ってくる
- ポータル画面の JavaScript がその JSON を整形し、ブラウザ上に表示する
つまり、実行履歴の I/O 表示は「ポータル → あなたのブラウザ → Logic App ランタイム」の 直接通信 に依存しています。APIM は経由しません。
Access Restriction と CORS の評価順序
ここで重要なのが、Access Restriction(ネットワーク ACL)と CORS の評価タイミング です。
| 評価ステージ | 主な役割 | 今回のケースでの挙動 |
|---|---|---|
| 1. Access Restriction(NW レベル) | 送信元 IP / VNet などでアクセスを許可 or 拒否 | ブラウザの送信元 IP が Allow に含まれていないため ここでブロック |
| 2. アプリ層(アプリコード) | リクエスト内容に応じた処理を実行 | Access Restriction で遮断されるため到達しない |
| 3. CORS | オリジン(https://portal.azure.com など)の許可 / 不許可判定 | そもそも HTTP レイヤーまで届かないため 評価されない |
このように、Access Restriction で遮断された後では CORS の設定が一切効かない ため、「CORS をいくらいじっても状況が変わらない」という状態になります。
ブラウザ側では結果的に「CORS に失敗したように見える」ため、エラーメッセージも CORS ベースで表示されますが、実体としては ネットワークで落ちている 点が落とし穴です。
誰の IP を許可すべきか
実行履歴の I/O を見たいのは「実際にポータルを開いているユーザー」です。したがって、Access Restriction で Allow すべき送信元は次のとおりです。
- APIM の送信元 IP(ワークフローを呼び出すため)
- ポータルを開いている担当者の送信元 IP(実行履歴の I/O を閲覧するため)
後者を許可していないと、実行履歴の I/O だけが見えなくなります。
正しい対処:閲覧者の送信元 IP を Access Restriction で Allow する
結論として、ポータルを開いている人(閲覧者)の送信元 IP を Logic App Standard のアクセス制限に Allow として追加する ことで解決します。
新 UI(Inbound traffic configuration)の例
Azure ポータルで Logic App Standard を開き、左メニューから 「ネットワーク」 を選びます。
- Inbound traffic configuration を開く
- 「Enabled with access restrictions」 を選択
- App access を 「Selected virtual networks and IP addresses」 にする
- Site access and rules の Main site に以下を追加
- Type: IP Address
- Address: 自分(または社内)の送信元グローバル IP /32
- Action: Allow
- Priority: 100 ~ 200 など、既存の Deny よりも小さい値
- Name:
allow-ops-ipなど分かりやすい名前
- 必要に応じて Advanced tools(scm) にも同様の Allow ルールを追加
- 保存 をクリック
設定反映には数十秒~数分程度かかることがあります。少し待ってからブラウザをリロードし、再度実行履歴の Inputs / Outputs を開いてみてください。
旧 UI(Access restrictions)を使う場合
古い UI の場合も考え方は同じです。
- Logic App Standard の 「ネットワーク」 → 「Access restrictions」 を開く
- Add rule から閲覧者のグローバル IP を Allow で追加
- APIM などの既存 Allow より優先されるように Priority を適切な値 に変更
- 必要なら scm(Advanced tools)側 にも同様のルールを追加
自分の送信元 IP を確認する方法
自分の送信元 IP は、一般的には次のいずれかで把握できます。
- 社内ネットワーク・VPN の設計資料(NAT / Egress IP 一覧)
- ネットワーク担当に確認する
- ブラウザの開発者ツールで実際にリクエストを投げてみて、FW ログから送信元 IP を調べる
特に Zscaler・プロキシ・VPN などを挟んでいる場合、ユーザーごとの IP が変動することもあるため、「代表 IP(NAT プール)」をまとめて許可する運用が現実的です。
うまくいかない場合のトラブルシュート
Access Restriction に IP を追加しても直らない場合、次の点を確認してください。
| チェック項目 | 確認ポイント |
|---|---|
| Priority の順序 | 追加した Allow ルールよりも上に、より小さい Priority の Deny が無いか |
| IP アドレスの誤り | /32 を付け忘れていないか、IPv4 / IPv6 を取り違えていないか |
| scm サイト | 一部の画面は scm サイトに依存するため、そちらにも Allow が必要な場合あり |
| ブラウザキャッシュ | シークレットウィンドウや別ブラウザで再度試してみる |
なぜ APIM だけを許可してもダメなのか
多くの構成では、HTTP トリガーのエンドポイントは APIM → Logic Apps Standard の経路でのみ呼び出されるように設計されています。そのため、「APIM の IP だけ Allow にしておけば安全」と考えがちです。
しかし、人間がポータルから実行履歴を閲覧する通信は APIM を経由しません。これが今回のポイントです。
| 通信の種類 | 送信元 | 経路 | Access Restriction の許可が必要な送信元 |
|---|---|---|---|
| HTTP トリガー呼び出し | APIM | APIM → Logic App | APIM の送信元 IP |
| 実行履歴の I/O 表示 | 閲覧者のブラウザ | ブラウザ → Logic App | 閲覧者の送信元 IP(または社内の代表 IP) |
APIM の IP だけを Allow していると、後者(閲覧者 → Logic App)の通信がすべて拒否されてしまい、結果として I/O が読み込めなくなります。
複数メンバーがいる企業環境での現実的な運用パターン
「運用メンバーごとに個別 IP を登録する」のは現場ではほぼ破綻します。そこで、現実的に運用しやすい代表的なパターンを整理します。
パターン 1:固定の社内送信元 IP(NAT / Egress)を許可する
最もシンプルで現実的な方法が、社内・拠点・VPN の固定グローバル IP をまとめて Allow に登録するパターンです。
- 社内インターネットゲートウェイのグローバル IP を 1 つまたは少数に集約している
- VPN クライアントの出口 IP が固定もしくは範囲で決まっている
このような環境であれば、次のようなルールを追加するだけで運用メンバー全員が実行履歴を閲覧できます。
203.0.113.0/29(社内インターネットゲートウェイ)198.51.100.0/28(VPN クライアントの出口 IP プール)
メリット・デメリットは以下のとおりです。
| 観点 | 内容 |
|---|---|
| メリット | メンバー追加のたびに IP 登録が不要 IP 変更があってもネットワーク側で吸収しやすい 運用負荷が最も低い |
| デメリット | その IP からのすべての端末が閲覧可能になるため、端末側の管理(端末認証・EDR など)が前提 「誰がアクセスしたか」の特定は Azure AD / 監査ログで行う必要がある |
パターン 2:プライベート エンドポイント+VPN/ExpressRoute
よりセキュアな構成として、Logic App(App Service)にプライベート エンドポイントを張り、社内からは VPN/ExpressRoute 経由でのみ到達させるパターンがあります。
構成イメージは次のとおりです。
- ハブ VNet に VPN/ExpressRoute ゲートウェイを配置
- スポーク VNet に Logic App Standard(プラン)を配置
- Logic App に対して プライベート エンドポイント を作成
- 社内 DNS(または Azure Private DNS)で Logic App の FQDN をプライベート IP に解決
- NSG / UDR で必要な経路のみ許可
この場合、運用メンバーが VPN に接続していれば、実行履歴の I/O 表示もプライベート経路を通って行われるため、インターネット側の IP 許可を気にせずに済みます。
ただし、以下の点には注意が必要です。
- ネットワーク設計・DNS 設計のコストが上がる
- 他の App Service / Function / Web App との整合性(同一ドメイン名)を考慮する必要がある
パターン 3:運用ウィンドウだけ一時的に IP を許可
セキュリティポリシーが厳格な環境では、「運用作業時だけ一時的に Access Restriction を緩める」という選択肢もあります。
- 障害対応やリリース作業など、運用ウィンドウを事前に決める
- その時間帯だけ、運用担当の VPN プール IP を Allow に追加
- 作業完了後に再度ルールを閉じる
この場合、運用手順書に Access Restriction の変更手順と戻し忘れ防止のチェックを必ず含めるようにしましょう。
パターン 4:診断ログを使って I/O を追跡する
「実行履歴の画面で I/O が見られないと困る」というケースでも、必ずしもポータル画面だけに頼る必要はありません。
- Logic Apps Standard の 診断設定 から、Log Analytics / Event Hub / Storage などにランタイムログを送信
- Log Analytics 上でクエリを組み、実行状況・入出力を可視化
- 開発環境では I/O をフルログ、本番では「機密入出力の保護」を有効化してマスクするなど、環境ごとにログの粒度を変える
これにより、Access Restriction を厳しく維持したまま監査・トラブルシュートを実現できます。ただし、「機密入出力の保護」を有効にしていると本文はマスクされる点に注意が必要です。
よくあるつまずきポイントと対処のコツ
APIM の IP だけ許可してしまう
もっとも多いのが、APIM の IP だけ Allow にして満足してしまうパターンです。
- APIM を経由しない操作(ポータルからの実行履歴閲覧など)はすべてブロックされる
- 結果として CORS エラーのように見えるため、原因の切り分けに時間がかかる
Access Restriction で Allow している送信元に、「人間が使う回線」も含まれているかを必ず確認しましょう。
IPv6 / プロキシ / Zscaler で送信元 IP が変わる
昨今の企業ネットワークでは、以下のような構成により「ユーザーごとの送信元 IP が頻繁に変わる」ことがあります。
- IPv6 ネイティブ+IPv4 NAT64 / プロキシ
- Zscaler やクラウド型プロキシサービス
- クラウド型セキュリティゲートウェイ(SWG)経由のインターネットアクセス
このような場合、個々の IP を Allow に追加するのではなく、サービスプロバイダが公開している IP レンジをまとめて許可する、あるいは VPN 経由の固定出口を用意するなど、ネットワーク設計側で安定した出口 IP を提供してもらうのが現実的です。
Main site だけ許可して scm 側を忘れる
Logic Apps Standard(App Service)は、Main site と scm(Advanced tools)サイトを持っています。
- 画面機能の中には scm 側に依存するものもある
- Main site だけ Allow にしても、一部の操作でエラーになることがある
ネットワーク画面で 「Main site」「Advanced tools」両方に必要な Allow ルールが入っているかを確認しましょう。
Deny ルールの Priority が高すぎる
Access Restriction の評価は Priority の小さいものから順に評価されます。よくあるミスとして、
Deny allを Priority 100 で設定- その後に Allow ルールを Priority 300 などで追加
というケースがあり、これでは Deny all が先にヒットしてしまいます。
Allow ルールは Deny ルールよりも小さい Priority を指定することを徹底しましょう。
チェックリスト:実行履歴の I/O が見えない時に確認すべきこと
最後に、実際にトラブルが起きたときに確認すべきポイントをチェックリストとしてまとめます。
| 項目 | 質問 | Yes の場合 |
|---|---|---|
| 1. ポータル以外では問題ないか | APIM 経由の実行やバックエンド呼び出しは成功しているか? | Yes ならネットワーク制限は APIM には問題なく、ポータル閲覧経路だけが怪しい |
| 2. 自分の IP を Allow 済みか | 自分の送信元 IP(または社内の固定 IP)は Access Restriction に含まれているか? | No ならまずは追加して再テスト |
| 3. Priority の順序 | Allow よりも上に広い Deny ルールが存在しないか? | Yes なら Priority の見直しが必要 |
| 4. VNet / プライベート エンドポイント | プライベート経路でのみアクセスできる構成になっていないか? | Yes なら DNS / ルーティングが正しく構成されているかを確認 |
| 5. 診断ログ | App Service のアクセスログに該当リクエストの 403 などが記録されているか? | Yes ならネットワークレベルの拒否である可能性が高い |
セキュリティと運用性のバランスを取るための考え方
Logic Apps Standard+APIM+VNet+Access Restriction という構成は、非常にセキュアである一方、一歩設定を間違えると運用性が大きく損なわれるという特徴があります。
セキュリティと運用性のバランスを取るために、次のような方針をおすすめします。
- 「呼び出し経路」と「監視・運用経路」を分けて考える
- APIM からの呼び出しに必要な IP / VNet
- 運用メンバーがポータルから見るための IP / VNet
- ネットワーク制御と ID ベース制御の両方を使う
- ネットワークは「どこから来たか」を制御する
- Azure AD / RBAC は「誰がアクセスしているか」を制御する
- 監査ログを必ず有効化する
- 診断設定で Log Analytics などにログを送信
- 誰がいつどの Logic App を閲覧・実行したかを追跡できるようにする
- 本番・検証・開発環境でポリシーを分ける
- 本番は Access Restriction を厳格に、実行履歴 I/O も最小限
- 検証・開発はもう少し緩めてデバッグしやすくする
まとめ:CORS を疑う前に Access Restriction を見直そう
最後に、本記事のポイントを整理します。
- Logic Apps Standard の実行履歴で Inputs / Outputs が表示されず、CORS 警告が出ることがある
- しかし多くの場合、真の原因は Access Restriction によるネットワークブロック であり、CORS 設定を変えても効果はない
- 実行履歴の I/O は ポータルを開いている人のブラウザ → Logic App ランタイム の直接通信で取得される
- APIM だけを Allow しても、人間が見るための通信は通らないため、閲覧者(または社内の固定送信元)の IP を Allow に追加する必要がある
- 複数メンバーがいる企業環境では、
- 固定社内 IP(NAT / Egress)を許可する
- プライベート エンドポイント+VPN/ExpressRoute を活用する
- 運用ウィンドウのみ一時的に許可する
- 診断ログで I/O を追跡する
- 困ったときは「自分の送信元 IP が Access Restriction で許可されているか?」をまず確認する
Logic Apps Standard はネットワーク・セキュリティの設計次第で非常に強力な基盤になりますが、その分だけ小さな設定ミスが可視性の低下につながりがちです。本記事の内容を参考に、「CORS 警告」に惑わされることなく、Access Restriction と運用パターンを正しく設計していただければ幸いです。

コメント