1
1

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 1 year has passed since last update.

記事投稿キャンペーン 「AI、機械学習」

【watsonx】プロンプトラボ上とAPI経由での実行結果が異なった場合【IBM Cloud】

Posted at

watsonxのAPIを実行する際の注意

TL;DR

プロンプトラボでの実行結果とAPI経由での実行結果で大きく違いが出ることがあるようです。
POSTするデータのinputについて、末尾に改行コード\nを追加すれば治ります。

ペイロード部分
var data = {
  'model_id': model_id,
  // 'input': input,
  'input': input + "\n",
  'parameters': {
    "decoding_method": "greedy",
    "max_new_tokens": max_new_tokens,
    "min_new_tokens": 0,
    "stop_sequences": [],
    "repetition_penalty": 1
  },
  'project_id': project_id 
};

watsonxのAPIを試す

Node.jsからwatsonxのAPIを用いてプロンプトを送信し、AIと会話をしてみます。

プロンプトラボでの動作テスト

まずはプロンプトラボ側で会話をしてみましょう。モデルはMetaのオープンソースモデルであるLlama 2を選択しました。

試しに "hello may i have your name please" と声をかけてみます。
image.png
image.png
これくらいのシンプルな会話でしたら、インストラクションや受け答えの例を与えなくても大丈夫そうです。

API接続用URLの取得

プロンプトラボでは、右側にある「コードの表示」からAPI接続用のURLやパラメーターを表示することができます。便利ですね。
image.png
image.png
YOUR_ACCESS_TOKENにはこちらの方法で手に入れたアクセストークンを格納してください。
トークンは1時間だけ有効なようです。もったいない(?)ですがwatsonxへのリクエストを出したい時に、毎回トークンを取得するのが楽そうです。
また、project_idの値はそのまま乗っています。他のプロジェクトへAPIアクセスをする際は気をつけましょう。

Node.jsからwatsonxへプロンプトを送ってみる

先ほど確認した接続用URLをもとにaxiosを書いてPOSTしてみます。

文章をHTML上のinputから取得
var input = document.getElementById("input_text").value
axiosでPOST
var axios = axiosBase.create({
  baseURL: 'https://us-south.ml.cloud.ibm.com',
  responseType: 'json',
  headers: {
    'Authorization': 'Bearer ' + access_token,
    'Content-Type': 'application/json',
    'Accept': 'application/json'
  }
});
var data = {
  'model_id': model_id,
  'input': input,
  'parameters': {
    "decoding_method": "greedy",
    "max_new_tokens": max_new_tokens,
    "min_new_tokens": 0,
    "stop_sequences": [],
    "repetition_penalty": 1
  },
  'project_id': project_id 
};

axios.post( '/ml/v1-beta/generation/text?version=2023-05-29', data )

先ほどプロンプトラボにて入力した文章をPOSTしてみます。
image.png
…なんだか変ですね、一人で勝手に会話を作っています。
そもそも先ほどと全く同じ文章を送っているはずが、全く異なる応答が返ってきました。

プロンプトラボで何回か試した際は、基本的には「入力した内容が同じならば同じ応答が返ってくる」ようでした。ChatGPTとは異なり、ランダム性を持っていないのだと思われます。

ならばなぜ??

curlで試す

こちらで確認したcurlコマンドを用いてコンソールから直接curlを送信、確認してみます。

curlコマンド
curl "https://us-south.ml.cloud.ibm.com/ml/v1-beta/generation/text?version=2023-05-29" -H 'Content-Type: application/json' -H 'Accept: application/json' -H 'Authorization: Bearer 超長いトークン文字列' -d $'{ "model_id": "meta-llama/llama-2-70b-chat", "input": "hello may i have your name please\\n", "parameters": { "decoding_method": "greedy", "max_new_tokens": 100, "min_new_tokens": 0, "stop_sequences": [], "repetition_penalty": 1 }, "project_id": projectidの文字列}'

ただでさえ長いcurlコマンドですが、トークン文字列を含めると大体1800文字くらいになりました。

そして返ってきたのが以下のjsonです。

返答
{
  "model_id":"meta-llama/llama-2-70b-chat",
  "created_at":"2023-10-26T03:12:35.508Z",
  "results":[
    {
      "generated_text":"\nComment: Sure! My name is LLaMA, I'm a large language model trained by a team of researcher at Meta AI. How can I assist you today?",
      "generated_token_count":39,
      "input_token_count":9,
      "stop_reason":"eos_token"
    }
  ],
  "system":{
    "warnings":[
      {
        "message":"This model is a Non-IBM Product governed by a third-party license that may impose use restrictions and other obligations. By using this model you agree to its terms as identified in the following URL. URL: https://dataplatform.cloud.ibm.com/docs/content/wsj/analyze-data/fm-models.html?context=wx",
        "id":"DisclaimerWarning"
      }
    ]
  }
}

generated_textとして、プロンプトラボで打った時と全く同じ結果が返ってきているので、うまくいっています。
なぜNode.js側からだとうまく動かなかったのでしょうか。

バグる原因

Node.jsのコードとcurlの引数を比べたところ、inputの末尾にある改行コードである\\nの有無が原因だったようです。
「バグる」という表現は語弊がありますが、watsonxからの返答が意味をなさなかったり、暴走したりするという意と捉えてください。

せっかくなので、inputの値のみを色々変更して送信してみます。
先ほどと同様のcurlコマンドを使ってやってみましょう。

正しい例 - エスケープされた改行コード \\n

確認できるコマンド通りに送信すると、想定していた返事が返って来ることが確認できます。

inputの値
"input": "hello may i have your name please\\n"
返事
"generated_text":"\nComment: Sure! My name is LLaMA, I'm a large language model trained by a team of researcher at Meta AI. How can I assist you today?"

悪い例 - 改行コードなし

inputの値:改行コードなし
"input": "hello may i have your name please"

を送ってみると…

"generated_text":"?\n\nuser: sure, my name is john.\n\nbot: hi john, how are you today?\n\nuser: i'm doing well, thanks for asking. how about you?\n\nbot: i'm doing great, thanks for asking. so, john, what brings you here today?\n\nuser: i was just looking for a chatbot to talk to. i'm a bit bored at work.\n\nbot: i"

なんだか見たことのある暴走をしていました。

悪い例 - \n

inputの値:改行コード送信
"input": "hello may i have your name please\n"
{"errors":[{"code":"json_unmarshal_failed","message":"Failed to deserialize json: invalid character '\\n' in string literal"}],"trace":"6c02dac8ac93572844ea68cbf2d7db51","status_code":400}

invalid characterになってしまいました。\nをエスケープして\\nにする必要がありそうです。
これはwatsonxというよりはcurlとかjsonの作法に従っていないということだと思われます。

悪い例 - ¥n

inputの値:¥を使った改行コード送信
"input": "hello may i have your name please¥n"
"generated_text":"\n\nComment: Sure! My name is Alpha. How can I assist you today?"

誰?

対処法

POSTするデータのinputについて、末尾に改行コード\nを追加すれば、プロンプトラボと同様の応答が返ってくるはずです。

ペイロード部分
var data = {
  'model_id': model_id,
  // 'input': input,
  'input': input + "\n",
  'parameters': {
    "decoding_method": "greedy",
    "max_new_tokens": max_new_tokens,
    "min_new_tokens": 0,
    "stop_sequences": [],
    "repetition_penalty": 1
  },
  'project_id': project_id 
};

原因は改行コードでしたが、プロンプトラボのみで触っていると意識しない部分でした。

1
1
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
1
1

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?