【Rails × OpenAI API】ChatGPTをアプリに組み込む方法（実装途中まで）


# 【Rails × OpenAI API】ChatGPTをアプリに組み込む方法（実装途中まで）

## 🔍 概要

今回は、OpenAI社が提供している**ChatGPTのAPI**を使って、生成AIチャット機能をRailsアプリに組み込む方法を学びました。  
従来のRailsアプリとは異なり、**クライアントからのリクエストに対して外部API（ChatGPT）を経由する構成**となるため、サーバーサイドの設計がやや特殊になります。

## 🎯 今回の目標（途中まで）

ユーザーが入力したテキスト（プロンプト）をChatGPT APIに送信し、返答を受け取るまでの流れを実装します。

## 🛠 実装ステップ（前半）

1. ページにアクセスできるようにルーティングとビューを作成  
2. フォームを作成し、ユーザーがテキスト（プロンプト）を送信できるようにする  
3. フォームの送信が `POST` リクエストとしてコントローラの `create` アクションに届くように設定  
4. `create` アクション内で、ChatGPT APIへリクエストを送信（Gem `http` を使用）

## 💡 JavaScriptの `fetch` とは？

`fetch()` は、JavaScriptでHTTPリクエストを送信するためのモダンなAPIです。  
古い `XMLHttpRequest` の後継で、よりシンプルに記述できます。

```js
fetch("/api/chat", {
  method: "POST",
  body: JSON.stringify({ prompt: "こんにちは" }),
  headers: {
    "Content-Type": "application/json",
    "Accept": "application/json"
  }
})
.then(response => response.json())
.then(data => {
  // データをビューに反映
})
.catch(error => {
  // エラーハンドリング
});
```

## 🌐 OpenAI Chat APIの構造

### ✅ エンドポイント
`https://api.openai.com/v1/chat/completions`

### ✅ リクエストに必要な項目

| パラメータ | 内容 |
|-----------|------|
| `model` | 使用するモデル（例：`gpt-3.5-turbo`） |
| `messages` | ユーザーとAIのやりとり履歴。例：`[{ role: "user", content: "こんにちは" }]` |
| `headers` | 認証情報やデータ形式の指定 |

#### headers の例

| ヘッダー名 | 値 | 説明 |
|------------|----|------|
| `Content-Type` | `application/json` | リクエストの形式 |
| `Accept` | `application/json` | 期待するレスポンス形式 |
| `Authorization` | `Bearer 秘密鍵` | OpenAI APIの認証キー |

## 🔐 APIキーの取得方法（OpenAI）

1. [OpenAI Platform](https://platform.openai.com/) にログイン  
2. 「API keys」タブに移動  
3. 「+ Create new secret key」で新規作成  
4. 発行されたキーを `.env` や `credentials.yml.enc` に保存して使用  

## 🧪 ChatGPT APIの呼び出し処理（Ruby）

```ruby
require 'http'

def openai_api_call(prompt)
  response = HTTP.headers(
    "Content-Type" => "application/json",
    "Authorization" => "Bearer #{ENV['OPENAI_API_KEY']}"
  ).post("https://api.openai.com/v1/chat/completions", json: {
    model: "gpt-3.5-turbo",
    messages: [
      { role: "user", content: prompt }
    ]
  })

  json = JSON.parse(response.body.to_s)
  json["choices"][0]["message"]["content"]
end
```

## 🗃 JSONレスポンスをどう扱う？

ChatGPT APIからのレスポンスはJSON形式で返されます。  
Railsでは `JSON.parse()` を使ってRubyのオブジェクトに変換（＝パース）します。

### 💡 補足：インスペクタ表現とは？

```ruby
#<Message:0x0000000111e26400>
```

このように表示されるのはRubyの**インスペクタ表現**です。  
オブジェクトの中身ではなく、メモリ上の構造を表しています。

## 🧩 APIレスポンス → クライアントへの返却

```ruby
render json: { response: @message.response }
```

これにより、JavaScript側が `response.response` としてChatGPTの返答を受け取れるようになります。

## 🖥 JavaScriptでビューに挿入する流れ

### 処理の流れ

1. `fetch()` でサーバーにPOSTリクエストを送る  
2. `then()` を使ってJSONをパース  
3. 画面に挿入（DOM操作）  
4. `catch()` でエラーハンドリング

```js
fetch("/api/chat", {
  method: "POST",
  headers: {
    "Content-Type": "application/json",
    "Accept": "application/json"
  },
  body: JSON.stringify({ prompt: "こんにちは" })
})
.then(response => response.json())
.then(data => {
  const answerBox = document.getElementById("chat-response");
  answerBox.textContent = data.response;
})
.catch(error => {
  console.error("エラーが発生しました：", error);
});
```

## 📌 用語まとめ

| 用語 | 意味 |
|------|------|
| プロンプト | ChatGPTに送信するテキスト |
| エンドポイント | APIが提供する特定のURL |
| fetch | JavaScriptでHTTPリクエストを送るAPI |
| then | 非同期処理の成功後に実行される関数チェーン |
| catch | 非同期処理の失敗時のエラーハンドリング |
| json() | レスポンスデータをJSON形式に変換するメソッド |
| パース（parse） | JSONをRubyオブジェクトやJSオブジェクトに変換する処理 |