しばやん雑記

Azure とメイドさんが大好きなプログラマーのブログ

Azure Container Apps Dynamic Sessions の MCP サポートを使って Code Interpreter を簡単に実現する

Ignite 2025 で発表された機能で個人的にかなり気になったのが Dynamic Sessions の MCP サポートです。これまでも LLM に Python コードを生成させて Dynamic Sessions で実行するという処理を書いたことはあるのですが、MCP として API が提供されているため簡単に Code Interpreter を組み込めるようになりました。

使い方は以下のブログが詳しいですが、Foundry Agent かつ Shell での利用なので若干ニッチな使い方をしています。今回はよりオーソドックスな Python で試してみます。

Dynamic Sessions を知らない方もいるとは思うので、詳細は以下のドキュメントを参照してください。ざっくり言うと Container Apps の実行基盤を利用して、サンドボックス環境下で Python などのコードを実行するサービスです。安全な環境でコードの実行が行えるので、LLM が生成したコードも安心して実行できます。

これまでは LLM に Python のコードを生成させて、その結果を Dynamic Sessions の API を経由して実行するという流れでしたが、MCP ツールとして提供されているので処理の途中に組み込むことや、コード生成を行って実行が必要なのかを LLM 側に判断させることが可能となりました。

現在 Dynamic Sessions の MCP を有効化するには ARM Template を使う必要があるため、以下のような Bicep を作成して ARM Template にコンパイルしてデプロイしました。

param name string = 'sessionpoolsample'

resource sessionPool 'Microsoft.App/sessionPools@2025-10-02-preview' = {
  name: name
  location: 'Japan East'
  properties: {
    poolManagementType: 'Dynamic'
    containerType: 'PythonLTS'
    scaleConfiguration: {
      maxConcurrentSessions: 5
    }
    sessionNetworkConfiguration: {
      status: 'EgressEnabled'
    }
    dynamicPoolConfiguration: {
      lifecycleConfiguration: {
        lifecycleType: 'Timed'
        cooldownPeriodInSeconds: 300
      }
    }
    mcpServerSettings: {
      isMcpServerEnabled: true
    }
  }
}
{
  "$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#",
  "contentVersion": "1.0.0.0",
  "metadata": {
    "_generator": {
      "name": "bicep",
      "version": "0.39.26.7824",
      "templateHash": "10140790373505388271"
    }
  },
  "parameters": {
    "name": {
      "type": "string",
      "defaultValue": "sessionpoolsample"
    }
  },
  "resources": [
    {
      "type": "Microsoft.App/sessionPools",
      "apiVersion": "2025-10-02-preview",
      "name": "[parameters('name')]",
      "location": "Japan East",
      "properties": {
        "poolManagementType": "Dynamic",
        "containerType": "PythonLTS",
        "scaleConfiguration": {
          "maxConcurrentSessions": 5
        },
        "sessionNetworkConfiguration": {
          "status": "EgressEnabled"
        },
        "dynamicPoolConfiguration": {
          "lifecycleConfiguration": {
            "lifecycleType": "Timed",
            "cooldownPeriodInSeconds": 300
          }
        },
        "mcpServerSettings": {
          "isMcpServerEnabled": true
        }
      }
    }
  ]
}

設定としては isMcpServerEnabledtrue にするだけなので非常に簡単です。ちなみに Japan East でも問題なく有効化して利用出来ています。

デプロイが完了すれば MCP のエンドポイントと API キーを取得すれば、各種 MCP に対応したクライアントから利用できます。エンドポイントは Azure Portal の JSON View から確認するのが一番楽です。

アクセスに必要な API キーは Azure CLI を使って直接 REST API を叩くしかないようなので、ブログにあるように以下のコマンドを実行して取得する必要があります。この辺りは Azure Portal から確認出来るようになって欲しいですね。既に RBAC でのアクセスも出来るようですが、設定が分からないので試してはいません。

az rest --method POST --uri "/subscriptions/$SUBSCRIPTION_ID/resourceGroups/$RESOURCE_GROUP/providers/Microsoft.App/sessionPools/$SESSION_POOL_NAME/fetchMCPServerCredentials?api-version=2025-10-02-preview" --query "apiKey" -o tsv

このコマンドで取得した API キーは x-ms-apikey というヘッダーで渡す必要があるので、GitHub Copilot Chat の場合は mcp.json ファイルで以下のように headers で API キーを指定すれば問題ありません。

{
	"servers": {
		"my-mcp-server-ddaf56e8": {
			"url": "https://japaneast.dynamicsessions.io/subscriptions/***/resourceGroups/***/sessionPools/***/mcp",
			"type": "http",
			"headers": {
				"x-ms-apikey": "***"
			}
		}
	}
}

設定後にサーバーを起動すれば以下のように 2 つの Dynamic Sessions MCP が提供するツールが確認出来ます。Dynamic Sessions は環境の作成と実行という二つの処理が必要なので、それぞれで MCP ツールが用意されているわけです。

それぞれの MCP ツールにはかなり長い説明が付けられているので、独自の MCP ツールを作る際の参考にもなりそうです。問題なくツールも認識されたので Copilot Chat から実行を試してみます。

ツールが正しく認識していれば、以下のようにコードの生成と実行までを自動的に行ってくれます。

Python コードの実行結果を確認すると、以下のように stdout に計算結果が出力されていることが確認出来ます。この結果を基に応答が生成されていることも同時に確認出来ます。

Dynamic Sessions は出力結果からわかるように stdoutstderr を返すようになっているので、生成されたコードが stdout に出力するようになっていないと、出力が空で返ってくるので注意が必要です。

明示的にコードの実行結果を stdout に出力するように指示する必要が出てくるケースもあります。この辺りはシステムプロンプトで定義しておくのが無難です。