> ## Documentation Index
> Fetch the complete documentation index at: https://docs.morph-data.io/llms.txt
> Use this file to discover all available pages before exploring further.

# チャットアプリを作成する

Morphでは、LLMのAPIを活用したチャットアプリを簡単に作成して、チームに共有することができます。

このチュートリアルでは、MorphのLLMコンポーネントとOpenAIのAPIを使用して、チャットアプリを作成します。

## 事前準備

このチュートリアルでは、事前に以下のコマンドを使用してパッケージをインストールしてください。

<CodeGroup>
  ```bash pip theme={"dark"}
  pip install openai
  ```

  ```bash poetry theme={"dark"}
  poetry add openai
  ```

  ```bash uv theme={"dark"}
  uv add openai
  ```
</CodeGroup>

OpenAIのAPIキーを事前にOpenAIのダッシュボードから取得して、`.env`ファイルに保存してください。

```shell .env theme={"dark"}
OPENAI_API_KEY=your_api_key
```

## 最終的な成果物

<img src="https://mintcdn.com/queue-4c50ebb3/evgQaQjX53Vch8Y5/assets/images/docs/tutorial/llm_chat_app.png?fit=max&auto=format&n=evgQaQjX53Vch8Y5&q=85&s=267db31c7296b45f990bf14719730b83" alt="chatbot" width="2983" height="1471" data-path="assets/images/docs/tutorial/llm_chat_app.png" />

## チュートリアル

`<Chat />`コンポーネントを使用して、LLMのAPIを活用したチャットアプリを作成します。
Python関数でLLMを用いたチャットアプリのロジックを実装し、`yield`を使用して、チャットのログをストリームで返することで、自動的に`<Chat />`がストリーミングの結果を表示します。

<Tabs>
  <Tab title="1. Python">
    OpenAIのSDKを使用して、ユーザーからの質問に回答するロジックを実装します。
    `<Chat />`コンポーネントの`postData`属性に指定された関数は`prompt`と`thread_id`を引数として受け取ります。

    * prompt: ユーザーから入力されたプロンプト
    * thread\_id: チャットスレッドのID。新しいスレッドが開かれると新しいIDが発行されます。

    ```python theme={"dark"}
    import os
    import morph
    from morph import MorphGlobalContext
    from openai import OpenAI

    @morph.func
    def llm_chat_app(context: MorphGlobalContext):
        client = OpenAI(api_key=os.getenv("OPENAI_API_KEY"))
        prompt = context.vars["prompt"]
        # thread_id can be used to identify the chat thread
        thread_id = context.vars["thread_id"]

        # chat
        messages = [{"role": "user", "content": prompt}]
        response = client.chat.completions.create(
            model="gpt-4o",
            messages=messages,
            stream=True,
        )

        for chunk in response:
            yield chunk.choices[0].delta.content

    ```
  </Tab>

  <Tab title="2. MDX(pages)">
    `<Chat />`コンポーネントの`postData`属性にPython関数を指定します。

    ```typescript theme={"dark"}
    export const title = "LLM Chat App"

    # Chat App

    <Chat postData="llm_chat_app" />

    ```
  </Tab>
</Tabs>
