<?xml version="1.0" encoding="utf-8"?><feed xmlns="http://www.w3.org/2005/Atom" ><generator uri="https://jekyllrb.com/" version="3.10.0">Jekyll</generator><link href="https://tech.saiut.com/feed.xml" rel="self" type="application/atom+xml" /><link href="https://tech.saiut.com/" rel="alternate" type="text/html" /><updated>2026-03-20T02:00:38+09:00</updated><id>https://tech.saiut.com/feed.xml</id><title type="html">saiut.github.io</title><subtitle>Azure で検証したことをまとめています。Azure インフラ領域の検証や Tips を紹介する技術ブログです。</subtitle><author><name>saiut</name></author><entry><title type="html">Private Link + Private DNS Zone の「あるある」トラブルシューティング集</title><link href="https://tech.saiut.com/privatelink-dns-troubleshooting/" rel="alternate" type="text/html" title="Private Link + Private DNS Zone の「あるある」トラブルシューティング集" /><published>2026-03-10T18:00:00+09:00</published><updated>2026-03-10T18:00:00+09:00</updated><id>https://tech.saiut.com/privatelink-dns-troubleshooting</id><content type="html" xml:base="https://tech.saiut.com/privatelink-dns-troubleshooting/"><![CDATA[<h2 id="こんなことを書いています">こんなことを書いています</h2>

<ul>
  <li>Azure Private Endpoint を使った際に名前解決がうまくいかない「あるある」パターン 7 選</li>
  <li>各パターンの事象・原因・解決策を具体的に整理</li>
  <li>nslookup / Resolve-DnsName などの確認コマンド例付き</li>
  <li>Hub-Spoke 構成やオンプレミス接続時に特にハマりやすいポイントを重点解説</li>
</ul>

<!--more-->

<h2 id="はじめに">はじめに</h2>

<p>Azure Private Endpoint を使うと、Azure PaaS サービスへの通信を VNet 内のプライベート IP 経由に閉じることができます。</p>

<p>ただし、Private Endpoint を作成しただけでは十分ではありません。<strong>DNS の名前解決が正しく Private IP を返すように構成する</strong>必要があります。</p>

<p>そこで重要になるのが Azure Private DNS Zone です。Private DNS Zone にレコードを用意し、対象の VNet にリンクすることで、VNet 内の VM や各種サービスが Private Endpoint の Private IP を名前解決できるようになります。</p>

<p>仕組み自体はシンプルですが、実務では「名前解決できない」「なぜかパブリック IP に解決される」「オンプレミスからだけつながらない」といったトラブルがよく発生します。</p>

<p>本記事では、特によくある 7 つのパターンを取り上げ、事象、原因、解決策の順で整理します。</p>

<h2 id="パターン-1-private-dns-zone-を-vnet-にリンクし忘れて名前解決できない">パターン 1: Private DNS Zone を VNet にリンクし忘れて名前解決できない</h2>

<h3 id="事象">事象</h3>

<p>Private Endpoint を作成し、Private DNS Zone にも A レコードが登録されているのに、VM から <code class="language-plaintext highlighter-rouge">nslookup</code> するとパブリック IP が返ってくる。</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>&gt; nslookup myaccount.blob.core.windows.net
Non-authoritative answer:
Name:    blob.xxxx.store.core.windows.net
Address:  20.xx.xx.xx   ← パブリック IP
</code></pre></div></div>

<h3 id="原因">原因</h3>

<p>Private DNS Zone を作成しただけでは、VNet 内のリソースはそのゾーンを参照しません。<strong>Private DNS Zone の「仮想ネットワーク リンク」が未設定</strong>のため、VNet の DNS 解決に Private DNS Zone が使われていない状態です。</p>

<h3 id="解決策">解決策</h3>

<p>Azure Portal で Private DNS Zone の <strong>[仮想ネットワーク リンク]</strong> を開き、対象の VNet をリンクします。</p>

<div class="language-powershell highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="c"># PowerShell でリンクを作成する例</span><span class="w">
</span><span class="n">New-AzPrivateDnsVirtualNetworkLink</span><span class="w"> </span><span class="se">`
</span><span class="w">  </span><span class="nt">-ResourceGroupName</span><span class="w"> </span><span class="s2">"rg-network"</span><span class="w"> </span><span class="se">`
</span><span class="w">  </span><span class="nt">-ZoneName</span><span class="w"> </span><span class="s2">"privatelink.blob.core.windows.net"</span><span class="w"> </span><span class="se">`
</span><span class="w">  </span><span class="nt">-Name</span><span class="w"> </span><span class="s2">"link-to-vnet-spoke01"</span><span class="w"> </span><span class="se">`
</span><span class="w">  </span><span class="nt">-VirtualNetworkId</span><span class="w"> </span><span class="s2">"/subscriptions/&lt;sub-id&gt;/resourceGroups/rg-network/providers/Microsoft.Network/virtualNetworks/vnet-spoke01"</span><span class="w"> </span><span class="se">`
</span><span class="w">  </span><span class="nt">-EnableRegistration</span><span class="w"> </span><span class="bp">$false</span><span class="w">
</span></code></pre></div></div>

<p>リンク作成後、再度名前解決を確認します。</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>&gt; nslookup myaccount.blob.core.windows.net
Name:    myaccount.privatelink.blob.core.windows.net
Address:  10.0.1.4   ← Private IP
</code></pre></div></div>

<h3 id="ポイント">ポイント</h3>

<ul>
  <li><strong><code class="language-plaintext highlighter-rouge">-EnableRegistration</code> は <code class="language-plaintext highlighter-rouge">$false</code></strong> にしてください。<code class="language-plaintext highlighter-rouge">$true</code> にすると VM のホスト名を Private DNS Zone に自動登録する機能が有効になりますが、PaaS の Private Endpoint の名前解決では通常不要です。</li>
  <li>1 つの Private DNS Zone に対して複数の VNet をリンクできます。</li>
</ul>

<h2 id="パターン-2-オンプレミスや他-vnet-から-private-endpoint-の名前解決ができない">パターン 2: オンプレミスや他 VNet から Private Endpoint の名前解決ができない</h2>

<h3 id="事象-1">事象</h3>

<p>Private Endpoint を配置した VNet 内の VM からは名前解決できるが、VPN/ExpressRoute 経由のオンプレミスや、ピアリングしている別の VNet からは名前解決できない。</p>

<h3 id="原因-1">原因</h3>

<p>Azure Private DNS Zone は、基本的に <strong>リンクされた VNet 内</strong> でのみ有効です。オンプレミスの DNS サーバーは Azure Private DNS Zone を直接参照できません。</p>

<p>そのため、オンプレミスのクライアントはパブリック DNS を引いてしまい、結果としてパブリック IP が返ります。</p>

<h3 id="解決策-1">解決策</h3>

<p><strong>DNS フォワーダー（条件付きフォワーダー）</strong> を構成し、<code class="language-plaintext highlighter-rouge">privatelink.*.core.windows.net</code> などのクエリを Azure 側へ転送できるようにします。</p>

<h4 id="方法-a-azure-dns-private-resolver-を使う推奨">方法 A: Azure DNS Private Resolver を使う（推奨）</h4>

<p>Azure DNS Private Resolver を Hub VNet にデプロイし、インバウンドエンドポイントの IP をオンプレミス DNS サーバーの条件付きフォワーダー先に設定します。</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>オンプレ DNS サーバー
  → 条件付きフォワーダー: privatelink.blob.core.windows.net → 10.0.0.4 (DNS Private Resolver のインバウンド IP)
    → Azure DNS (168.63.129.16)
      → Private DNS Zone の A レコード → Private IP
</code></pre></div></div>

<h4 id="方法-b-azure-vm-上に-dns-フォワーダーを構成する">方法 B: Azure VM 上に DNS フォワーダーを構成する</h4>

<p>Hub VNet 上の VM に DNS サーバー（Windows DNS や Unbound など）を構成し、<code class="language-plaintext highlighter-rouge">168.63.129.16</code> への条件付きフォワーダーを設定します。オンプレミスの DNS サーバーからはこの VM の IP にフォワードします。</p>

<h3 id="ポイント-1">ポイント</h3>

<ul>
  <li>Azure DNS Private Resolver は VM 不要のマネージドサービスなので、新規構築では方法 A を推奨します。</li>
  <li>オンプレミス側のフォワーダー設定では、<code class="language-plaintext highlighter-rouge">privatelink</code> を含む FQDN のゾーンを対象にしてください。</li>
</ul>

<h2 id="パターン-3-private-dns-zone-のゾーン名を間違えている">パターン 3: Private DNS Zone のゾーン名を間違えている</h2>

<h3 id="事象-2">事象</h3>

<p>Private DNS Zone を作成し、VNet リンクも設定しているが、名前解決が Private IP にならない。</p>

<h3 id="原因-2">原因</h3>

<p>Azure サービスごとに <strong>Private DNS Zone のゾーン名が異なります</strong>。間違ったゾーン名で作成すると、DNS クエリがそのゾーンにマッチしないため、パブリック DNS にフォールバックします。</p>

<h3 id="よくある間違いの例">よくある間違いの例</h3>

<table>
  <thead>
    <tr>
      <th>サービス</th>
      <th>正しいゾーン名</th>
      <th>ありがちな間違い</th>
    </tr>
  </thead>
  <tbody>
    <tr>
      <td>Blob Storage</td>
      <td><code class="language-plaintext highlighter-rouge">privatelink.blob.core.windows.net</code></td>
      <td><code class="language-plaintext highlighter-rouge">privatelink.storage.core.windows.net</code></td>
    </tr>
    <tr>
      <td>Azure SQL Database</td>
      <td><code class="language-plaintext highlighter-rouge">privatelink.database.windows.net</code></td>
      <td><code class="language-plaintext highlighter-rouge">privatelink.sql.azure.com</code></td>
    </tr>
    <tr>
      <td>Key Vault</td>
      <td><code class="language-plaintext highlighter-rouge">privatelink.vaultcore.azure.net</code></td>
      <td><code class="language-plaintext highlighter-rouge">privatelink.keyvault.azure.net</code></td>
    </tr>
    <tr>
      <td>Azure Cosmos DB (SQL API)</td>
      <td><code class="language-plaintext highlighter-rouge">privatelink.documents.azure.com</code></td>
      <td><code class="language-plaintext highlighter-rouge">privatelink.cosmosdb.azure.com</code></td>
    </tr>
    <tr>
      <td>Azure Monitor (Log Analytics)</td>
      <td><code class="language-plaintext highlighter-rouge">privatelink.oms.opinsights.azure.com</code> など複数</td>
      <td>ゾーンの一部が欠落</td>
    </tr>
  </tbody>
</table>

<h3 id="解決策-2">解決策</h3>

<p>Microsoft Learn の公式ドキュメント <a href="https://learn.microsoft.com/ja-jp/azure/private-link/private-endpoint-dns">Azure プライベート エンドポイントの DNS 構成</a> に、サービスごとの正しいゾーン名一覧が掲載されています。必ずこのドキュメントを参照してください。</p>

<h3 id="ポイント-2">ポイント</h3>

<ul>
  <li>特に <strong>Azure Monitor 関連</strong> は、利用する機能に応じて <code class="language-plaintext highlighter-rouge">privatelink.oms.opinsights.azure.com</code>、<code class="language-plaintext highlighter-rouge">privatelink.ods.opinsights.azure.com</code>、<code class="language-plaintext highlighter-rouge">privatelink.agentsvc.azure-automation.net</code>、<code class="language-plaintext highlighter-rouge">privatelink.monitor.azure.com</code>、<code class="language-plaintext highlighter-rouge">privatelink.blob.core.windows.net</code> など複数のゾーンが必要になりやすく、漏れやすいです。</li>
  <li>Private Endpoint 作成時の <strong>自動 DNS 統合</strong>（後述のパターン 7）を使えば、正しいゾーン名で自動作成されるため、ゾーン名の間違いを防げます。</li>
</ul>

<h2 id="パターン-4-パブリック-dns-が優先されて-private-ip-に解決されない">パターン 4: パブリック DNS が優先されて Private IP に解決されない</h2>

<h3 id="事象-3">事象</h3>

<p>VNet 内の VM から名前解決しても、Private IP ではなくパブリック IP が返ってくる。Private DNS Zone のリンクは設定済み。</p>

<h3 id="原因-3">原因</h3>

<p>VNet または VM の <strong>DNS 設定がカスタム DNS サーバーを指している</strong> 場合、Azure 既定の DNS（168.63.129.16）は使われません。</p>

<p>そのカスタム DNS サーバーが <code class="language-plaintext highlighter-rouge">privatelink.*</code> のクエリを適切に処理できていないと、Private DNS Zone が参照されず、パブリック DNS にフォールバックしてしまいます。</p>

<h3 id="確認方法">確認方法</h3>

<div class="language-powershell highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="c"># VM の DNS 設定を確認</span><span class="w">
</span><span class="n">Get-DnsClientServerAddress</span><span class="w"> </span><span class="nt">-InterfaceAlias</span><span class="w"> </span><span class="s2">"Ethernet"</span><span class="w">

</span><span class="c"># VNet の DNS 設定を Azure CLI で確認</span><span class="w">
</span><span class="n">az</span><span class="w"> </span><span class="nx">network</span><span class="w"> </span><span class="nx">vnet</span><span class="w"> </span><span class="nx">show</span><span class="w"> </span><span class="nt">--name</span><span class="w"> </span><span class="nx">vnet-spoke01</span><span class="w"> </span><span class="nt">--resource-group</span><span class="w"> </span><span class="nx">rg-network</span><span class="w"> </span><span class="nt">--query</span><span class="w"> </span><span class="s2">"dhcpOptions.dnsServers"</span><span class="w">
</span></code></pre></div></div>

<h3 id="解決策-3">解決策</h3>

<p>カスタム DNS サーバー（例: Hub VNet 上の DC や DNS サーバー）に、<code class="language-plaintext highlighter-rouge">privatelink.*</code> ゾーンの<strong>条件付きフォワーダー</strong>を <code class="language-plaintext highlighter-rouge">168.63.129.16</code> 宛に設定してください。</p>

<p>Windows DNS サーバーの場合:</p>

<div class="language-powershell highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="c"># 条件付きフォワーダーの追加例</span><span class="w">
</span><span class="n">Add-DnsServerConditionalForwarderZone</span><span class="w"> </span><span class="se">`
</span><span class="w">  </span><span class="nt">-Name</span><span class="w"> </span><span class="s2">"privatelink.blob.core.windows.net"</span><span class="w"> </span><span class="se">`
</span><span class="w">  </span><span class="nt">-MasterServers</span><span class="w"> </span><span class="nx">168.63.129.16</span><span class="w">
</span></code></pre></div></div>

<h3 id="ポイント-3">ポイント</h3>

<ul>
  <li><code class="language-plaintext highlighter-rouge">168.63.129.16</code> は Azure のワイヤサーバーで、<strong>Azure VM 内からのみ到達可能</strong>です。オンプレミスの DNS サーバーから直接フォワードすることはできません（パターン 2 参照）。</li>
  <li>VNet の DNS 設定を「既定（Azure 提供）」に戻すと解消するケースもありますが、Active Directory 環境ではカスタム DNS が必要なことが多いため、条件付きフォワーダーで対応するのが現実的です。</li>
</ul>

<h2 id="パターン-5-hub-spoke-構成で-private-dns-zone-のリンク先-vnet-を間違える">パターン 5: Hub-Spoke 構成で Private DNS Zone のリンク先 VNet を間違える</h2>

<h3 id="事象-4">事象</h3>

<p>Hub-Spoke 構成で、Spoke VNet 上の VM から Private Endpoint の名前解決ができない。Hub VNet 上の VM からは名前解決できる。</p>

<h3 id="原因-4">原因</h3>

<p>Private DNS Zone の仮想ネットワーク リンクが <strong>Hub VNet のみに設定</strong>されており、Spoke VNet にリンクされていないケースです。</p>

<p>Hub-Spoke 構成では、DNS の設計パターンによって対応が異なります。</p>

<h3 id="解決策-4">解決策</h3>

<h4 id="パターン-a-spoke-vnet-が-azure-既定-dns-を使っている場合">パターン A: Spoke VNet が Azure 既定 DNS を使っている場合</h4>

<p>Spoke VNet にも Private DNS Zone の仮想ネットワーク リンクを追加します。</p>

<div class="language-powershell highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="c"># Spoke VNet へのリンク追加</span><span class="w">
</span><span class="n">New-AzPrivateDnsVirtualNetworkLink</span><span class="w"> </span><span class="se">`
</span><span class="w">  </span><span class="nt">-ResourceGroupName</span><span class="w"> </span><span class="s2">"rg-network"</span><span class="w"> </span><span class="se">`
</span><span class="w">  </span><span class="nt">-ZoneName</span><span class="w"> </span><span class="s2">"privatelink.blob.core.windows.net"</span><span class="w"> </span><span class="se">`
</span><span class="w">  </span><span class="nt">-Name</span><span class="w"> </span><span class="s2">"link-to-vnet-spoke01"</span><span class="w"> </span><span class="se">`
</span><span class="w">  </span><span class="nt">-VirtualNetworkId</span><span class="w"> </span><span class="s2">"/subscriptions/&lt;sub-id&gt;/resourceGroups/rg-network/providers/Microsoft.Network/virtualNetworks/vnet-spoke01"</span><span class="w">
</span></code></pre></div></div>

<h4 id="パターン-b-spoke-vnet-のカスタム-dns-が-hub-の-dns-サーバーを指している場合">パターン B: Spoke VNet のカスタム DNS が Hub の DNS サーバーを指している場合</h4>

<p>Hub VNet のリンクのみで OK ですが、Hub 上の DNS サーバー（またはDNS Private Resolver）が <code class="language-plaintext highlighter-rouge">168.63.129.16</code> に条件付きフォワードしている必要があります。</p>

<div class="language-plaintext highlighter-rouge"><div class="highlight"><pre class="highlight"><code>Spoke VM → Hub DNS サーバー → 168.63.129.16 → Private DNS Zone → Private IP
</code></pre></div></div>

<p>この設計では、<strong>Hub 側に DNS を集約し、Spoke が常に Hub の DNS を利用する</strong> 前提であれば、実装上は Private DNS Zone を <strong>Hub VNet のみにリンク</strong>して名前解決できるケースがあります。ただし、Microsoft Learn では、名前解決が必要な VNet をそれぞれ Private DNS Zone にリンクする構成が基本です。中央集約型 DNS 設計を採る場合は、この前提を明示して設計してください。</p>

<h3 id="ポイント-4">ポイント</h3>

<ul>
  <li>Hub-Spoke が多数ある環境では、<strong>パターン B の中央集約型 DNS 設計</strong>は管理しやすい一方で、Spoke が Hub DNS を必ず利用することを前提に設計・運用する必要があります。</li>
  <li>Azure DNS Private Resolver を Hub に配置し、Spoke VNet の DNS 設定でその IP を利用する構成は、実務でも採用しやすいパターンです。</li>
</ul>

<h2 id="パターン-6-dns-は解決できるのにアプリから接続できない">パターン 6: DNS は解決できるのにアプリから接続できない</h2>

<h3 id="事象-5">事象</h3>

<p><code class="language-plaintext highlighter-rouge">nslookup</code> や <code class="language-plaintext highlighter-rouge">Resolve-DnsName</code> では Private IP が正しく返ってくるのに、アプリケーション（Web アプリ、SDK など）から Private Endpoint 経由で接続できない。</p>

<div class="language-powershell highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="c"># DNS は正しく解決できている</span><span class="w">
</span><span class="n">Resolve-DnsName</span><span class="w"> </span><span class="nx">myaccount.blob.core.windows.net</span><span class="w">
</span><span class="c"># → 10.0.1.4 (Private IP) ✓</span><span class="w">

</span><span class="c"># しかし接続するとタイムアウトする</span><span class="w">
</span><span class="n">Test-NetConnection</span><span class="w"> </span><span class="nt">-ComputerName</span><span class="w"> </span><span class="nx">myaccount.blob.core.windows.net</span><span class="w"> </span><span class="nt">-Port</span><span class="w"> </span><span class="nx">443</span><span class="w">
</span><span class="c"># → TcpTestSucceeded : False</span><span class="w">
</span></code></pre></div></div>

<h3 id="原因複数の可能性">原因（複数の可能性）</h3>

<h4 id="原因-a-nsg--ファイアウォールでブロックされている">原因 A: NSG / ファイアウォールでブロックされている</h4>

<p>Private Endpoint のサブネットに関連付けられた NSG や、Azure Firewall / NVA がトラフィックをブロックしている場合があります。</p>

<div class="language-powershell highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="c"># Private Endpoint への疎通確認</span><span class="w">
</span><span class="n">Test-NetConnection</span><span class="w"> </span><span class="nt">-ComputerName</span><span class="w"> </span><span class="nx">10.0.1.4</span><span class="w"> </span><span class="nt">-Port</span><span class="w"> </span><span class="nx">443</span><span class="w">
</span></code></pre></div></div>

<h4 id="原因-b-プロキシ設定">原因 B: プロキシ設定</h4>

<p>アプリケーションや OS にプロキシが設定されていると、DNS 解決はローカルで行われても、実際の HTTP 通信がプロキシ経由になり、プロキシサーバー側でパブリック IP に解決されてしまうことがあります。</p>

<div class="language-powershell highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="c"># プロキシ設定の確認</span><span class="w">
</span><span class="n">netsh</span><span class="w"> </span><span class="nx">winhttp</span><span class="w"> </span><span class="nx">show</span><span class="w"> </span><span class="nx">proxy</span><span class="w">

</span><span class="c"># 環境変数の確認</span><span class="w">
</span><span class="nv">$</span><span class="nn">env</span><span class="p">:</span><span class="nv">HTTP_PROXY</span><span class="w">
</span><span class="nv">$</span><span class="nn">env</span><span class="p">:</span><span class="nv">HTTPS_PROXY</span><span class="w">
</span></code></pre></div></div>

<h4 id="原因-c-split-brain-dns">原因 C: Split-brain DNS</h4>

<p><code class="language-plaintext highlighter-rouge">nslookup</code> はシステムの DNS キャッシュやホストファイルを無視して直接 DNS サーバーに問い合わせます。一方、アプリケーションは OS の名前解決を使います。<code class="language-plaintext highlighter-rouge">hosts</code> ファイルや DNS クライアントキャッシュに古いエントリが残っていると、アプリだけ異なる IP に解決される場合があります。</p>

<div class="language-powershell highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="c"># DNS キャッシュの確認</span><span class="w">
</span><span class="n">Get-DnsClientCache</span><span class="w"> </span><span class="o">|</span><span class="w"> </span><span class="n">Where-Object</span><span class="w"> </span><span class="p">{</span><span class="w"> </span><span class="bp">$_</span><span class="o">.</span><span class="nf">Entry</span><span class="w"> </span><span class="o">-like</span><span class="w"> </span><span class="s2">"*myaccount*"</span><span class="w"> </span><span class="p">}</span><span class="w">

</span><span class="c"># hosts ファイルの確認</span><span class="w">
</span><span class="n">Get-Content</span><span class="w"> </span><span class="nx">C:\Windows\System32\drivers\etc\hosts</span><span class="w"> </span><span class="o">|</span><span class="w"> </span><span class="n">Select-String</span><span class="w"> </span><span class="s2">"myaccount"</span><span class="w">

</span><span class="c"># DNS キャッシュのクリア</span><span class="w">
</span><span class="n">Clear-DnsClientCache</span><span class="w">
</span></code></pre></div></div>

<h3 id="ポイント-5">ポイント</h3>

<ul>
  <li><code class="language-plaintext highlighter-rouge">nslookup</code> の結果だけで「DNS は問題ない」と判断しないことが重要です。<code class="language-plaintext highlighter-rouge">Resolve-DnsName</code>、<code class="language-plaintext highlighter-rouge">dig</code>、アプリケーション実行時の挙動を合わせて確認し、どこで結果が変わるのかを切り分けましょう。</li>
  <li>プロキシが原因の場合は、Private Endpoint の FQDN をプロキシのバイパスリストに追加します。</li>
</ul>

<h2 id="パターン-7-自動-dns-統合を使わず-a-レコードが登録されていない">パターン 7: 自動 DNS 統合を使わず A レコードが登録されていない</h2>

<h3 id="事象-6">事象</h3>

<p>Private Endpoint を作成したが、Private DNS Zone に A レコードが存在せず、名前解決が Private IP にならない。</p>

<h3 id="原因-5">原因</h3>

<p>Azure Portal で Private Endpoint を作成する際、<strong>「プライベート DNS ゾーンとの統合」</strong> オプションがあります。このオプションを「いいえ」にした場合、または ARM テンプレート / Terraform / Bicep で <code class="language-plaintext highlighter-rouge">privateDnsZoneGroups</code> を構成しなかった場合、A レコードは自動登録されません。</p>

<h3 id="解決策-5">解決策</h3>

<h4 id="方法-a-private-dns-zone-group-を後から追加する推奨">方法 A: Private DNS Zone Group を後から追加する（推奨）</h4>

<div class="language-powershell highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="c"># Private DNS Zone Group の作成</span><span class="w">
</span><span class="nv">$zone</span><span class="w"> </span><span class="o">=</span><span class="w"> </span><span class="n">Get-AzPrivateDnsZone</span><span class="w"> </span><span class="nt">-ResourceGroupName</span><span class="w"> </span><span class="s2">"rg-network"</span><span class="w"> </span><span class="nt">-Name</span><span class="w"> </span><span class="s2">"privatelink.blob.core.windows.net"</span><span class="w">

</span><span class="nv">$config</span><span class="w"> </span><span class="o">=</span><span class="w"> </span><span class="n">New-AzPrivateDnsZoneConfig</span><span class="w"> </span><span class="se">`
</span><span class="w">  </span><span class="nt">-Name</span><span class="w"> </span><span class="s2">"privatelink-blob-core-windows-net"</span><span class="w"> </span><span class="se">`
</span><span class="w">  </span><span class="nt">-PrivateDnsZoneId</span><span class="w"> </span><span class="nv">$zone</span><span class="o">.</span><span class="nf">ResourceId</span><span class="w">

</span><span class="n">New-AzPrivateDnsZoneGroup</span><span class="w"> </span><span class="se">`
</span><span class="w">  </span><span class="nt">-ResourceGroupName</span><span class="w"> </span><span class="s2">"rg-app"</span><span class="w"> </span><span class="se">`
</span><span class="w">  </span><span class="nt">-PrivateEndpointName</span><span class="w"> </span><span class="s2">"pe-storage01"</span><span class="w"> </span><span class="se">`
</span><span class="w">  </span><span class="nt">-Name</span><span class="w"> </span><span class="s2">"default"</span><span class="w"> </span><span class="se">`
</span><span class="w">  </span><span class="nt">-PrivateDnsZoneConfig</span><span class="w"> </span><span class="nv">$config</span><span class="w">
</span></code></pre></div></div>

<p>Private DNS Zone Group を構成すると、A レコードが自動的に作成・管理されます。Private Endpoint の IP が変わった場合も自動更新されるため、<strong>この方法を強く推奨</strong>します。</p>

<h4 id="方法-b-手動で-a-レコードを追加する">方法 B: 手動で A レコードを追加する</h4>

<div class="language-powershell highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="c"># 手動で A レコードを登録する例</span><span class="w">
</span><span class="n">New-AzPrivateDnsRecordSet</span><span class="w"> </span><span class="se">`
</span><span class="w">  </span><span class="nt">-ResourceGroupName</span><span class="w"> </span><span class="s2">"rg-network"</span><span class="w"> </span><span class="se">`
</span><span class="w">  </span><span class="nt">-ZoneName</span><span class="w"> </span><span class="s2">"privatelink.blob.core.windows.net"</span><span class="w"> </span><span class="se">`
</span><span class="w">  </span><span class="nt">-Name</span><span class="w"> </span><span class="s2">"myaccount"</span><span class="w"> </span><span class="se">`
</span><span class="w">  </span><span class="nt">-RecordType</span><span class="w"> </span><span class="nx">A</span><span class="w"> </span><span class="se">`
</span><span class="w">  </span><span class="nt">-Ttl</span><span class="w"> </span><span class="nx">3600</span><span class="w"> </span><span class="se">`
</span><span class="w">  </span><span class="nt">-PrivateDnsRecords</span><span class="w"> </span><span class="p">(</span><span class="n">New-AzPrivateDnsRecordConfig</span><span class="w"> </span><span class="nt">-IPv4Address</span><span class="w"> </span><span class="s2">"10.0.1.4"</span><span class="p">)</span><span class="w">
</span></code></pre></div></div>

<h3 id="ポイント-6">ポイント</h3>

<ul>
  <li>手動登録の場合、Private Endpoint を再作成して IP が変わると<strong>レコードの更新を忘れる</strong>リスクがあります。必ず Private DNS Zone Group を使いましょう。</li>
  <li>Bicep / Terraform で IaC 管理している場合は、必ず <code class="language-plaintext highlighter-rouge">privateDnsZoneGroups</code>（Bicep）または <code class="language-plaintext highlighter-rouge">azurerm_private_dns_zone_group</code>（Terraform）をテンプレートに含めてください。</li>
</ul>

<h2 id="トラブルシューティングに使えるコマンド集">トラブルシューティングに使えるコマンド集</h2>

<p>以下は、Private Link + DNS のトラブルシューティング時に役立つコマンドをまとめたものです。</p>

<h3 id="dns-の名前解決確認">DNS の名前解決確認</h3>

<div class="language-powershell highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="c"># Windows - Resolve-DnsName（OS のリゾルバーを使用。推奨）</span><span class="w">
</span><span class="n">Resolve-DnsName</span><span class="w"> </span><span class="nx">myaccount.blob.core.windows.net</span><span class="w">

</span><span class="c"># Windows - nslookup（直接 DNS サーバーに問い合わせ）</span><span class="w">
</span><span class="n">nslookup</span><span class="w"> </span><span class="nx">myaccount.blob.core.windows.net</span><span class="w">

</span><span class="c"># Linux - dig（詳細な DNS 応答を確認）</span><span class="w">
</span><span class="n">dig</span><span class="w"> </span><span class="nx">myaccount.blob.core.windows.net</span><span class="w">

</span><span class="c"># Linux - host</span><span class="w">
</span><span class="n">host</span><span class="w"> </span><span class="nx">myaccount.blob.core.windows.net</span><span class="w">
</span></code></pre></div></div>

<h3 id="cname-チェーンの確認">CNAME チェーンの確認</h3>

<p>Private Endpoint が正しく構成されている場合、<code class="language-plaintext highlighter-rouge">privatelink</code> を含む CNAME が返ります。</p>

<div class="language-powershell highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="n">Resolve-DnsName</span><span class="w"> </span><span class="nx">myaccount.blob.core.windows.net</span><span class="w"> </span><span class="nt">-Type</span><span class="w"> </span><span class="nx">CNAME</span><span class="w">
</span><span class="c"># → myaccount.blob.core.windows.net → myaccount.privatelink.blob.core.windows.net</span><span class="w">
</span></code></pre></div></div>

<p><code class="language-plaintext highlighter-rouge">privatelink</code> の CNAME が返らない場合、Private Endpoint の作成自体に問題がある可能性があります。</p>

<h3 id="ネットワーク疎通確認">ネットワーク疎通確認</h3>

<div class="language-powershell highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="c"># TCP 接続テスト</span><span class="w">
</span><span class="n">Test-NetConnection</span><span class="w"> </span><span class="nt">-ComputerName</span><span class="w"> </span><span class="nx">myaccount.blob.core.windows.net</span><span class="w"> </span><span class="nt">-Port</span><span class="w"> </span><span class="nx">443</span><span class="w">

</span><span class="c"># Linux</span><span class="w">
</span><span class="n">curl</span><span class="w"> </span><span class="nt">-v</span><span class="w"> </span><span class="nx">https://myaccount.blob.core.windows.net</span><span class="w">
</span><span class="n">nc</span><span class="w"> </span><span class="nt">-zv</span><span class="w"> </span><span class="nx">myaccount.blob.core.windows.net</span><span class="w"> </span><span class="nx">443</span><span class="w">
</span></code></pre></div></div>

<h3 id="dns-キャッシュの管理">DNS キャッシュの管理</h3>

<div class="language-powershell highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="c"># Windows - キャッシュ確認</span><span class="w">
</span><span class="n">Get-DnsClientCache</span><span class="w"> </span><span class="o">|</span><span class="w"> </span><span class="n">Where-Object</span><span class="w"> </span><span class="p">{</span><span class="w"> </span><span class="bp">$_</span><span class="o">.</span><span class="nf">Entry</span><span class="w"> </span><span class="o">-like</span><span class="w"> </span><span class="s2">"*privatelink*"</span><span class="w"> </span><span class="p">}</span><span class="w">

</span><span class="c"># Windows - キャッシュクリア</span><span class="w">
</span><span class="n">Clear-DnsClientCache</span><span class="w">

</span><span class="c"># Linux - systemd-resolved のキャッシュクリア</span><span class="w">
</span><span class="n">sudo</span><span class="w"> </span><span class="nx">systemd-resolve</span><span class="w"> </span><span class="nt">--flush-caches</span><span class="w">
</span></code></pre></div></div>

<h3 id="private-dns-zone-の状態確認-azure-cli">Private DNS Zone の状態確認 (Azure CLI)</h3>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="c"># Private DNS Zone のレコード一覧</span>
az network private-dns record-set list <span class="se">\</span>
  <span class="nt">--resource-group</span> rg-network <span class="se">\</span>
  <span class="nt">--zone-name</span> privatelink.blob.core.windows.net <span class="se">\</span>
  <span class="nt">--output</span> table

<span class="c"># 仮想ネットワーク リンクの一覧</span>
az network private-dns <span class="nb">link </span>vnet list <span class="se">\</span>
  <span class="nt">--resource-group</span> rg-network <span class="se">\</span>
  <span class="nt">--zone-name</span> privatelink.blob.core.windows.net <span class="se">\</span>
  <span class="nt">--output</span> table

<span class="c"># Private Endpoint の DNS 構成確認</span>
az network private-endpoint dns-zone-group list <span class="se">\</span>
  <span class="nt">--resource-group</span> rg-app <span class="se">\</span>
  <span class="nt">--endpoint-name</span> pe-storage01 <span class="se">\</span>
  <span class="nt">--output</span> table
</code></pre></div></div>

<h2 id="まとめ">まとめ</h2>

<p>Private Link + Private DNS Zone のトラブルの多くは、<strong>「DNS の名前解決が Private IP を返さない」</strong> という点に集約されます。切り分けの基本は以下のフローです。</p>

<ol>
  <li><strong><code class="language-plaintext highlighter-rouge">Resolve-DnsName</code> で FQDN を引いて、Private IP が返るか？</strong>
    <ul>
      <li>返らない場合は、DNS 構成の問題を疑います（パターン 1〜5, 7）。</li>
      <li>返る場合は、ネットワークまたはアプリ側の問題を疑います（パターン 6）。</li>
    </ul>
  </li>
  <li><strong>CNAME チェーンに <code class="language-plaintext highlighter-rouge">privatelink</code> が含まれるか？</strong>
    <ul>
      <li>含まれない場合は、Private Endpoint の構成自体を確認します。</li>
      <li>含まれる場合は、Private DNS Zone 側の問題を確認します。</li>
    </ul>
  </li>
  <li><strong>どこから名前解決しているか？</strong>
    <ul>
      <li>VNet 内なら、Private DNS Zone のリンクとレコードを確認します。</li>
      <li>オンプレミスや他 VNet なら、DNS フォワーダーの構成を確認します。</li>
    </ul>
  </li>
</ol>

<p>この順番で見ていくと、どこで名前解決が崩れているのかをかなり効率よく切り分けられます。</p>

<h2 id="参考リンク">参考リンク</h2>

<ul>
  <li><a href="https://learn.microsoft.com/ja-jp/azure/private-link/private-endpoint-dns">Azure プライベート エンドポイントの DNS 構成</a></li>
  <li><a href="https://learn.microsoft.com/ja-jp/azure/private-link/private-link-overview">Azure Private Link とは</a></li>
  <li><a href="https://learn.microsoft.com/ja-jp/azure/dns/dns-private-resolver-overview">Azure DNS Private Resolver とは</a></li>
  <li><a href="https://learn.microsoft.com/ja-jp/azure/private-link/troubleshoot-private-endpoint-connectivity">プライベート エンドポイントの DNS の問題のトラブルシューティング</a></li>
  <li><a href="https://learn.microsoft.com/ja-jp/azure/dns/private-dns-virtual-network-links">仮想ネットワーク リンクを使用した Azure プライベート DNS ゾーン</a></li>
  <li><a href="https://learn.microsoft.com/ja-jp/azure/architecture/networking/guide/private-link-hub-spoke-network">Hub-spoke ネットワーク トポロジにおけるプライベート エンドポイントの DNS 解決</a></li>
</ul>]]></content><author><name>saiut</name></author><category term="ネットワーク" /><category term="Azure Private Link" /><category term="Azure Private Endpoint" /><category term="Azure Private DNS Zone" /><category term="DNS" /><category term="トラブルシューティング" /><summary type="html"><![CDATA[こんなことを書いています Azure Private Endpoint を使った際に名前解決がうまくいかない「あるある」パターン 7 選 各パターンの事象・原因・解決策を具体的に整理 nslookup / Resolve-DnsName などの確認コマンド例付き Hub-Spoke 構成やオンプレミス接続時に特にハマりやすいポイントを重点解説]]></summary></entry><entry><title type="html">Azure Site Recovery でフェールオーバーしたときは VM 拡張機能を再インストールすることを忘れずに</title><link href="https://tech.saiut.com/asr-extension/" rel="alternate" type="text/html" title="Azure Site Recovery でフェールオーバーしたときは VM 拡張機能を再インストールすることを忘れずに" /><published>2025-11-08T23:34:25+09:00</published><updated>2025-11-08T23:34:25+09:00</updated><id>https://tech.saiut.com/asr-extension</id><content type="html" xml:base="https://tech.saiut.com/asr-extension/"><![CDATA[<h2 id="こんなことを書いています">こんなことを書いています</h2>

<ul>
  <li>ASR のフェールオーバーは拡張機能の移行をサポートしていない</li>
  <li>AMA でログ取得している場合、フェールオーバー後はログが取得されなくなってしまう</li>
  <li>AMA の DCR を活用して、VM の再登録などを復旧計画に入れてしまうことを忘れずに</li>
</ul>

<!--more-->

<h2 id="asr-の制限事項">ASR の制限事項</h2>

<p>Azure Site Recovery の制限事項の 1 つとして、「拡張機能は再インストールしてください」というものがあります。</p>

<p><a href="https://learn.microsoft.com/ja-jp/azure/site-recovery/azure-to-azure-support-matrix#replicated-machines---compute-settings">Azure リージョン間での Azure VM ディザスター リカバリーに関するサポート マトリックス</a></p>

<p><img src="/assets/article_images/2025-11-08-asr-extension/limitation.jpg" alt="Limitation" /></p>

<p>そもそも拡張機能は公式サイトから引用すると以下のようなもので、「Azure VM に様々な機能を提供する軽量なアプリケーション」です。</p>
<blockquote>
  <p>拡張機能は、Azure 仮想マシン (VMs)でのデプロイ後の構成と自動化を提供する小さなアプリケーションです。 Azure プラットフォームでは、VM の構成、監視、セキュリティ、およびユーティリティのアプリケーションを対象とする多くの拡張機能をホストします。</p>
</blockquote>

<p><a href="https://learn.microsoft.com/ja-jp/azure/virtual-machines/extensions/overview">Azure 仮想マシンの拡張機能とその機能</a></p>

<p>代表的な拡張機能として Azure VM でログを取得する Azure Monitor Agent （AMA）がありますが、ASR でフェールオーバーした後は制限事項にある通り、拡張機能を再インストールしない限り、AMA を利用してログを取得することができません。</p>

<hr />

<h2 id="拡張機能を再インストールする">拡張機能を再インストールする</h2>

<p>ここでは AMA を例にして実際に ASR を使ってフェールオーバーした VM に対して AMA を再インストールする流れを見てみます。</p>

<p>VM をデプロイし、AMA でログを取得した場合、VM の拡張機能はこのようになっています。（AMA 以外の拡張機能も含まれています、AMA は AzureMonitorWindowsAgent です）</p>

<p><img src="/assets/article_images/2025-11-08-asr-extension/vmextension.jpg" alt="VM 拡張機能" /></p>

<p>対象の VM をフェールオーバーした後、改めて VM の拡張機能を確認してみると、サポートされていないためすべてなくなっています。
（対象の VM 名が一緒なのでわかりにくいですが）</p>

<p><img src="/assets/article_images/2025-11-08-asr-extension/vmextension_afterfailover.jpg" alt="フェールオーバー後" /></p>

<p>一応コマンドで確認すると…</p>

<div class="language-text highlighter-rouge"><div class="highlight"><pre class="highlight"><code> Type                : Microsoft.Azure.Monitor.AzureMonitorWindowsAgent
    TypeHandlerVersion  : 1.20.0.0
    Status              :
      Code              : ProvisioningState/Unresponsive
      Level             : Warning
      DisplayStatus     : Unresponsive
      Message           : Handler Microsoft.Azure.Monitor.AzureMonitorWindowsAgent of version 1.20.0.0 is unresponsive. Last
heartbeat: 10/6/2023 5:50:06 AM
</code></pre></div></div>

<p>「Unresponsive」と書かれていて、AMA の反応がないことがわかります。
この場合、AMA でログ取得するデータ収集ルールにおいても、フェールオーバーを行った VM を選択できません。
ですので、一度 AMA 拡張機能をアンインストールする必要があります。</p>

<p>コマンド</p>

<div class="language-powershell highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="n">Remove-AzVMExtension</span><span class="w"> </span><span class="nt">-Name</span><span class="w"> </span><span class="nx">AzureMonitorWindowsAgent</span><span class="w"> </span><span class="nt">-ResourceGroupName</span><span class="w"> </span><span class="err">&lt;</span><span class="nx">resource-group-name</span><span class="err">&gt;</span><span class="w"> </span><span class="nt">-VMName</span><span class="w"> </span><span class="err">&lt;</span><span class="nx">virtual-machine-name</span><span class="err">&gt;</span><span class="w">
</span></code></pre></div></div>

<p>結果</p>

<div class="language-text highlighter-rouge"><div class="highlight"><pre class="highlight"><code>Virtual machine extension removal operation
This cmdlet will remove the specified virtual machine extension. Do you want to continue?
[Y] Yes  [N] No  [S] Suspend  [?] Help (default is "Y"): Y
RequestId IsSuccessStatusCode StatusCode ReasonPhrase
                         True  NoContent No Content
</code></pre></div></div>

<p>削除をしてあげることで、データ収集ルールで VM を選択できるようになっているので追加してあげます。
（下記のスクリーンショットにはないのですが、AMA 拡張機能削除前は対象の VM は選べない状態となっています）</p>

<p><img src="/assets/article_images/2025-11-08-asr-extension/dcr.jpg" alt="データ収集ルール" /></p>

<p>これでログが無事取得できるようになりました。</p>

<p>ただ、この方法だと人力すぎますよね。</p>

<h2 id="復旧計画で-ama-再インストールを自動化する">復旧計画で AMA 再インストールを自動化する</h2>

<p>ASR では復旧計画というものがあり、DR 発動時に行う作業を1つの流れにまとめることが可能です。</p>

<p>例えば、復旧する順番として「DB サーバーを先に起動した後に Web サーバーを起動する」といった流れのように、 FO 時に起動の順番を決定することができるのが、復旧計画です。
この復旧計画を活用し、 ASR 発動後に AMA を再インストールするという流れにしてあげることで、自動で AMA が再インストールされてログが取れるようになります。</p>

<h2 id="automation-でフェールオーバー対象の-vm-の拡張機能を再インストールしてしまう">Automation でフェールオーバー対象の VM の拡張機能を再インストールしてしまう</h2>

<p>復旧計画では、Azure Automation のスクリプトを利用することが可能です。
流れとしては以下のような流れになるでしょう。</p>

<ol>
  <li>FO が開始され、別リージョンで VM が起動する</li>
  <li>別リージョンの VM から AMA をアンインストールするコマンドを実行する -&gt; Automation で実行</li>
  <li>AMA をインストールするコマンドが実行される</li>
  <li>データ収集ルール（DCR）に VM を再関連付けする</li>
</ol>

<p>以下は、Azure Automation の Runbook で使用できる AMA のインストールスクリプトの一例です。</p>

<div class="language-powershell highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="kr">param</span><span class="p">(</span><span class="w">
    </span><span class="p">[</span><span class="n">Parameter</span><span class="p">(</span><span class="n">Mandatory</span><span class="o">=</span><span class="bp">$true</span><span class="p">)]</span><span class="w">
    </span><span class="p">[</span><span class="n">string</span><span class="p">]</span><span class="nv">$vmName</span><span class="p">,</span><span class="w">
    
    </span><span class="p">[</span><span class="n">Parameter</span><span class="p">(</span><span class="n">Mandatory</span><span class="o">=</span><span class="bp">$true</span><span class="p">)]</span><span class="w">
    </span><span class="p">[</span><span class="n">string</span><span class="p">]</span><span class="nv">$resourceGroupName</span><span class="p">,</span><span class="w">
    
    </span><span class="p">[</span><span class="n">Parameter</span><span class="p">(</span><span class="n">Mandatory</span><span class="o">=</span><span class="bp">$true</span><span class="p">)]</span><span class="w">
    </span><span class="p">[</span><span class="n">string</span><span class="p">]</span><span class="nv">$location</span><span class="p">,</span><span class="w">
    
    </span><span class="p">[</span><span class="n">Parameter</span><span class="p">(</span><span class="n">Mandatory</span><span class="o">=</span><span class="bp">$true</span><span class="p">)]</span><span class="w">
    </span><span class="p">[</span><span class="n">string</span><span class="p">]</span><span class="nv">$dcrId</span><span class="w">
</span><span class="p">)</span><span class="w">

</span><span class="c"># Azure に接続（Managed Identity を使用）</span><span class="w">
</span><span class="n">Connect-AzAccount</span><span class="w"> </span><span class="nt">-Identity</span><span class="w">

</span><span class="c"># 既存の AMA 拡張機能を削除（エラーハンドリング付き）</span><span class="w">
</span><span class="kr">try</span><span class="w"> </span><span class="p">{</span><span class="w">
    </span><span class="n">Write-Output</span><span class="w"> </span><span class="s2">"Removing existing AMA extension from VM: </span><span class="nv">$vmName</span><span class="s2">"</span><span class="w">
    </span><span class="n">Remove-AzVMExtension</span><span class="w"> </span><span class="nt">-Name</span><span class="w"> </span><span class="s2">"AzureMonitorWindowsAgent"</span><span class="w"> </span><span class="nt">-ResourceGroupName</span><span class="w"> </span><span class="nv">$resourceGroupName</span><span class="w"> </span><span class="nt">-VMName</span><span class="w"> </span><span class="nv">$vmName</span><span class="w"> </span><span class="nt">-Force</span><span class="w">
    </span><span class="n">Write-Output</span><span class="w"> </span><span class="s2">"AMA extension removed successfully"</span><span class="w">
</span><span class="p">}</span><span class="w"> </span><span class="kr">catch</span><span class="w"> </span><span class="p">{</span><span class="w">
    </span><span class="n">Write-Output</span><span class="w"> </span><span class="s2">"Failed to remove AMA extension or extension not found: </span><span class="si">$(</span><span class="bp">$_</span><span class="o">.</span><span class="nf">Exception</span><span class="o">.</span><span class="nf">Message</span><span class="si">)</span><span class="s2">"</span><span class="w">
</span><span class="p">}</span><span class="w">

</span><span class="c"># AMA 拡張機能をインストール</span><span class="w">
</span><span class="kr">try</span><span class="w"> </span><span class="p">{</span><span class="w">
    </span><span class="n">Write-Output</span><span class="w"> </span><span class="s2">"Installing AMA extension on VM: </span><span class="nv">$vmName</span><span class="s2">"</span><span class="w">
    </span><span class="n">Set-AzVMExtension</span><span class="w"> </span><span class="nt">-ResourceGroupName</span><span class="w"> </span><span class="nv">$resourceGroupName</span><span class="w"> </span><span class="nt">-VMName</span><span class="w"> </span><span class="nv">$vmName</span><span class="w"> </span><span class="nt">-Name</span><span class="w"> </span><span class="s2">"AzureMonitorWindowsAgent"</span><span class="w"> </span><span class="nt">-Publisher</span><span class="w"> </span><span class="s2">"Microsoft.Azure.Monitor"</span><span class="w"> </span><span class="nt">-Type</span><span class="w"> </span><span class="s2">"AzureMonitorWindowsAgent"</span><span class="w"> </span><span class="nt">-TypeHandlerVersion</span><span class="w"> </span><span class="s2">"1.0"</span><span class="w"> </span><span class="nt">-Location</span><span class="w"> </span><span class="nv">$location</span><span class="w">
    </span><span class="n">Write-Output</span><span class="w"> </span><span class="s2">"AMA extension installed successfully"</span><span class="w">
</span><span class="p">}</span><span class="w"> </span><span class="kr">catch</span><span class="w"> </span><span class="p">{</span><span class="w">
    </span><span class="n">Write-Error</span><span class="w"> </span><span class="s2">"Failed to install AMA extension: </span><span class="si">$(</span><span class="bp">$_</span><span class="o">.</span><span class="nf">Exception</span><span class="o">.</span><span class="nf">Message</span><span class="si">)</span><span class="s2">"</span><span class="w">
    </span><span class="kr">throw</span><span class="w">
</span><span class="p">}</span><span class="w">

</span><span class="c"># データ収集ルールとの関連付け</span><span class="w">
</span><span class="kr">try</span><span class="w"> </span><span class="p">{</span><span class="w">
    </span><span class="n">Write-Output</span><span class="w"> </span><span class="s2">"Associating VM with Data Collection Rule: </span><span class="nv">$dcrId</span><span class="s2">"</span><span class="w">
    </span><span class="nv">$vm</span><span class="w"> </span><span class="o">=</span><span class="w"> </span><span class="n">Get-AzVM</span><span class="w"> </span><span class="nt">-ResourceGroupName</span><span class="w"> </span><span class="nv">$resourceGroupName</span><span class="w"> </span><span class="nt">-Name</span><span class="w"> </span><span class="nv">$vmName</span><span class="w">
    </span><span class="nv">$associationName</span><span class="w"> </span><span class="o">=</span><span class="w"> </span><span class="s2">"vm-</span><span class="nv">$vmName</span><span class="s2">-dcr-association"</span><span class="w">
    </span><span class="n">New-AzDataCollectionRuleAssociation</span><span class="w"> </span><span class="nt">-ResourceUri</span><span class="w"> </span><span class="nv">$vm</span><span class="o">.</span><span class="nf">Id</span><span class="w"> </span><span class="nt">-AssociationName</span><span class="w"> </span><span class="nv">$associationName</span><span class="w"> </span><span class="nt">-DataCollectionRuleId</span><span class="w"> </span><span class="nv">$dcrId</span><span class="w">
    </span><span class="n">Write-Output</span><span class="w"> </span><span class="s2">"DCR association completed successfully"</span><span class="w">
</span><span class="p">}</span><span class="w"> </span><span class="kr">catch</span><span class="w"> </span><span class="p">{</span><span class="w">
    </span><span class="n">Write-Error</span><span class="w"> </span><span class="s2">"Failed to associate VM with DCR: </span><span class="si">$(</span><span class="bp">$_</span><span class="o">.</span><span class="nf">Exception</span><span class="o">.</span><span class="nf">Message</span><span class="si">)</span><span class="s2">"</span><span class="w">
    </span><span class="kr">throw</span><span class="w">
</span><span class="p">}</span><span class="w">

</span><span class="n">Write-Output</span><span class="w"> </span><span class="s2">"AMA reinstallation and DCR association completed for VM: </span><span class="nv">$vmName</span><span class="s2">"</span><span class="w">
</span></code></pre></div></div>

<h2 id="復旧計画での実装手順">復旧計画での実装手順</h2>

<ol>
  <li><strong>Azure Automation アカウントの準備</strong>
    <ul>
      <li>Automation アカウントを作成</li>
      <li>必要な PowerShell モジュール（Az.Accounts、Az.Monitor など）をインポート</li>
      <li>システム割り当て Managed Identity を有効化し、適切な権限を付与</li>
    </ul>
  </li>
  <li><strong>Runbook の作成</strong>
    <ul>
      <li>上記のスクリプトを Runbook として作成</li>
      <li>パラメータを適切に設定</li>
    </ul>
  </li>
  <li><strong>復旧計画への組み込み</strong>
    <ul>
      <li>ASR の復旧計画でグループを作成</li>
      <li>フェールオーバー後のアクションとして Automation Runbook を追加</li>
      <li>必要なパラメータ（VM名、リソースグループ、DCR ID など）を設定</li>
    </ul>
  </li>
</ol>

<h2 id="注意事項">注意事項</h2>

<h3 id="linux-vm-の場合">Linux VM の場合</h3>

<p>Linux VM の場合は拡張機能の名前が異なるため、以下のように修正が必要です。</p>

<div class="language-powershell highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="c"># Linux の場合</span><span class="w">
</span><span class="n">Remove-AzVMExtension</span><span class="w"> </span><span class="nt">-Name</span><span class="w"> </span><span class="s2">"AzureMonitorLinuxAgent"</span><span class="w"> </span><span class="nt">-ResourceGroupName</span><span class="w"> </span><span class="nv">$resourceGroupName</span><span class="w"> </span><span class="nt">-VMName</span><span class="w"> </span><span class="nv">$vmName</span><span class="w"> </span><span class="nt">-Force</span><span class="w">
</span><span class="n">Set-AzVMExtension</span><span class="w"> </span><span class="nt">-ResourceGroupName</span><span class="w"> </span><span class="nv">$resourceGroupName</span><span class="w"> </span><span class="nt">-VMName</span><span class="w"> </span><span class="nv">$vmName</span><span class="w"> </span><span class="nt">-Name</span><span class="w"> </span><span class="s2">"AzureMonitorLinuxAgent"</span><span class="w"> </span><span class="nt">-Publisher</span><span class="w"> </span><span class="s2">"Microsoft.Azure.Monitor"</span><span class="w"> </span><span class="nt">-Type</span><span class="w"> </span><span class="s2">"AzureMonitorLinuxAgent"</span><span class="w"> </span><span class="nt">-TypeHandlerVersion</span><span class="w"> </span><span class="s2">"1.0"</span><span class="w"> </span><span class="nt">-Location</span><span class="w"> </span><span class="nv">$location</span><span class="w">
</span></code></pre></div></div>

<h3 id="複数の拡張機能がある場合">複数の拡張機能がある場合</h3>

<p>AMA 以外にも拡張機能を利用している場合は、それらも同様に再インストールが必要です。例えば：</p>

<ul>
  <li>Dependency Agent</li>
  <li>カスタム拡張機能</li>
</ul>

<p>これらも同様の手順で復旧計画に組み込むことができます。</p>

<h2 id="まとめ">まとめ</h2>

<p>ASR を利用する際は、拡張機能の制限事項を理解し、事前に復旧計画に組み込んでおくことが重要です。特に監視やセキュリティに関わる拡張機能は、DR 発動後も継続して動作させる必要があるため、自動化しておくことをお勧めします。</p>

<p>復旧計画と Azure Automation を活用することで、手動での作業を減らし、確実な復旧を実現することができます。定期的な DR テストの際に、拡張機能の動作確認も含めて実施することを忘れずに行いましょう。</p>]]></content><author><name>saiut</name></author><category term="DR" /><category term="Azure Site Recovery" /><category term="Azure Monitor Agent" /><summary type="html"><![CDATA[こんなことを書いています ASR のフェールオーバーは拡張機能の移行をサポートしていない AMA でログ取得している場合、フェールオーバー後はログが取得されなくなってしまう AMA の DCR を活用して、VM の再登録などを復旧計画に入れてしまうことを忘れずに]]></summary></entry><entry><title type="html">Logic Apps ワークフローのアクション分岐をまとめる</title><link href="https://tech.saiut.com/logicapps-control/" rel="alternate" type="text/html" title="Logic Apps ワークフローのアクション分岐をまとめる" /><published>2025-07-03T23:34:25+09:00</published><updated>2025-07-03T23:34:25+09:00</updated><id>https://tech.saiut.com/logicapps-control</id><content type="html" xml:base="https://tech.saiut.com/logicapps-control/"><![CDATA[<h2 id="こんなこと書いてます">こんなこと書いてます</h2>

<ul>
  <li>Logic Apps は既定でワークフローは順番で実行される</li>
  <li>分岐をさせる方法をまとめました</li>
</ul>

<!--more-->

<h2 id="分岐方法のいくつか">分岐方法のいくつか</h2>

<p>Logic Apps を利用してワークフローを実行させる場合、通常であれば順に沿って実行されます。</p>

<p>ただし、条件を付けて「特定の曜日の場合は実行させない」などといったことを実施したいことはあると思います。</p>

<p>その場合にどのような方法があるかをまとめました。</p>

<p>以下のような方法があります。</p>

<ul>
  <li>Conditional</li>
  <li>Switch</li>
  <li>Branches</li>
  <li>Loop</li>
  <li>Scopes</li>
</ul>

<h3 id="conditional">Conditional</h3>

<p>まずは Conditional、条件です。
その名の通り、条件に合致すればxxxする、合致しなければ△△△する、といった条件分岐です。</p>

<p>下記の例は「注文金額が10万円以上なら承認処理を呼び出す、10万円未満なら即時処理」です。</p>
<div class="language-json highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="nl">"actions"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
  </span><span class="nl">"CheckAmount"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
    </span><span class="nl">"type"</span><span class="p">:</span><span class="w"> </span><span class="s2">"If"</span><span class="p">,</span><span class="w">
    </span><span class="nl">"expression"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
      </span><span class="nl">"greaterOrEquals"</span><span class="p">:</span><span class="w"> </span><span class="p">[</span><span class="w">
        </span><span class="s2">"@int(body('GetOrder')?['amount'])"</span><span class="p">,</span><span class="w">
        </span><span class="mi">100000</span><span class="w">
      </span><span class="p">]</span><span class="w">
    </span><span class="p">},</span><span class="w">
    </span><span class="nl">"actions"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
      </span><span class="nl">"CallApproval"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
        </span><span class="nl">"type"</span><span class="p">:</span><span class="w"> </span><span class="s2">"ApiConnection"</span><span class="p">,</span><span class="w">
        </span><span class="nl">"inputs"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
          </span><span class="nl">"host"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
            </span><span class="err">/*</span><span class="w"> </span><span class="err">承認API接続情報</span><span class="w"> </span><span class="err">*/</span><span class="w">
          </span><span class="p">}</span><span class="w">
        </span><span class="p">}</span><span class="w">
      </span><span class="p">}</span><span class="w">
    </span><span class="p">},</span><span class="w">
    </span><span class="nl">"else"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
      </span><span class="nl">"actions"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
        </span><span class="nl">"AutoApprove"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
          </span><span class="nl">"type"</span><span class="p">:</span><span class="w"> </span><span class="s2">"Compose"</span><span class="p">,</span><span class="w">
          </span><span class="nl">"inputs"</span><span class="p">:</span><span class="w"> </span><span class="s2">"自動承認"</span><span class="w">
        </span><span class="p">}</span><span class="w">
      </span><span class="p">}</span><span class="w">
    </span><span class="p">}</span><span class="w">
  </span><span class="p">}</span><span class="w">
</span><span class="p">}</span><span class="w">
</span></code></pre></div></div>
<ul>
  <li>typeにIfを指定</li>
  <li>expressionで真偽を判定</li>
  <li>actionsにTrue時の処理、elseにFalse時の処理を記述</li>
</ul>

<h3 id="switch">Switch</h3>

<p>スイッチです。条件式に合致するかどうかを複数パターンに振り分けます。
下記の例はケースごとに新規通知・確認通知・その他通知をさせるような処理をしています。</p>

<div class="language-json highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="nl">"actions"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
  </span><span class="nl">"OrderStatusSwitch"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
    </span><span class="nl">"type"</span><span class="p">:</span><span class="w"> </span><span class="s2">"Switch"</span><span class="p">,</span><span class="w">
    </span><span class="nl">"expression"</span><span class="p">:</span><span class="w"> </span><span class="s2">"@body('GetOrder')?['status']"</span><span class="p">,</span><span class="w">
    </span><span class="nl">"cases"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
      </span><span class="nl">"New"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
        </span><span class="nl">"actions"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
          </span><span class="nl">"NotifyNew"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
            </span><span class="err">/*</span><span class="w"> </span><span class="err">新規通知処理</span><span class="w"> </span><span class="err">*/</span><span class="w">
          </span><span class="p">}</span><span class="w">
        </span><span class="p">}</span><span class="w">
      </span><span class="p">},</span><span class="w">
      </span><span class="nl">"Confirmed"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
        </span><span class="nl">"actions"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
          </span><span class="nl">"NotifyConfirmed"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
            </span><span class="err">/*</span><span class="w"> </span><span class="err">確認通知処理</span><span class="w"> </span><span class="err">*/</span><span class="w">
          </span><span class="p">}</span><span class="w">
        </span><span class="p">}</span><span class="w">
      </span><span class="p">}</span><span class="w">
    </span><span class="p">},</span><span class="w">
    </span><span class="nl">"default"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
      </span><span class="nl">"actions"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
        </span><span class="nl">"NotifyUnknown"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
          </span><span class="err">/*</span><span class="w"> </span><span class="err">その他通知処理</span><span class="w"> </span><span class="err">*/</span><span class="w">
        </span><span class="p">}</span><span class="w">
      </span><span class="p">}</span><span class="w">
    </span><span class="p">}</span><span class="w">
  </span><span class="p">}</span><span class="w">
</span><span class="p">}</span><span class="w">
</span></code></pre></div></div>
<ul>
  <li>casesでキーごとに処理を定義</li>
  <li>defaultでどのケースにも該当しない値をハンドリング</li>
</ul>

<h3 id="branches">Branches</h3>

<p>いわゆるパラレル処理、処理を並列で走らせ、処理の高速化や非同期実行を実現させます。
下記の例は、メール送信とログ記録を同時に行わせています。</p>

<div class="language-json highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="nl">"actions"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
  </span><span class="nl">"SendEmail"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
    </span><span class="nl">"type"</span><span class="p">:</span><span class="w"> </span><span class="s2">"Compose"</span><span class="p">,</span><span class="w">
    </span><span class="nl">"inputs"</span><span class="p">:</span><span class="w"> </span><span class="s2">"メール送信"</span><span class="p">,</span><span class="w">
    </span><span class="nl">"runAfter"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
      </span><span class="nl">"PreviousAction"</span><span class="p">:</span><span class="w"> </span><span class="p">[</span><span class="s2">"Succeeded"</span><span class="p">]</span><span class="w">
    </span><span class="p">}</span><span class="w">
  </span><span class="p">},</span><span class="w">
  </span><span class="nl">"LogApi"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
    </span><span class="nl">"type"</span><span class="p">:</span><span class="w"> </span><span class="s2">"Http"</span><span class="p">,</span><span class="w">
    </span><span class="nl">"inputs"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
      </span><span class="err">/*</span><span class="w"> </span><span class="err">ログ記録API</span><span class="w"> </span><span class="err">*/</span><span class="w">
    </span><span class="p">},</span><span class="w">
    </span><span class="nl">"runAfter"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
      </span><span class="nl">"PreviousAction"</span><span class="p">:</span><span class="w"> </span><span class="p">[</span><span class="s2">"Succeeded"</span><span class="p">]</span><span class="w">
    </span><span class="p">}</span><span class="w">
  </span><span class="p">}</span><span class="w">
</span><span class="p">}</span><span class="w">
</span></code></pre></div></div>
<ul>
  <li>Logic Apps には「Parallel」タイプは存在しない</li>
  <li>同じ runAfter の依存先を指定することで、複数アクションが並列実行される</li>
  <li>上記の例では SendEmail と LogApi が PreviousAction の後に同時に実行される</li>
</ul>

<h3 id="loop">Loop</h3>
<p>繰り返し処理です。Loop は For each と Until の 2 種類があります。</p>

<h4 id="for-each">For each</h4>
<p>配列内にある要素を処理します。 parallel で同時実行数を調整できます。
下記の例の場合は 5 回繰り返します。</p>

<div class="language-json highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="nl">"actions"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
  </span><span class="nl">"ForEachItem"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
    </span><span class="nl">"type"</span><span class="p">:</span><span class="w"> </span><span class="s2">"Foreach"</span><span class="p">,</span><span class="w">
    </span><span class="nl">"foreach"</span><span class="p">:</span><span class="w"> </span><span class="s2">"@body('GetList')"</span><span class="p">,</span><span class="w">
    </span><span class="nl">"actions"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
      </span><span class="nl">"ProcessItem"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
        </span><span class="nl">"type"</span><span class="p">:</span><span class="w"> </span><span class="s2">"Compose"</span><span class="p">,</span><span class="w">
        </span><span class="nl">"inputs"</span><span class="p">:</span><span class="w"> </span><span class="s2">"@item()"</span><span class="w">
      </span><span class="p">}</span><span class="w">
    </span><span class="p">},</span><span class="w">
    </span><span class="nl">"runtimeConfiguration"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
      </span><span class="nl">"concurrency"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
        </span><span class="nl">"repetitions"</span><span class="p">:</span><span class="w"> </span><span class="mi">5</span><span class="w">
      </span><span class="p">}</span><span class="w">
    </span><span class="p">}</span><span class="w">
  </span><span class="p">}</span><span class="w">
</span><span class="p">}</span><span class="w">
</span></code></pre></div></div>

<ul>
  <li>foreachで対象の配列を指定</li>
  <li>runtimeConfiguration.concurrency.repetitionsで同時実行数を設定</li>
</ul>

<h4 id="until">Until</h4>
<p>条件が満たされるまで繰り返します。無限ループを防ぐためにも limit や timeout を設定するといいでしょう。</p>

<div class="language-json highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="nl">"actions"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
  </span><span class="nl">"UntilLoop"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
    </span><span class="nl">"type"</span><span class="p">:</span><span class="w"> </span><span class="s2">"Until"</span><span class="p">,</span><span class="w">
    </span><span class="nl">"expression"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
      </span><span class="nl">"equals"</span><span class="p">:</span><span class="w"> </span><span class="p">[</span><span class="w">
        </span><span class="s2">"@variables('done')"</span><span class="p">,</span><span class="w">
        </span><span class="kc">true</span><span class="w">
      </span><span class="p">]</span><span class="w">
    </span><span class="p">},</span><span class="w">
    </span><span class="nl">"actions"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
      </span><span class="nl">"CheckStatus"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
        </span><span class="err">/*</span><span class="w"> </span><span class="err">ステータス確認処理</span><span class="w"> </span><span class="err">*/</span><span class="w">
      </span><span class="p">},</span><span class="w">
      </span><span class="nl">"Delay"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
        </span><span class="nl">"type"</span><span class="p">:</span><span class="w"> </span><span class="s2">"Wait"</span><span class="p">,</span><span class="w">
        </span><span class="nl">"inputs"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
          </span><span class="nl">"interval"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
            </span><span class="nl">"count"</span><span class="p">:</span><span class="w"> </span><span class="mi">10</span><span class="p">,</span><span class="w">
            </span><span class="nl">"unit"</span><span class="p">:</span><span class="w"> </span><span class="s2">"Second"</span><span class="w">
          </span><span class="p">}</span><span class="w">
        </span><span class="p">}</span><span class="w">
      </span><span class="p">}</span><span class="w">
    </span><span class="p">},</span><span class="w">
    </span><span class="nl">"limit"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
      </span><span class="nl">"count"</span><span class="p">:</span><span class="w"> </span><span class="mi">20</span><span class="p">,</span><span class="w">
      </span><span class="nl">"timeout"</span><span class="p">:</span><span class="w"> </span><span class="s2">"PT5M"</span><span class="w">
    </span><span class="p">}</span><span class="w">
  </span><span class="p">}</span><span class="w">
</span><span class="p">}</span><span class="w">
</span></code></pre></div></div>
<ul>
  <li>limitで最大試行回数</li>
  <li>timeoutで全体の実行上限時間</li>
</ul>

<h3 id="scopes">Scopes</h3>
<p>複数アクションをまとめて、成功・失敗時の後続処理を一括で設定します。</p>

<div class="language-json highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="nl">"actions"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
  </span><span class="nl">"TryScope"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
    </span><span class="nl">"type"</span><span class="p">:</span><span class="w"> </span><span class="s2">"Scope"</span><span class="p">,</span><span class="w">
    </span><span class="nl">"actions"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
      </span><span class="nl">"StepA"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w"> </span><span class="err">/*</span><span class="w"> </span><span class="err">処理A</span><span class="w"> </span><span class="err">*/</span><span class="w"> </span><span class="p">},</span><span class="w">
      </span><span class="nl">"StepB"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w"> </span><span class="err">/*</span><span class="w"> </span><span class="err">処理B</span><span class="w"> </span><span class="err">*/</span><span class="w"> </span><span class="p">}</span><span class="w">
    </span><span class="p">}</span><span class="w">
  </span><span class="p">},</span><span class="w">
  </span><span class="nl">"CatchScope"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
    </span><span class="nl">"type"</span><span class="p">:</span><span class="w"> </span><span class="s2">"Scope"</span><span class="p">,</span><span class="w">
    </span><span class="nl">"runAfter"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w"> </span><span class="nl">"TryScope"</span><span class="p">:</span><span class="w"> </span><span class="p">[</span><span class="s2">"Failed"</span><span class="p">]</span><span class="w"> </span><span class="p">},</span><span class="w">
    </span><span class="nl">"actions"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
      </span><span class="nl">"LogError"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w"> </span><span class="err">/*</span><span class="w"> </span><span class="err">エラーログ記録</span><span class="w"> </span><span class="err">*/</span><span class="w"> </span><span class="p">},</span><span class="w">
      </span><span class="nl">"NotifyAdmin"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w"> </span><span class="err">/*</span><span class="w"> </span><span class="err">管理者通知</span><span class="w"> </span><span class="err">*/</span><span class="w"> </span><span class="p">}</span><span class="w">
    </span><span class="p">}</span><span class="w">
  </span><span class="p">},</span><span class="w">
  </span><span class="nl">"FinallyScope"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
    </span><span class="nl">"type"</span><span class="p">:</span><span class="w"> </span><span class="s2">"Scope"</span><span class="p">,</span><span class="w">
    </span><span class="nl">"runAfter"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
      </span><span class="nl">"TryScope"</span><span class="p">:</span><span class="w"> </span><span class="p">[</span><span class="s2">"Succeeded"</span><span class="p">],</span><span class="w">
      </span><span class="nl">"CatchScope"</span><span class="p">:</span><span class="w"> </span><span class="p">[</span><span class="s2">"Succeeded"</span><span class="p">]</span><span class="w">
    </span><span class="p">},</span><span class="w">
    </span><span class="nl">"actions"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w">
      </span><span class="nl">"Cleanup"</span><span class="p">:</span><span class="w"> </span><span class="p">{</span><span class="w"> </span><span class="err">/*</span><span class="w"> </span><span class="err">後始末処理</span><span class="w"> </span><span class="err">*/</span><span class="w"> </span><span class="p">}</span><span class="w">
    </span><span class="p">}</span><span class="w">
  </span><span class="p">}</span><span class="w">
</span><span class="p">}</span><span class="w">
</span></code></pre></div></div>
<ul>
  <li>Scopeを3つ用意してTry/Catch/Finally構成を実現</li>
  <li>runAfterで実行条件をまとめて指定</li>
</ul>

<h2 id="まとめ">まとめ</h2>

<p>改めて、それぞれの分岐方法の紹介です。</p>

<ul>
  <li>Conditional：Ifタイプでシンプルに2択分岐</li>
  <li>Switch：複数ケースの振り分けに最適</li>
  <li>Branches：Parallelで並列実行を実現</li>
  <li>Loop：Foreach／Untilでバッチや条件付き繰り返し</li>
  <li>Scopes：Scope＋RunAfterでTry/Catch/Finallyを実装</li>
</ul>

<p>ワークフローで適切な分岐を選択することで、拡張性の高い設計が可能となります。</p>]]></content><author><name>saiut</name></author><category term="アプリケーション" /><category term="Logic Apps" /><summary type="html"><![CDATA[こんなこと書いてます Logic Apps は既定でワークフローは順番で実行される 分岐をさせる方法をまとめました]]></summary></entry><entry><title type="html">Application Gateway で「疑似」重みづけをしよう</title><link href="https://tech.saiut.com/appgw-omomi/" rel="alternate" type="text/html" title="Application Gateway で「疑似」重みづけをしよう" /><published>2024-06-22T23:34:25+09:00</published><updated>2024-06-22T23:34:25+09:00</updated><id>https://tech.saiut.com/appgw-omomi</id><content type="html" xml:base="https://tech.saiut.com/appgw-omomi/"><![CDATA[<h2 id="こんなことを書いています">こんなことを書いています</h2>

<ul>
  <li>Application Gateway では AFD や TM で可能な「トラフィックの重みづけでの負荷分散」ができない</li>
  <li>作りこみで「疑似」重みづけをやってみる</li>
</ul>

<!--more-->

<h2 id="afd-と-tm-でもいいんだけど">AFD と TM でもいいんだけど</h2>

<p>トラフィックの負荷分散で重みづけができるサービスは、Azure Front Door や Traffic Manager になります。
この 2 つのサービスはグローバルサービスになるので、特定のリージョンに依存せず、パブリックに公開されるサービスになります。</p>

<p>こうなると、もしパブリックに公開させたくない要件のあるシステムの場合は利用できないため、 AFD や TM は残念ながら利用できません。</p>

<p>L7 トラフィックの負荷分散を行うことが出来る Azure のサービスは Application Gateway になりますが、AppGW は重みづけをつけたトラフィックのルーティングができません。</p>

<p>今回は、Application Gateway を利用して疑似的にトラフィックの重みづけをする方法を考えてみます。</p>

<h2 id="思いついた方法-2-つ">思いついた方法 2 つ</h2>

<p>パッと思いつく方法はこんな形でしょうか。</p>

<ul>
  <li>VM 2 台のうち、VM2 をシャットダウンしておいて、VM1 側に障害があった際に立ち上げる</li>
</ul>

<p><img src="/assets/article_images/2024-06-22-appgw-omomi/VMshutdown.png" alt="architecture" /></p>

<ul>
  <li>AppGW で VM2 にもルーティングされるように設定しておき、普段は VM2 にルーティングされないように NSG をつけておいて、VM1 障害時に VM2 の NSG を外す</li>
</ul>

<p><img src="/assets/article_images/2024-06-22-appgw-omomi/nsg.png" alt="architecture2" /></p>

<p>両方とも不可能ではなさそうです。 VM1 側で障害を検知したら、VM2 を立ち上げる or VM2 NIC に付随の NSG を外すだけで OK ですからね。
ただし、VM2 を立ち上げるのと NSG を外す動作だと、NSG を外すほうが時間的にはかからないので、今回は後者の方法をとってみたいと思います。</p>

<h2 id="nsg-を外す">NSG を外す</h2>

<p>では、VM1 側に障害があった際に、VM2 の NSG を外して VM2 側にルーティングする方法を考えていきます。
今回の場合は 2 台なので、アラート発報の契機としては、AppGW の正常なホストの数でよさそうです。</p>

<p>AppGW では、メトリックとして正常なホスト数（Healthy Host Count）というのを取得していて、その正常なホストがなくなったときに VM2 についている NSG を外すようにします。</p>

<p>ちなみに正常「ではない」ホスト数に関しては Unhealthy Host Count というメトリックになります。</p>

<p><img src="/assets/article_images/2024-06-22-appgw-omomi/metric.png" alt="metric" /></p>

<p>上記の画像だと、2 台の正常なホストがいて、とあるタイミングで 1 台に異常があって正常なホストが 1 に減っています。</p>

<p>今回のやりたいことだと、2台構成の Active-Standby だと、正常なホスト数が1台で、それ以下になった場合はアラートが発生して VM2 が動作する流れになります。</p>

<p>アラート発生時に NSG を外すには、アラートのアクションとして Automation を利用して、アラート発生時に Automation が作動して NSG を外す流れです。</p>

<p>サンプルとしてはこのような形でしょうか</p>

<div class="language-powershell highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="nv">$AzureContext</span><span class="w"> </span><span class="o">=</span><span class="w"> </span><span class="n">Connect-AzAccount</span><span class="w"> </span><span class="nt">-Identity</span><span class="w">

</span><span class="c">## Place the network interface configuration into a variable. ##</span><span class="w">
</span><span class="nv">$nic</span><span class="w"> </span><span class="o">=</span><span class="w"> </span><span class="n">Get-AzNetworkInterface</span><span class="w"> </span><span class="nt">-Name</span><span class="w"> </span><span class="err">&lt;</span><span class="nx">nicname</span><span class="err">&gt;</span><span class="w"> </span><span class="nt">-ResourceGroupName</span><span class="w"> </span><span class="err">&lt;</span><span class="nx">RGname</span><span class="err">&gt;</span><span class="w">

</span><span class="c">## Remove the NSG to the NIC configuration. ##</span><span class="w">
</span><span class="nv">$nic</span><span class="o">.</span><span class="nf">NetworkSecurityGroup</span><span class="w"> </span><span class="o">=</span><span class="w"> </span><span class="bp">$null</span><span class="w">

</span><span class="c">## Save the configuration to the network interface. ##</span><span class="w">
</span><span class="nv">$nic</span><span class="w"> </span><span class="o">|</span><span class="w"> </span><span class="n">Set-AzNetworkInterface</span><span class="w">
</span></code></pre></div></div>

<p>NSG を外す NIC を指定し、その値を NULL とする = NSG を外すという方法です。
なので、あくまで NIC につけている NSG は、AppGW からのルーティングされない設定だけ追加（AppGW からの HTTP,HTTPS を受け付けない）しておき、その他セキュリティとして必要な NSG はサブネットの NSG で設定するようにしておきます。</p>

<h2 id="デメリット">デメリット</h2>

<p>大きなデメリットとしては、どうしても振り分けに時間がかかってしまうところでしょうか。</p>

<p>何度か試していたところ、 Healthy Host Count が減ったことを検知して、正常な VM 側の NSG を外すまである程度バラつきはありますが 5 分～7,8 分かかるといったところでしょうか。</p>

<p>また、今回の例で出している VM1 が正常に戻った場合のオペレーションも考える必要があります。</p>

<p>例えば VM1 が正常に戻った場合、 VM1 側に AppGW からの通信が急に流れることになります。これが問題なければ OK ですが、例えば VM1 側で受け付けるべきポートは空いてるけどサービスが立ち上がってないなどがある場合は VM1 側への通信がエラーとなるので、サービスとして通信を受け入れる準備が出来てから通信を流したいですよね。</p>

<p>その場合は例えば VM1 に AppGW からの通信をブロックする NSG をつけるなど対策を考える必要があります。</p>

<p>どうしても標準でない機能を無理くり実装することによってダウンタイムが出るなど考慮点は増えてしまうので、なるべく標準機能だけで実装していきたいですね。</p>]]></content><author><name>saiut</name></author><category term="ネットワーク" /><category term="Application Gateway" /><summary type="html"><![CDATA[こんなことを書いています Application Gateway では AFD や TM で可能な「トラフィックの重みづけでの負荷分散」ができない 作りこみで「疑似」重みづけをやってみる]]></summary></entry><entry><title type="html">Azure Update Manager のアップデート方法の違い</title><link href="https://tech.saiut.com/aum-update/" rel="alternate" type="text/html" title="Azure Update Manager のアップデート方法の違い" /><published>2024-04-16T23:34:25+09:00</published><updated>2024-04-16T23:34:25+09:00</updated><id>https://tech.saiut.com/aum-update</id><content type="html" xml:base="https://tech.saiut.com/aum-update/"><![CDATA[<h2 id="こんなことを書いています">こんなことを書いています</h2>

<ul>
  <li>Update Manager はパッチ更新管理に便利なサービスです</li>
  <li>パッチ適用のタイミングは様々なパターンがあるので注意</li>
</ul>

<!--more-->

<h2 id="azure-update-manager">Azure Update Manager</h2>

<p>Windows, Linux 双方とも大事な運用項目の1つとして挙げられるパッチ適用ですが、
Azure では Azure Update Manager（AUM）というサービスを利用して、「どの VM にどのパッチが適用されていないか」などを確認することが可能です。</p>

<p>AUM では、Resource Graph を用いて、VM や Arc 対応サーバーにある拡張機能からパッチの適用状況を引っ張ってきます。</p>

<p><img src="/assets/article_images/2024-04-16-aum-update/aum-architecture.png" alt="AUM Architecture" /></p>

<p>こちらから図を引用しています。：<a href="https://learn.microsoft.com/ja-jp/azure/update-manager/overview?tabs=azure-vms#key-benefits">Azure Update Manager について</a></p>

<p>パッチ適用状態の確認はオンデマンド/定期的に実行され、さらにパッチ適用もオンデマンド/定期的に実行可能です。</p>

<p>このうち、 <strong>パッチを適用する定期的なタイミング</strong> が様々存在しているので、そちらをまとめたいと思います。</p>

<h2 id="パッチ適用タイミングの色々">パッチ適用タイミングの色々</h2>

<p>大きく分けて 4 つあります。</p>

<table>
  <thead>
    <tr>
      <th>パッチオーケストレーション</th>
      <th>どのような挙動か</th>
    </tr>
  </thead>
  <tbody>
    <tr>
      <td>Customer Managed Schedules</td>
      <td>ユーザーが決めたスケジュールでパッチを適用する</td>
    </tr>
    <tr>
      <td>Azure マネージド - 安全なデプロイ</td>
      <td>Azure 側で自動的にパッチを適用する</td>
    </tr>
    <tr>
      <td>Windows 自動更新/イメージの既定値</td>
      <td>ゲスト OS 側の設定に任せる</td>
    </tr>
    <tr>
      <td>手動更新</td>
      <td>Windows OS 側も自動更新が無効になるため、自身で更新</td>
    </tr>
  </tbody>
</table>

<h3 id="customer-managed-schedules">Customer Managed Schedules</h3>

<p>その名の通り、ユーザー側で「いつパッチを適用していいか」というタイミングを決めて、そのタイミングでパッチを適用するという方法です。</p>

<p>追加方法は簡単で、AUM 概要から「スケジュールの更新」から設定します。</p>

<p><img src="/assets/article_images/2024-04-16-aum-update/schedule.png" alt="Schedule" /></p>

<p>リソースとして作成していきます。</p>

<ul>
  <li>メンテナンススコープは「ゲスト(Azure VM、Arc 対応 VM/サーバー)にする</li>
  <li>「再起動の設定」で、パッチ適用時に再起動してしまっていいか</li>
  <li>「スケジュール」で、いつから/メンテナンスする期間/期間を決定</li>
</ul>

<p><img src="/assets/article_images/2024-04-16-aum-update/add-schedule.png" alt="add-Schedule" /></p>

<p>次にどの VM を対象のスケジュールでパッチを当てるかを設定します。</p>

<p>動的スコープを利用することで、今後増えるだろう VM も抜け漏れなく Update Manager でパッチ適用管理が可能になります。</p>

<p>リソースの種類（VM, Arc 対応）やどのリージョンに所属する VM なのかなどを決めましょう。</p>

<p>静的に割り当てる場合は、動的スコープはスルーして、次の「リソース」タブでどの VM かを全て決めます。</p>

<p><img src="/assets/article_images/2024-04-16-aum-update/dynamicscope.png" alt="動的スコープ" /></p>

<p>次に、どのパッチを適用するかを決定します。 KB ID からも決めることが可能です。
<img src="/assets/article_images/2024-04-16-aum-update/patch.png" alt="パッチ" /></p>

<p>こういった形で、決められたスケジュールで決められた範囲のパッチを自動で適用できるようになります。</p>

<h3 id="azure-マネージド">Azure マネージド</h3>

<p>こちらを利用すると、以下に従って Azure 側が必要なパッチを適用します。</p>

<ul>
  <li>[重大] または [セキュリティ] に分類されているパッチは、自動的にダウンロードされ、VM に適用されます。</li>
  <li>パッチは、IaaS VM のピーク外の時間帯 (VM のタイムゾーン) に適用されます。</li>
  <li>VMSS Flex の場合、パッチはすべての時間に適用されます。</li>
  <li>パッチ オーケストレーションが Azure によって管理され、可用性優先の原則に従ってパッチが適用されます。</li>
  <li>プラットフォーム正常性シグナルによって特定された仮想マシンの正常性は、パッチ適用の失敗を検出するために監視されます。</li>
  <li>アプリケーションの正常性はアプリケーション正常性拡張機能を使って監視できます。</li>
  <li>すべての VM サイズで機能します。</li>
</ul>

<p>こちらからの引用です。
<a href="https://learn.microsoft.com/ja-jp/azure/virtual-machines/automatic-vm-guest-patching">Azure VM での VM ゲストの自動パッチ適用</a></p>

<p>その中で「可用性優先の原則」と記載がありますが、パッチ適用によって可用性が下がらないように担保するようにパッチ適用するよ、というものです。
以下のような原則があります。（あくまで一部ですがわかりやすいものを記載）</p>

<ul>
  <li>geo ペアリージョン（東日本と西日本みたいなペア）同時に更新しない</li>
  <li>異なる AZ にある VM が同時に更新されない</li>
  <li>共通の AS 内にある VM が同時に更新されない</li>
</ul>

<p>また、Azure マネージドの場合はパッチオーケストレーションモードが <strong>AutomaticByPlatform</strong> である必要があります。</p>

<p><a href="#パッチオーケストレーションモードの確認方法">パッチオーケストレーションモードの確認方法</a></p>

<h3 id="windows-自動更新イメージの既定値">Windows 自動更新/イメージの既定値</h3>

<p>こちらは非常に簡単で、OS 側の設定に任せる、という設定です。</p>

<ul>
  <li>Windows 自動更新： Windows OS のみ</li>
  <li>イメージの既定値： Linux OS のみ</li>
</ul>

<p>先ほどのパッチオーケストレーションモードの確認コマンドで確認した際には、以下のように出力されます。</p>

<ul>
  <li>Windows 自動更新： AutomaticByOS</li>
  <li>イメージの既定値： ImageDefault</li>
</ul>

<p>このパッチオーケストレーションモードは、特に他のモード設定をしていない場合に使用されます。</p>

<h3 id="手動更新">手動更新</h3>

<p>こちらは、Windows OS のみ対応しており、自動更新を無効にします。このモードは、自身でパッチを適用したり、WSUS など別の管理サービスを利用する際に使います。</p>

<p>パッチオーケストレーションモードは、 <strong>Manual</strong> です。</p>

<h3 id="パッチオーケストレーションモードの確認方法">パッチオーケストレーションモードの確認方法</h3>

<p>仮想マシン作成時の「管理」タブにある「ゲスト OS の更新プログラム」で選択可能です。こちらの場合は Azure マネージドが設定されています。（Azure-orchestrated using Automatic guest patching）
<img src="/assets/article_images/2024-04-16-aum-update/automaticbyplatform.png" alt="AutomaticByPlatform" /></p>

<p>また、以下のコマンドによって、対象 VM のパッチオーケストレーションモードを確認することが可能です。</p>

<div class="language-bash highlighter-rouge"><div class="highlight"><pre class="highlight"><code> az vm get-instance-view <span class="nt">--resource-group</span> &lt;rgname&gt; <span class="nt">--name</span> &lt;vmname&gt;
</code></pre></div></div>

<p><img src="/assets/article_images/2024-04-16-aum-update/cli-check.png" alt="CLI" /></p>

<h3 id="customer-managed-schedule-の注意点">Customer Managed Schedule の注意点</h3>

<p>Customer Managed Schedule でのスケジュールでの適用は便利ですが、スケジュールを外したときに、 VM の自動パッチ適用（Azure-orchestrated）によって、 <strong>意図しないタイミングで</strong> パッチが適用されてしまう可能性があります。</p>

<p>これを回避するために、 <strong>ByPassPlatformSafetyChecksOnUserSchedule</strong> という設定があります。
この設定が true になっている場合、スケジュールが設定されていない場合、自動でパッチ適用されることがなくなりますので、これはぜひ設定しておきましょう。転ばぬ先の杖というやつですね。</p>

<p>パッチオーケストレーションを確認しておきましょう。</p>

<p><img src="/assets/article_images/2024-04-16-aum-update/kokokara.png" alt="設定場所" /></p>

<p><img src="/assets/article_images/2024-04-16-aum-update/bypass.png" alt="ByPass" /></p>

<h2 id="まとめ">まとめ</h2>

<p>Azure Update Manger を利用することで、パッチ管理が Azure Portal 上で可能になります。
ただ、 WSUS のように「WSUS 自体がパッチをダウンロードし、それをクライアントにばら撒く」ようなことはせずに、あくまでパッチの適用状況の確認と、パッチを適用する場合は VM がインターネット経由で取得しにいくという点には注意です。</p>]]></content><author><name>saiut</name></author><category term="運用" /><category term="Azure Update Manager" /><summary type="html"><![CDATA[こんなことを書いています Update Manager はパッチ更新管理に便利なサービスです パッチ適用のタイミングは様々なパターンがあるので注意]]></summary></entry><entry><title type="html">Azure VM のディスク使用量を取得しよう</title><link href="https://tech.saiut.com/disk-usage-law/" rel="alternate" type="text/html" title="Azure VM のディスク使用量を取得しよう" /><published>2024-04-06T23:34:25+09:00</published><updated>2024-04-06T23:34:25+09:00</updated><id>https://tech.saiut.com/disk-usage-law</id><content type="html" xml:base="https://tech.saiut.com/disk-usage-law/"><![CDATA[<h2 id="こんなことを書いています">こんなことを書いています</h2>

<ul>
  <li>Azure のホストメトリックではディスク使用量/率は取得できない</li>
  <li>ディスク使用量はカスタムメトリックか Log Analytics にログとして送って取得しよう</li>
</ul>

<!--more-->

<h2 id="vm-のディスク使用量">VM のディスク使用量</h2>

<p>ディスクの IOPS や Read/Write といったディスクのパフォーマンスについては取得できるのですが、ディスク使用量は現状 VM のホストメトリックからは取得することができません。</p>

<p>ちなみに Azure 基盤側から VM のディスクの使用量まで取れないことに起因しています。</p>

<p>監視としてディスクの使用量が少なくなったなどは実施することは多いと思いますので、取得するようにしていきましょう。</p>

<p class="notice--info">VM ディスクのパフォーマンスをどう考えたらいいのか？については以下が非常に参考になります。
<a href="https://jpaztech.github.io/blog/vm/disk-metrics/">Azure VM のディスクパフォーマンス状況の確認方法について</a></p>

<p>2024/4現在、ディスクの使用量（空き容量）を取得するには、ゲスト VM 側の情報を取得する必要があります。</p>

<h2 id="カスタムメトリックを利用する">カスタムメトリックを利用する</h2>

<p>Azure 基盤側からみたメトリックではなく、ゲスト OS 側で取得できる「カスタムメトリック」を利用することで、ディスクの使用量を取得することが可能です。
別記事でカスタムメトリックを取得する方法を記載していますので、こちらを参考にしてカスタムメトリックを取得してください。</p>

<p><a href="/ama-custom-metric/">Azure VM のゲスト OS 上のパフォーマンスカウンターを気軽に取ってみる</a></p>

<p>Linux の場合は、「disk/used_percent」などで取得するといいでしょう。</p>

<p><img src="/assets/article_images/2024-04-06-disk-usage-law/linux-custom-metric.png" alt="Linux Free Disk Usage" /></p>

<p>Windows の場合は使用率ではなく、使用量なので「Free Space」を取得するといいかと。
（こちらの例では_totalで取得しており、全ディスクの空き容量を取得してしまっているので、それぞれのディスクを分けて取得したい場合は C,D,E など分けてカスタムメトリックを取得する必要があります）</p>

<p><img src="/assets/article_images/2024-04-06-disk-usage-law/windows-custom-metric.png" alt="Windows Free Space" /></p>

<h2 id="log-analytics-を利用する">Log Analytics を利用する</h2>

<p>もう1つの方法は Log Analytics に対してパフォーマンスカウンターなどのメトリックを飛ばし、Log Analytics からクエリを抽出する方法です。
カスタムメトリックを取得する方法と同じように、DCR を利用することでパフォーマンスカウンターを Log Analytics にデータを送信することが可能です。</p>

<p><a href="/ama-custom-metric/">Azure VM のゲスト OS 上のパフォーマンスカウンターを気軽に取ってみる</a></p>

<p>ゲスト OS のパフォーマンスデータを Log Analytics に送信できたら、このような形でクエリを打ちこんでみましょう</p>

<div class="language-powershell highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="c"># Linux の場合</span><span class="w">
</span><span class="n">Perf</span><span class="w">
 </span><span class="o">|</span><span class="w"> </span><span class="n">where</span><span class="w"> </span><span class="nx">CounterName</span><span class="w"> </span><span class="o">==</span><span class="w"> </span><span class="s2">"% Used Space"</span><span class="w">
 </span><span class="o">|</span><span class="w"> </span><span class="n">where</span><span class="w"> </span><span class="nx">InstanceName</span><span class="w"> </span><span class="o">==</span><span class="w"> </span><span class="s2">"/"</span><span class="w">
 </span><span class="o">|</span><span class="w"> </span><span class="n">where</span><span class="w"> </span><span class="nx">Computer</span><span class="w"> </span><span class="o">==</span><span class="w"> </span><span class="s2">"&lt;VM Name&gt;"</span><span class="w">
</span><span class="c"># Windows の場合</span><span class="w">
</span><span class="n">Perf</span><span class="w">
</span><span class="o">|</span><span class="w"> </span><span class="n">where</span><span class="w"> </span><span class="nx">Computer</span><span class="w"> </span><span class="o">==</span><span class="w"> </span><span class="s2">"&lt;VM Name&gt;"</span><span class="w">
</span><span class="o">|</span><span class="w"> </span><span class="n">where</span><span class="w"> </span><span class="nx">CounterName</span><span class="w"> </span><span class="o">==</span><span class="w"> </span><span class="s2">"% Free Space"</span><span class="w">
</span></code></pre></div></div>

<p><img src="/assets/article_images/2024-04-06-disk-usage-law/linux-law.png" alt="Linux Disk Law" /></p>

<p><img src="/assets/article_images/2024-04-06-disk-usage-law/windows-law.png" alt="Windows Disk Law" /></p>

<p>ディスクの使用量が取得できるはずです。</p>

<h2 id="アラートを設定したい場合">アラートを設定したい場合</h2>

<h3 id="log-analytics-の場合">Log Analytics の場合</h3>

<p>CounterValue で使用率が 80% を超えたら、などになると思いますので、</p>

<div class="language-powershell highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="n">CounterValue</span><span class="w"> </span><span class="err">&gt;</span><span class="o">=</span><span class="w"> </span><span class="mi">80</span><span class="w">
</span></code></pre></div></div>

<p>といったものを追加してあげて、アラートを設定してあげるといいでしょう。</p>

<h3 id="カスタムメトリックの場合">カスタムメトリックの場合</h3>

<p>特に考えることなく、対象のカスタムメトリックからアラートを作成してあげましょう。</p>

<p><img src="/assets/article_images/2024-04-06-disk-usage-law/metric-alert.png" alt="Metric Alert" /></p>]]></content><author><name>saiut</name></author><category term="監視" /><category term="Log Analytics" /><category term="Custom Metrics" /><summary type="html"><![CDATA[こんなことを書いています Azure のホストメトリックではディスク使用量/率は取得できない ディスク使用量はカスタムメトリックか Log Analytics にログとして送って取得しよう]]></summary></entry><entry><title type="html">Azure VM のゲスト OS 上のパフォーマンスカウンターを気軽に取ってみる</title><link href="https://tech.saiut.com/ama-custom-metric/" rel="alternate" type="text/html" title="Azure VM のゲスト OS 上のパフォーマンスカウンターを気軽に取ってみる" /><published>2024-03-19T14:34:25+09:00</published><updated>2024-03-19T14:34:25+09:00</updated><id>https://tech.saiut.com/ama-custom-metric</id><content type="html" xml:base="https://tech.saiut.com/ama-custom-metric/"><![CDATA[<h2 id="こんなことを書いています">こんなことを書いています</h2>

<ul>
  <li>データ収集ルールを使えば簡単に Azure VM 上のゲストメトリックが取得可能</li>
  <li>メトリックを Log Analytics Workspace に入れるまでもないときに活用</li>
</ul>

<!--more-->

<h2 id="カスタムメトリックの取得">カスタムメトリックの取得</h2>

<p>Azure VM では、仮想マシンの基盤から VM のメトリックを自動で取得してくれます。</p>

<p>ただ、あくまで基盤のメトリックなので VM 内部のメトリックは取得できません。カスタムメトリックを利用することで、ゲスト OS のメトリック（例えば Windows のパフォーマンスカウンター）を取得し、メトリックスエクスプローラーで確認が可能となります。</p>

<p>昔はもうちょっと面倒だったなーという記憶があるのですが、 Azure Monitor Agent がリリースされてデータ収集ルール（DCR）が使える現状では、
DCR を活用すれば簡単に取得することが可能です。</p>

<p class="notice--warning">AMA を利用したカスタムメトリクスはプレビュー機能です。なお、2024年8月のドキュメント更新により、<strong>この機能は一般提供（GA）されないことが公式に発表されています</strong>。今後は Azure Monitor ワークスペースでの Prometheus メトリックや OpenTelemetry を使用した収集が推奨されています。詳細は <a href="https://learn.microsoft.com/ja-jp/azure/azure-monitor/essentials/metrics-custom-overview">Azure Monitor のカスタム メトリック (プレビュー)</a> を参照してください。</p>

<hr />

<h2 id="dcr-からゲスト-os-のメトリックを取得する">DCR からゲスト OS のメトリックを取得する</h2>

<p>Azure Monitor の DCR を活用することで、DCR で設定した収集するデータ、データを収集する VM、送信先を簡単に管理することが可能です。</p>

<p><img src="/assets/article_images/2024-03-19-ama-custom-metric/dcr-datasource.png" alt="DCR Data Source" /></p>

<p>どのデータを取得するか</p>

<p><img src="/assets/article_images/2024-03-19-ama-custom-metric/dcr-resource.png" alt="DCR Resource" /></p>

<p>どの VM から設定したデータを取得するか</p>

<p>データソースについては、デフォルトではベーシックなものが選ばれています。
<img src="/assets/article_images/2024-03-19-ama-custom-metric/dcr-performancecounter.png" alt="DCR Resource" /></p>

<p>カスタムにすることで、細かく取得が可能になります。
<img src="/assets/article_images/2024-03-19-ama-custom-metric/dcr-performancecounter-custom.png" alt="DCR Resource Custom" /></p>

<h2 id="パフォーマンスカウンターは-_total-しかデフォルトでとれないので各プロセスのカウンターを取得する">パフォーマンスカウンターは _total しかデフォルトでとれないので各プロセスのカウンターを取得する</h2>

<p>カスタムで取得できるのは基本的にそれぞれのパフォーマンスで「_total」や「*」といった、全プロセスなどを足し合わせたものを取得するので、
例えば特定プロセスの CPU 使用率を取得したい場合はパフォーマンスカウンターを追加してあげる必要があります。</p>

<div class="language-text highlighter-rouge"><div class="highlight"><pre class="highlight"><code>\Process(プロセス名)\ % Processor Time
</code></pre></div></div>

<p>取得したいプロセス名を全部いれる必要があるので手間ではありますが。。。</p>

<p><img src="/assets/article_images/2024-03-19-ama-custom-metric/dcr-add-performance.png" alt="DCR Add Performance" /></p>

<p>設定してあげることで、VM のメトリック名前空間に「仮想マシンのゲスト」が追加され、そこから DCR で設定したパフォーマンスカウンターのメトリックを確認することが可能です。</p>

<p>こちらの例では、Azure の拡張機能である Network Watcher Agent のスレッド数を取得しています。</p>

<p><img src="/assets/article_images/2024-03-19-ama-custom-metric/custommetric.png" alt="Custom Metric" /></p>

<h2 id="appendix">Appendix</h2>

<p><a href="https://learn.microsoft.com/ja-jp/azure/azure-monitor/essentials/metrics-custom-overview">Azure Monitor のカスタム メトリック (プレビュー)</a></p>

<p><strong>2024年8月追記</strong>: 上記公式ドキュメントにて「カスタム メトリックの送信」機能が一般提供されないことが明記されました。代替手段として以下が推奨されています。</p>

<ul>
  <li><a href="https://learn.microsoft.com/ja-jp/azure/azure-monitor/essentials/prometheus-metrics-overview">Azure Monitor ワークスペースでの Prometheus メトリック収集</a></li>
  <li><a href="https://learn.microsoft.com/ja-jp/azure/azure-monitor/app/opentelemetry-overview">OpenTelemetry を使用したメトリック収集</a></li>
</ul>]]></content><author><name>saiut</name></author><category term="監視" /><category term="Azure Monitor Agent" /><category term="Custom Metrics" /><summary type="html"><![CDATA[こんなことを書いています データ収集ルールを使えば簡単に Azure VM 上のゲストメトリックが取得可能 メトリックを Log Analytics Workspace に入れるまでもないときに活用]]></summary></entry><entry><title type="html">Microsoft Entra Domain Services に Azure NetApp Files を接続するときにハマったこと</title><link href="https://tech.saiut.com/anf-entrads/" rel="alternate" type="text/html" title="Microsoft Entra Domain Services に Azure NetApp Files を接続するときにハマったこと" /><published>2024-03-13T23:34:25+09:00</published><updated>2024-03-13T23:34:25+09:00</updated><id>https://tech.saiut.com/anf-entrads</id><content type="html" xml:base="https://tech.saiut.com/anf-entrads/"><![CDATA[<h2 id="こんなことを書いています">こんなことを書いています</h2>

<ul>
  <li>ANF を SMB 接続する際にいきなりエラーになります</li>
  <li>Microsoft Entra Domain Services の設定を行うユーザーにも注意</li>
</ul>

<!--more-->

<h2 id="architecture">Architecture</h2>

<p>アーキテクチャはこのような構成図になります。
<img src="/assets/article_images/2024-03-13-anf-entrads/architecture.png" alt="Architecture" /></p>

<p>ANF のテナントと Entra Domain Services のテナントを分けていますが、深い意味はありません。
簡単に解説するとこのようなアーキテクチャです。</p>

<ul>
  <li>オンプレミスを模倣した左側の PC は、オンプレ AD に所属</li>
  <li>クライアント PC は SMB プロトコルで Entra DS に参加している ANF をマウント</li>
  <li>オンプレミス AD は Entra ID Connect 経由で Entra ID に同期</li>
  <li>Entra ID に同期されたユーザーは Entra Domain Services に同期される</li>
</ul>

<p>それぞれのサービスについては以下リンクを参照してください。</p>

<p><a href="https://learn.microsoft.com/ja-jp/entra/identity/domain-services/overview">Microsoft Entra Domain Services</a></p>

<p><a href="https://learn.microsoft.com/ja-jp/azure/azure-netapp-files/azure-netapp-files-introduction">Azure NetApp Files</a></p>

<h2 id="ハマったこと">ハマったこと</h2>

<p>Entra Domain Service は簡単にいうと「マネージドの Active Directory Domain Services」ですが、
マネージドなので ADDS とは異なる部分があります。
エンタープライズ管理者の特権がない、スキーマの拡張機能がないなど ADDS とは違う部分があるので、利用方法には注意が必要です。</p>

<p>比較についてはこちらをご確認ください。</p>

<p><a href="https://learn.microsoft.com/ja-jp/entra/identity/domain-services/compare-identity-solutions#domain-services-and-self-managed-ad-ds">セルフマネージド Active Directory Domain Services、Microsoft Entra ID、マネージド Microsoft Entra Domain Services を比較する</a></p>

<p>ANF を SMB で利用したい場合には、ANF を ADDS に所属する必要があります。</p>

<p><img src="/assets/article_images/2024-03-13-anf-entrads/connect-adds.png" alt="ADDS接続" /></p>

<p><a href="https://learn.microsoft.com/ja-jp/azure/azure-netapp-files/create-active-directory-connections">Azure NetApp Files の Active Directory 接続の作成と管理</a></p>

<p>その AD 接続を行った際に、Entra Domain Services ならではのハマったことがあったので、そちらを下記にいくつか記載します。</p>

<h3 id="entra-domain-service-の-addsdns-を見たい場合は-aad-dc-administrators-に所属しているユーザーでログイン">Entra Domain Service の ADDS/DNS を見たい場合は AAD DC Administrators に所属しているユーザーでログイン</h3>

<p>そもそも ANF をマウントする前に、Entra Domain Services の ADDS/DNS 機能を設定するには、Azure ポータルなどからは出来ず、別途 Entra Domain Services に接続できる VM などを構築する必要があります。</p>

<p>その際、対象の VM にログインするユーザーは AAD DC Administrators に所属している必要があります。</p>

<p>Entra ID でユーザーを作成してあげるか、ADDS で同期されてきた Entra ID に出来たユーザーに対して、 AAD DC Administrators に所属させてあげましょう。</p>

<p><img src="/assets/article_images/2024-03-13-anf-entrads/aaddcadministrators.png" alt="AAD DC Administrators" /></p>

<p>対象のユーザーで VM に対してログインし、 VM に ADDS のツールや DNS のツールをインストールして設定してあげましょう。
ちなみに DNS ツールを利用する際は、Entra ID に割り当てられた IP アドレスではなく、FQDN を利用しないといけないことに注意です。</p>

<h3 id="ptr-レコードを-entra-ds-環境の-dns-に入れる">PTR レコードを Entra DS 環境の DNS に入れる</h3>

<p>ADDS 接続を作成し、SMB ボリュームを作成する際、以下のエラーが発生しました。</p>

<div class="language-text highlighter-rouge"><div class="highlight"><pre class="highlight"><code>&gt;Failed to create the Active Directory machine account \"SMB-ANF-VOL. Reason: LDAP Error: Local error occurred Details: Error: Machine account creation procedure failed. [nnn] Loaded the preliminary configuration. [nnn] Successfully connected to ip 10.x.x.x, port 88 using TCP [nnn] Successfully connected to ip 10.x.x.x, port 389 using [nnn] Entry for host-address: 10.x.x.x not found in the current source: FILES. Ignoring and trying next available source [nnn] Source: DNS unavailable. Entry for host-address:10.x.x.x found in any of the available sources\n*[nnn] FAILURE: Unable to SASL bind to LDAP server using GSSAPI: local error [nnn] Additional info: SASL(-1): generic failure: GSSAPI Error: Unspecified GSS failure. Minor code may provide more information (Cannot determine realm for numeric host address) [nnn] Unable to connect to LDAP (Active Directory) service on contoso.com (Error: Local error) [nnn] Unable to make a connection (LDAP (Active Directory):contosa.com, result: 7643.
</code></pre></div></div>

<p>これは、ANF を AD 接続する際は、 PTR レコードが必要なために発生するエラーです。
あくまで検証環境なので、ADDS 環境はユーザーを作成したりするぐらいで、あまりいじっていなかったのが1つ原因かもしれません。
このエラーが発生した際は、 Entra Domain Services の DNS に AD サーバーの PTR レコードを登録してあげましょう。</p>

<h3 id="ou-の指定が-aaddc-computers">OU の指定が AADDC Computers</h3>

<p><img src="/assets/article_images/2024-03-13-anf-entrads/connect-adds.png" alt="ADDS接続" /></p>

<p>AD 接続設定時、「組織単位のパス」を入れます。
これは ANF 自体をどの OU に所属させるかという設定になります。
特に値を設定しない場合は CN=Computers を利用しますが、 Entra DS の場合は <em>OU=AADDC Computers</em> である必要があります。</p>

<p>エラーとしてはこんな感じに出てしまいます。</p>

<div class="language-json highlighter-rouge"><div class="highlight"><pre class="highlight"><code><span class="p">{</span><span class="w">
 </span><span class="nl">"code"</span><span class="p">:</span><span class="w"> </span><span class="s2">"DeploymentFailed"</span><span class="p">,</span><span class="w">
 </span><span class="nl">"message"</span><span class="p">:</span><span class="w"> </span><span class="s2">"At least one resource deployment operation failed. Please list deployment operations for details. Please see https://aka.ms/DeployOperations for usage details."</span><span class="p">,</span><span class="w">
 </span><span class="nl">"details"</span><span class="p">:</span><span class="w"> </span><span class="p">[</span><span class="w">
  </span><span class="p">{</span><span class="w">
   </span><span class="nl">"code"</span><span class="p">:</span><span class="w"> </span><span class="s2">"InternalServerError"</span><span class="p">,</span><span class="w">
   </span><span class="nl">"message"</span><span class="p">:</span><span class="w"> </span><span class="s2">"Error when creating - Failed to create the Active Directory machine account </span><span class="se">\"</span><span class="s2">SMBTESTAD-D9A2</span><span class="se">\"</span><span class="s2">. Reason: SecD Error: ou not found Details: Error: Machine account creation procedure failed</span><span class="se">\n</span><span class="s2"> [ 561] Loaded the preliminary configuration.</span><span class="se">\n</span><span class="s2"> [ 665] Successfully connected to ip 10.x.x.x, port 88 using TCP</span><span class="se">\n</span><span class="s2"> [ 1039] Successfully connected to ip 10.x.x.x, port 389 using TCP</span><span class="se">\n</span><span class="s2">**[ 1147] FAILURE: Specifed OU 'OU=AADDC Com' does not exist in</span><span class="se">\n</span><span class="s2">** contoso.com</span><span class="se">\n</span><span class="s2">. "</span><span class="w">
  </span><span class="p">}</span><span class="w">
 </span><span class="p">]</span><span class="w">
</span><span class="p">}</span><span class="w">
</span></code></pre></div></div>

<h3 id="aes-暗号化がされていない">AES 暗号化がされていない</h3>

<p>Entra DS では、Kerberos RC4 暗号化が利用できますが、既定では無効化されています。
特に設定をしていない場合、ANF の AD 接続時にAES 暗号化にチェックを入れておく必要があります。
以下のようなエラーが発生します。</p>

<div class="language-text highlighter-rouge"><div class="highlight"><pre class="highlight"><code>Failed to create the Active Directory machine account \"SMB-ANF-VOL\". Reason: Kerberos Error: KDC has no support for encryption type Details: Error: Machine account creation procedure failed [nnn]Loaded the preliminary configuration. [nnn]Successfully connected to ip 10.x.x.x, port 88 using TCP [nnn]FAILURE: Could not authenticate as 'contosa.com': KDC has no support for encryption type (KRB5KDC_ERR_ETYPE_NOSUPP)
</code></pre></div></div>

<h2 id="まとめ">まとめ</h2>

<p>今まで紹介したことが特に設定していない Entra DS に対して ANF の AD 接続を行う際にハマったことです。</p>

<p>上記に関しては、 ANF 側で AD 接続を行ったときには出ないエラーで、ボリューム作成時に SMB プロトコルで接続する設定を入れたときに発生するエラーなので、すぐには気付かず、
ボリューム作成時に「あれ？？」となるエラーになります。
なので、事前に上記のようなエラーとなりそうなものに対処してからボリューム接続に臨みましょう。</p>

<h2 id="appendix">Appendix</h2>

<p><a href="https://learn.microsoft.com/ja-jp/azure/azure-netapp-files/troubleshoot-volumes">Azure NetApp Files のボリュームに関するエラーをトラブルシューティングする</a></p>]]></content><author><name>saiut</name></author><category term="ストレージ" /><category term="Azure NetApp Files" /><category term="Entra Domain Services" /><summary type="html"><![CDATA[こんなことを書いています ANF を SMB 接続する際にいきなりエラーになります Microsoft Entra Domain Services の設定を行うユーザーにも注意]]></summary></entry><entry><title type="html">Virtual WAN で仮想ハブが相互接続されているときの VNet の動作</title><link href="https://tech.saiut.com/vwan-vhub-vnet/" rel="alternate" type="text/html" title="Virtual WAN で仮想ハブが相互接続されているときの VNet の動作" /><published>2024-03-10T23:34:25+09:00</published><updated>2024-03-10T23:34:25+09:00</updated><id>https://tech.saiut.com/vwan-vhub-vnet</id><content type="html" xml:base="https://tech.saiut.com/vwan-vhub-vnet/"><![CDATA[<h2 id="こんなことを書いています">こんなことを書いています</h2>

<ul>
  <li>同じ Virtual WAN 内の仮想ハブは暗黙で Peering が張られて、お互いの仮想ハブに接続されているネットワークは相互に通信が可能</li>
  <li>仮想ハブについては VNet を接続できるが、違う仮想ハブであれば同じ IP Range の VNet を接続できる</li>
  <li>接続できてしまうが、対象の VNet 同士は通信できないので注意</li>
  <li>同一仮想ハブ内であれば IP Range が被っていると接続できないとエラーが出るのに。。。</li>
</ul>

<!--more-->

<h2 id="virtual-wan">Virtual WAN</h2>

<p>Virtual WAN を活用することで、様々な場所から Azure への接続を 1 つの Hub にまとめることができます。
以下のようなものを、1 つの Virtual WAN にまとめてしまい、相互に接続することが出来るサービスです。</p>

<ul>
  <li>S2S VPN</li>
  <li>P2S VPN</li>
  <li>ExpressRoute</li>
  <li>VNet</li>
</ul>

<p>公式ドキュメントからの抜粋ですが、以下のような形になります。
<img src="/assets/article_images/2024-03-10-vwan-vhub-vnet/vwan-architecture.png" alt="VWAN-Architecture" /></p>

<p>大規模に様々な接続形態がある場合に使用されることが多い Virtual WAN ですが、
その中心にいるものが仮想ハブと言われるものです。</p>

<h2 id="複数の仮想ハブ">複数の仮想ハブ</h2>

<p>仮想ハブは同一リージョン内に複数作成することも可能で、仮想ハブ同士は特に設定を意識することなくピアリングされ推移的な接続がなされます。</p>

<p>ですので、オンプレミス - 仮想ハブA - 仮想ハブB - VNet C といった接続を設定なしで通信してくれるようになります。</p>

<p><img src="/assets/article_images/2024-03-10-vwan-vhub-vnet/onp-virtualhub-vnet.jpg" alt="OnP-VirtualHub-Vnet" /></p>

<p>VNet の追加は非常に簡単で、Virtual WAN の設定より「接続の追加」から VNet を追加するだけです。</p>

<p><img src="/assets/article_images/2024-03-10-vwan-vhub-vnet/vwan-add-vnet.jpg" alt="VWAN-add-VNet" /></p>

<p>VNet を追加すると、 VNet 側には自動で VNet Peering が追加されます。</p>

<p><img src="/assets/article_images/2024-03-10-vwan-vhub-vnet/vnet-peering.jpg" alt="VNet-Peering" /></p>

<p>もちろん 同じ仮想ハブ内で複数の VNet やオンプレミスのネットワークを接続する際、 VNet の IP Range が被っているとエラーがでます。</p>

<p><img src="/assets/article_images/2024-03-10-vwan-vhub-vnet/same_iprange.jpg" alt="Same-IP Range" /></p>

<hr />

<h2 id="vwan-で仮想ハブが複数存在する場合の-ip-range-には注意">VWAN で仮想ハブが複数存在する場合の IP Range には注意</h2>

<p>そりゃそうですが、VNet 同士の IP Range が重複している場合、お互いに通信できることはできません。
IP Range は管理されていることが多いので、重複が発生することはほぼないと思います。
しかし、例えば Virtual WAN はとある部署が管理していて、そこに接続するためのシステムが別部署で管理している場合に　IP Range が被ってしまうことが起こり得てしまうでしょう。</p>

<p>そんな時に何も考えずに 仮想ハブに VNet を繋いでいくと、こんな構成が取れてしまいます。
<img src="/assets/article_images/2024-03-10-vwan-vhub-vnet/vwan-same-ip-range.jpg" alt="VWAN-Same-Ip-Range" /></p>

<p>この場合、仮想ハブ A と仮想ハブ B に同じ 10.1.0.0/16 の IP Range を持つ VNet C と VNet D がありますが、
2 つの VNet 間はもちろん通信できません。</p>

<p>テストしてみると、VNet C と VNet D 以外の VNet （例えば 192.168.0.0/16）以外は通信可能なので、
なんでもかんでもとりあえずえいやで繋いでしまう構成はよくないってことがわかりますね。</p>

<h2 id="appendix">Appendix</h2>

<p>Azure VWAN のテストをしたい場合は以下のテンプレートを使うのがいいでしょう。</p>

<p><a href="https://learn.microsoft.com/ja-jp/samples/azure/azure-quickstart-templates/virtual-wan-with-all-gateways/">Azure Virtual WAN (vWAN) Multi-Hub Deployment</a></p>]]></content><author><name>saiut</name></author><category term="ネットワーク" /><category term="Virtual WAN" /><category term="VNet" /><summary type="html"><![CDATA[こんなことを書いています 同じ Virtual WAN 内の仮想ハブは暗黙で Peering が張られて、お互いの仮想ハブに接続されているネットワークは相互に通信が可能 仮想ハブについては VNet を接続できるが、違う仮想ハブであれば同じ IP Range の VNet を接続できる 接続できてしまうが、対象の VNet 同士は通信できないので注意 同一仮想ハブ内であれば IP Range が被っていると接続できないとエラーが出るのに。。。]]></summary></entry></feed>