aws-samples / bedrock-claude-chat

AWS-native chatbot using Bedrock + Claude (+Mistral)
MIT No Attribution
688 stars 232 forks source link

Feature: ReACT Agent [Frontend] #329

Closed k70suK3-k06a7ash1 closed 3 weeks ago

k70suK3-k06a7ash1 commented 1 month ago

Issue #, if available:

274 Frontend

コード量増えてきていたので、今回agent FE実装関連は features/agent 配下に、Component,Types、Libs、Hooksなどを配置する感じにしておりますmm

Description of changes:

By submitting this pull request, I confirm that you can use, modify, copy, and redistribute this contribution, under the terms of your choice.

k70suK3-k06a7ash1 commented 1 month ago
スクリーンショット 2024-05-29 14 27 39
k70suK3-k06a7ash1 commented 1 month ago

@statefb @wadabee レビューお願いします!

@wadabee 別件ですが、BotEditPageが肥大化してきており、リファクタリングしたいと考えております features/単位で複数のカスタムHooksと純粋関数に切り剥がしていこうと思っているのですが、方針や懸念点など相談させてくださいmm features/editBot/hooks/ features/editBot/libs/

statefb commented 1 month ago

ありがとうございます! descriptionについてですが、現在はLLMに理解させるためのdescriptionをそのまま返してしまっているので、専用の説明を返すべきかなとは思っています。一方でi18n対応をどうするかが悩ましいところです。

@wadabee @Yukinobu-Mine

statefb commented 1 month ago

backendのkeyだけ利用するi18nのindex.tsのイメージ(frontend側で独立して管理する)

{
  ...
  agent: {
    tools: [
      get_weather: {
        name: 天気取得ツール
        description: 現在の天気予報を取得します。
      }
    ]
  }
}

backend側で返却されたツールのうち、i18n.tsに定義がない場合はbackendから返却されたpayloadにfallbackするのはどうでしょうか。

wadabee commented 1 month ago

@k70suK3-k06a7ash1

別件ですが、BotEditPageが肥大化してきており、リファクタリングしたいと考えております features/単位で複数のカスタムHooksと純粋関数に切り剥がしていこうと思っているのですが、方針や懸念点など相談させてくださいmm features/editBot/hooks/ features/editBot/libs/

現状の構成では限界を迎えつつあるので、ぜひリファクタリングお願いします! 以下の方針でリファクタリングできたらと思っています。何かご意見ありましたらお願いします!

@statefb

backendのkeyだけ利用するi18nのindex.tsのイメージ(frontend側で独立して管理する)

上記の案に賛成です! この部分だけ英語のみというのは一貫性がないので、システムエラーメッセージ等を除きi18n対応したいです! 言語設定関係なく、keyが存在すればlocaleファイルを優先、なければAPIのpayloadを表示するというロジックでいいと思います!

statefb commented 1 month ago

forkして作業している人もいるので、できるだけ取り込みやすい修正とする 完全に救うことは不可能ですが、一気に数十ファイルがコンフリクトするような大規模リファクタリングだと心理的に辛いと思うので、徐々に進めていく

今回はメジャーアップデートなので、これを機会にするのも悪くないと思います(事実、backend側は結構手を入れてしまいました(しないと、例えばprivate hosted modelの追加の話が出てきており、今後しんどくなりそうだったので。frontendとbackendだとカスタマイズの大小も違うので一概には言えないかもしれませんが))

k70suK3-k06a7ash1 commented 1 month ago

thinkingのインタラクション実装忘れてたので、追加しますmm

wadabee commented 1 month ago

今回はメジャーアップデートなので、これを機会にするのも悪くないと思います

一気に修正すると、リファクタリングする側の負荷もあがってしまうので、その観点でも徐々に進めることでも良いかなと思います! (どこをリファクタリングするかによりますが、リグレッションテストがかなりしんどいと思います。。)

今回のリファクタリングを行う際に、既存の構成がツラミになってリファクタリング自体がやりづらいのであれば、範囲を広げてリファクタリングも全然問題ないと思います!

k70suK3-k06a7ash1 commented 1 month ago

https://ja.wikipedia.org/wiki/%E3%83%AD%E3%82%B8%E3%83%83%E3%83%88 ロジット曲線の計算式をもとに、Start、Progress、Endのうち、Progressの進捗率を高く見せ、UXに考慮する

指数分布の場合、Startの増加量が多く、Process部分でストレスになりそうなので(よくあるProgress前半は進捗が良いが、後半に進行が遅くなる体験)、不採用にしたい

k70suK3-k06a7ash1 commented 1 month ago

ロジスティック曲線も良さそう https://ja.wikipedia.org/wiki/%E3%83%AD%E3%82%B8%E3%82%B9%E3%83%86%E3%82%A3%E3%83%83%E3%82%AF%E6%96%B9%E7%A8%8B%E5%BC%8F

k70suK3-k06a7ash1 commented 1 month ago

@wadabee CC : @statefb

一点状態管理の観点で相談させてください

今回、AgentThinkingの状態管理としてStateMachineを定義できるXStateを使いたいと思ってます Delayed transitions

2023年のデータなので少し古いですが、シェアとしてはzustand,jotaiに次ぐ感じになっているようです

スクリーンショット 2024-05-30 10 17 30

See:https://www.ecomottblog.com/?p=12768

意図としては 今回Thinkingの進捗を累積分布関数を適用して計算することで、バックエンドから送られてくるdata.status===THINKING のカウント5で99に近似する関数で待機時間の体験を向上を目指しております 進捗の計算結果もStateMachineにまとめることで、関連する状態と値をStateMachineでグルーピングし、保守性も担保して実装したいと思っております

またAgentのThinkingがEndした場合に、進捗率をDelayed transitionsで100にする処理を追加しようと思ってます。Delayedを使うことで、カウント2などで推論が完了した場合の進捗率20%でSTREAMING_ENDした場合、突然回答が生成されるといった体験を回避できると考えております ※代替案:おそらくuseReduder or useState とuseEffect+setTimeoutで同等のことはできそうなイメージです。ただコードとしては読みにくく、useEffectを使って発火するので保守性も低くなる懸念があります・・・

ただ、以下二点懸念があり、許容できるレベルの内容なのか判断いただきたく・・・

上記、うまく言語化できてない箇所があるので、説明不足なところがあればご指摘いただきたいですmm

k70suK3-k06a7ash1 commented 1 month ago

Memo 時間軸における変化量を定義するのではなく、イベント発生の頻度を項とした累積分布関数を定義

k70suK3-k06a7ash1 commented 1 month ago
スクリーンショット 2024-05-30 14 38 16
k70suK3-k06a7ash1 commented 1 month ago
const logisticCurve = (x: number) => {
  const L = 1; // 最大値
  const k = 0.8; // 勾配を決定する定数
  const x0 = 3; // 中点
  return L / (1 + Math.exp(-k * (x - x0)));
};

export const progress = (thinkingCount: number) => {
  const percentage = logisticCurve(thinkingCount);
  const progressBlock = Math.floor(percentage * 10);
  const current = [...Array(progressBlock)].map((_) => '◼︎');
  const rest = [...Array(10 - progressBlock)].map((_) => '◻︎');

  return `Thinking Agent ${[...current, ...rest].join('')} ${Math.round(
    logisticCurve(thinkingCount) * 100
  )}%`;
};
k70suK3-k06a7ash1 commented 1 month ago

WIP agentの場合のみプログレスバーを表示する

k70suK3-k06a7ash1 commented 1 month ago

@wadabee CC : @statefb すいません、別件対応がありコード展開遅れました XStateでの実装イメージ以下のような感じになりますmm

補記 XStateのダイアグラムはVSCodeの拡張機能で出力できるので、ステートマシンの仕様理解をする上で認知コストが下がると思われますmm

スクリーンショット 2024-05-30 17 28 39
import { setup, assign } from 'xstate';

export type AgentThinkingEvent =
  | { type: 'wakeup' }
  | { type: 'thinking' }
  | { type: 'sleeping' };

export type AgentThinkingEventKeys = AgentThinkingEvent['type'];

export const agentThinkingState = setup({
  types: {
    context: {} as { count: number },
    events: {} as AgentThinkingEvent,
  },
  actions: {
    reset: assign({ count: () => 0 }),
    counter: assign({
      count: ({ context }) => context.count + 1,
    }),
    close: assign({
      count: () => 100,
    }),
  },
}).createMachine({
  /** @xstate-layout N4IgpgJg5mDOIC5QAoC2BDAxgCwJYDswBKAOlgBswwAHAYgHd0BrMAV2oG0AGAXUVGoB7WLgAuuQfn4gAHogCMAFi4kATAA55qxQGZd89V2U6ANCACeiVQHYVOgGzqAnKp2vH866oC+3s2iw8QlJMSVhMCVZYWlEgpgIobj4kECERcUlpOQRVex0SAFYndR0teWL7eXlTCysuFVcCrlUnapL5LicC338MHAJiElD8cMjoiipqBKTpNLEJKRTsnXVrQqLnIq43e3ttM0sc6zXK6wNFRQ11ewLrex6QAP7gkgAzAlxYbAB1QQAnJi0GSwUToURgEjoV7gv7IVRNLhEWhPIKDd74T4-f5MGYpOYZRagZardbFLpOba5PaKA6ITQkNwtJT2axOXZcdSKXx+ED4QQQODSFEDIizYTzTJLRAAWnstIQ0oKJCcKtVarVOgewpeExoYvSCyyiEu8vUStuBhsuR01kMNy1fVRITCEUEUX1EsJsisRQZBRZ1kUBQMrK4BRqhx09UKnWO8JZWk2DsCIreHy+vwBHoJRoQBVU8hIFxuKvqu0UWlN6hIXDOZqZ1Wqims3O8QA */
  context: {
    count: 0,
  },
  initial: 'sleep',
  states: {
    sleep: {
      on: {
        wakeup: {
          actions: 'reset',
          target: 'conscious',
        },
      },
    },
    conscious: {
      on: {
        thinking: [
          {
            actions: 'counter',
          },
        ],
        sleeping: {
          actions: 'close',
          target: 'finishWork',
        },
      },
    },
    finishWork: {
      after: {
        2500: { target: 'sleep' },
      },
    },
  },
});
k70suK3-k06a7ash1 commented 1 month ago

has_agentを追加したことによるBEテスト修正

wadabee commented 1 month ago
スクリーンショット 2024-05-30 14 38 16

Progress.tsxというプログレスバーを表示するコンポーネントがあるので、こちらをご利用ください! ボットのファイルのアップロード進捗表示に使っているものです

k70suK3-k06a7ash1 commented 1 month ago

InputTextChatContentの作成  ⇒画像関連のInterfaceが存在しない、Textのみのコンポーネントを別途作成   hasAgentの場合に分岐し、UserInterfaceとしてImageを受け付けない実装 ※既存コンポーネントを拡張すると肥大化するので、features/agent機能におけるInoutとして分離して作成する予定

k70suK3-k06a7ash1 commented 1 month ago

dispatch event のthinling をgo-on に変更

k70suK3-k06a7ash1 commented 1 month ago

sleeping thinking leaving の状態名に変更予定

(人格がある対象であり、かつ時間概念を加味した状態遷移を表現したい)

k70suK3-k06a7ash1 commented 1 month ago

Rule state は動名詞で定義 イベントは動詞で定義

k70suK3-k06a7ash1 commented 1 month ago

useSelector で状態を参照できるっぽい

k70suK3-k06a7ash1 commented 4 weeks ago
スクリーンショット 2024-06-03 15 48 10 スクリーンショット 2024-06-03 15 48 37
k70suK3-k06a7ash1 commented 4 weeks ago

@statefb @wadabee レビューお願いしますmm

k70suK3-k06a7ash1 commented 4 weeks ago

@statefb @wadabee 再レビューお願いします!