次の方法で共有


Foundry Agent Service (Python) で App Service アプリをツールとして追加する

このチュートリアルでは、OpenAPI を使用して FastAPI アプリの機能を公開し、Foundry Agent Service にツールとして追加し、エージェントプレイグラウンドで自然言語を使用してアプリと対話する方法について説明します。

Web アプリケーションにショッピング、ホテル予約、データ管理などの便利な機能が既にある場合は、Foundry Agent Service の AI エージェントでそれらの機能を簡単に使用できます。 アプリに OpenAPI スキーマを追加するだけで、エージェントがユーザーのプロンプトに応答する際に、アプリの機能を理解して使用できるようになります。 つまり、アプリでできることはすべて、アプリ用の OpenAPI エンドポイントを作成するだけの最小限の労力で、AI エージェントでも実行できるということです。 このチュートリアルでは、シンプルなレストラン評価アプリから始めます。 最終的に、レストランの評価を確認することや、会話型 AI を通じてエージェントと新しいレストランや新しいレビューを作成することができるようになります。

OpenAPI ツールを使用してアクションを実行する会話中のエージェント プレイグラウンドを示すスクリーンショット。

  • Web アプリに OpenAPI 機能を追加します。
  • OpenAPI スキーマが Foundry Agent Service と互換性があることを確認します。
  • Foundry Agent Service でアプリを OpenAPI ツールとして登録します。
  • エージェントのプレイグラウンドでエージェントをテストします。

[前提条件]

このチュートリアルでは、「PostgreSQL を使用した Python FastAPI Web アプリを Azure にデプロイする」で使用したサンプルを利用することを前提としています。

少なくとも、GitHub Codespaces でサンプル アプリケーションを開き、azd up を実行してアプリをデプロイします。

GitHub codespaces で開く で開く

Web アプリに OpenAPI 機能を追加する

FasAPI には、既定のパス /openapi.json にある OpenAPI 機能が既に含まれています。 既存のコードにいくつか変更を加えるだけで、エージェントによるリモート呼び出しが可能になります。

  1. src/fastapi_app/app.py を開き、FastAPI アプリが宣言されている 24 行目を見つけます。 app = FastAPI() を次のコードに置き換えます。

    if os.getenv("WEBSITE_HOSTNAME"):
        server_url = f"https://{os.getenv('WEBSITE_HOSTNAME')}"
    else:
        server_url = "http://localhost:8000"
    app = FastAPI(
        title="Restaurant Review API",
        version="1.0.0",
        description="Can show restaurant ratings HTML and add new restaurants and reviews.",
        servers=[{"url": server_url}],
    )
    

    このコードを使用して、titledescription などのメタデータを OpenAPI スキーマに追加します。 最も重要なのは、API エンドポイントのサーバー URL を追加する点です。

  2. src/fastapi_app/app.py を開き、//details/{id} GET API に operation_id を追加します。 これら 2 つの API により、AI エージェントが解析できる HTML ドキュメントが返されます。 その他のすべての API に対して、include_in_schema=False パラメーターを追加します。

    @app.get("/", response_class=HTMLResponse, operation_id="getRestaurantsWithRatingsHtml")
        ...    
    
    @app.get("/create", response_class=HTMLResponse, include_in_schema=False)
        ...    
    
    @app.post("/add", response_class=RedirectResponse, include_in_schema=False)
        ...
    
    @app.get("/details/{id}", response_class=HTMLResponse, operation_id="getRestaurantDetails")
        ...    
    
    @app.post("/review/{id}", response_class=RedirectResponse, include_in_schema=False)
        ...
    

    include_in_schema=False を使用して GET /createPOST /addPOST /review/{id} を除外します。これらはフォームベースの機能の一部ですが、AI エージェントは JSON データを送信する必要があるためです。

  3. JSON を使用してレストランの追加機能とレビューの追加機能を追加するには、次のコードを追加します。

    from typing import Optional
    from fastapi import Body, HTTPException
    
    @app.post("/api/restaurants", response_model=Restaurant, status_code=status.HTTP_201_CREATED, operation_id="createRestaurant")
    async def create_restaurant_json(
        name: str = Body(...),
        street_address: str = Body(...),
        description: str = Body(...),
        session: Session = Depends(get_db_session),
    ):
        restaurant = Restaurant(name=name, street_address=street_address, description=description)
        session.add(restaurant)
        session.commit()
        session.refresh(restaurant)
        return restaurant
    
    
    @app.post("/api/restaurants/{id}/reviews", response_model=Review, status_code=status.HTTP_201_CREATED,operation_id="createReview")
    async def create_review_for_restaurant_json(
        id: int,
        user_name: str = Body(...),
        rating: Optional[int] = Body(None),
        review_text: str = Body(...),
        session: Session = Depends(get_db_session),
    ):
        if not session.get(Restaurant, id):
            raise HTTPException(status_code=status.HTTP_404_NOT_FOUND, detail="Restaurant not found")
    
        review = Review(
            restaurant=id, user_name=user_name, rating=rating, review_text=review_text, review_date=datetime.now()
        )
        session.add(review)
        session.commit()
        session.refresh(review)
        return review
    

    簡潔さと既存のサンプル アプリケーションとの整合性を考慮し、このコードでは作成 API のみを示しています。 必要に応じて、更新や削除などの他の API を追加することもできます。

  4. 次のコマンドを使用して、サンプル アプリの開発サーバーを起動します。

    python3 -m venv .venv
    source .venv/bin/activate
    pip install -r src/requirements.txt
    pip install -e src
    python3 src/fastapi_app/seed_data.py
    python3 -m uvicorn fastapi_app:app --reload --port=8000
    
  5. [ブラウザーで開く] を選択します。

  6. URL に /openapi.json を追加して OpenAPI スキーマを表示します。これは、FastAPI がスキーマを提供するために使用する既定のパスです。

  7. codespace ターミナルに戻り、変更をコミットして変更をデプロイするか (GitHub Actions メソッド)、azd up (Azure Developer CLI メソッド) を実行します。

  8. 変更がデプロイされたら、https://<your-app's-url>/openapi.json に移動し、後で使用できるようにスキーマをコピーします。

Microsoft Foundry でエージェントを作成する

これらの手順では、新しい Foundry ポータルを使用します。

  1. Foundry ポータルの右上のメニューで、[New Foundry] を選択します。

  2. 新しい Foundry ポータルでこれが初めての場合は、プロジェクト名を選択し、[ 新しいプロジェクトの作成] を選択します。

  3. プロジェクトに名前を付け、[ 作成] を選択します。

  4. [ ビルドの開始]、[ エージェントの作成] の順に選択します。

  5. エージェントに名前を付け、[ 作成] を選択します。 エージェントの準備ができたら、エージェント プレイグラウンドが表示されます。

    使用できるモデルと使用できるリージョンに注意してください。

  6. エージェントのプレイグラウンドで、[ ツール ] を展開し、[ 追加>Custom>OpenAPI ツール>Create を選択します。

  7. ツールに名前と説明を付けます。 OpenAPI 3.0 以降のスキーマ ボックスに、先ほどコピーしたスキーマを貼り付けます。

  8. [ 作成ツール] を選択します。

  9. 保存 を選択します。

ヒント

このチュートリアルでは、認証なしでアプリを匿名で呼び出すように OpenAPI ツールを構成します。 運用シナリオでは、マネージド ID 認証を使用してツールをセキュリティで保護する必要があります。 詳細な手順については、「 Foundry Agent Service の OpenAPI エンドポイントをセキュリティで保護する」を参照してください。

エージェントをテストする

  1. [手順] で、"restaurantReview ツールを使用してレストランのレビューを管理してください" などの簡単な手順を説明します。

  2. 次のプロンプト例を使用してエージェントとチャットします。

    • 「レストランのレビュー一覧を表示してください。」
    • 「レストランを作成してください。 詳細については想像力を働かせてください。」
    • 「このレストランの料理は好みではありませんでした。 2 つ星のレビューを作成してください。」

    OpenAPI ツールを使用してアクションを実行する会話の途中にあるエージェントのプレイグラウンドを示すスクリーンショット。プロンプトには、レストランのレビューの一覧が表示されます。

セキュリティのベスト プラクティス

Azure App Service で OpenAPI 経由で API を公開する場合は、次のセキュリティのベスト プラクティスに従ってください。

  • 認証と承認: Microsoft Entra 認証を使用して OpenAPI エンドポイントを保護します。 詳細な手順については、「 Foundry Agent Service の OpenAPI エンドポイントをセキュリティで保護する」を参照してください。 また、 Microsoft Entra ID を使用して Azure API Management の背後にあるエンドポイントを保護し、承認されたユーザーまたはエージェントのみがツールにアクセスできるようにすることもできます。
  • 入力データの検証: 無効な入力や悪意のある入力を防ぐために、受信データは常に検証します。 Python アプリの場合、Pydantic などのライブラリを使用して、専用の要求スキーマ モデル (RestaurantCreate や ReviewCreate など) でデータ検証規則を適用します。 ベスト プラクティスと実装の詳細については、付属のドキュメントを参照してください。
  • HTTPS を使用する: このサンプルは、既定で HTTPS を適用し、転送中のデータを暗号化するための無料の TLS/SSL 証明書を提供する Azure App Service を利用しています。
  • CORS を制限する: クロスオリジン リソース共有 (CORS) を信頼される側のドメインのみに制限します。 詳細については、「CORS を有効にする」を参照してください。
  • レート制限を適用する:API Management またはカスタム ミドルウェアを使用して、不正使用やサービス拒否攻撃を防ぎます。
  • 機密エンドポイントを非表示にする: OpenAPI スキーマで内部 API または管理 API を公開しないようにします。
  • OpenAPI スキーマを確認する: OpenAPI スキーマから機密情報 (内部 URL、シークレット、実装の詳細など) が漏えいしていないことを確認します。
  • 依存関係を最新の状態に保つ: NuGet パッケージを定期的に更新し、セキュリティ アドバイザリを監視します。
  • アクティビティの監視とログ: ログを有効にしてアクセスを監視し、疑わしいアクティビティを検出します。
  • マネージド ID を使用する: 他の Azure サービスを呼び出すときは、ハードコーディングされた資格情報ではなくマネージド ID を使用します。

詳細については、「App Service アプリをセキュリティで保護する」と「REST API のセキュリティのベスト プラクティス」を参照してください。

次のステップ

これで、App Service アプリを Foundry Agent Service のツールとして使用し、エージェントのプレイグラウンドで自然言語を使用してアプリの API と対話できるようになりました。 ここから、Foundry ポータルで引き続きエージェントに機能を追加したり、Microsoft Foundry SDK または REST API を使用して独自のアプリケーションに統合したり、大規模なソリューションの一部としてデプロイしたりできます。 Microsoft Foundry で作成されたエージェントは、クラウドで実行したり、チャットボットに統合したり、Web アプリやモバイル アプリに埋め込んだりすることができます。

次の手順に進み、Azure App Service 内でエージェントを直接実行する方法を学ぶには、次のチュートリアルを参照してください。

その他のリソース