@xpert-ai/chatkit-ui 0.1.1 → 0.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (337) hide show
  1. package/dist/app/assets/{_baseUniq-p9H3Gzep.js → _baseUniq-U3ZlyosM.js} +1 -1
  2. package/dist/app/assets/{abap-bJX3iBqH.js → abap-8X6m4nc9.js} +1 -1
  3. package/dist/app/assets/{abnf-BoiZ35EE.js → abnf-B9FqRK4Q.js} +1 -1
  4. package/dist/app/assets/{actionscript-D-H9vZ8b.js → actionscript-BRiggmYG.js} +1 -1
  5. package/dist/app/assets/{ada-Bne3WpOl.js → ada-FFsIKz3W.js} +1 -1
  6. package/dist/app/assets/{agda-C938cagi.js → agda-CSry7vG2.js} +1 -1
  7. package/dist/app/assets/{al-Dcxw3Vj0.js → al-B86I55sd.js} +1 -1
  8. package/dist/app/assets/{antlr4-uTm2QqyV.js → antlr4-DLdIrmfn.js} +1 -1
  9. package/dist/app/assets/{apacheconf-D52D513G.js → apacheconf-CyFZwC58.js} +1 -1
  10. package/dist/app/assets/{apex-B76H7J4g.js → apex-DMVXQx7B.js} +1 -1
  11. package/dist/app/assets/{apl-CzLk42pF.js → apl-CvxzOn3f.js} +1 -1
  12. package/dist/app/assets/{applescript-Dx8Ig-Eo.js → applescript-D9BsJ4nv.js} +1 -1
  13. package/dist/app/assets/{aql-wjx32tAU.js → aql-Du46VsVP.js} +1 -1
  14. package/dist/app/assets/{arc-B32_yhh0.js → arc-Cgg2Li2V.js} +1 -1
  15. package/dist/app/assets/{architectureDiagram-Q4EWVU46-Ba-C8DAI.js → architectureDiagram-Q4EWVU46-3DQlJdjW.js} +1 -1
  16. package/dist/app/assets/{arduino-BwKDxTSS.js → arduino-Bsv1YPmE.js} +1 -1
  17. package/dist/app/assets/{arff-DrkRViyY.js → arff-CJK1I_i3.js} +1 -1
  18. package/dist/app/assets/{asciidoc-BGLZq9v8.js → asciidoc-DxmnfpMK.js} +1 -1
  19. package/dist/app/assets/{asm6502-MsEWIyJj.js → asm6502-B-ig6A0r.js} +1 -1
  20. package/dist/app/assets/{asmatmel-CeHxqS5T.js → asmatmel-DlH3PvMo.js} +1 -1
  21. package/dist/app/assets/{aspnet-CmsQfR5a.js → aspnet-D8iv0Uvb.js} +1 -1
  22. package/dist/app/assets/{autohotkey-Cusm-zTm.js → autohotkey-B0J5KM1J.js} +1 -1
  23. package/dist/app/assets/{autoit-Da8gsEm-.js → autoit-DjZ-C8Ct.js} +1 -1
  24. package/dist/app/assets/{avisynth-C46xLzyo.js → avisynth-DBwstp_C.js} +1 -1
  25. package/dist/app/assets/{avro-idl-D2WmoYBG.js → avro-idl-D2NmTxDF.js} +1 -1
  26. package/dist/app/assets/{bash-BrsKn3za.js → bash-CaYF0XP6.js} +1 -1
  27. package/dist/app/assets/{basic-Dt5oGQ8B.js → basic-CmOS0BPn.js} +1 -1
  28. package/dist/app/assets/{batch-DtrIlfXi.js → batch-0uLA_1q6.js} +1 -1
  29. package/dist/app/assets/{bbcode-BWYlAYoE.js → bbcode-DofDtehq.js} +1 -1
  30. package/dist/app/assets/{bicep-C4sxks0f.js → bicep-Csi6HiBf.js} +1 -1
  31. package/dist/app/assets/{birb-gYyyIZ-F.js → birb-wpSYHdbW.js} +1 -1
  32. package/dist/app/assets/{bison-or-umhj6.js → bison-B_ycJmsC.js} +1 -1
  33. package/dist/app/assets/{blockDiagram-DXYQGD6D-5oqbPp8P.js → blockDiagram-DXYQGD6D-C5FR_JeB.js} +1 -1
  34. package/dist/app/assets/{bnf-BQR7hfk2.js → bnf-BFkvwiYp.js} +1 -1
  35. package/dist/app/assets/{brainfuck-DkQqhNHv.js → brainfuck-CKXec9xF.js} +1 -1
  36. package/dist/app/assets/{brightscript-rGhg0HBT.js → brightscript-da2DAp0M.js} +1 -1
  37. package/dist/app/assets/{bro-CIgtBg0f.js → bro-CMEOqxCO.js} +1 -1
  38. package/dist/app/assets/{bsl-C4geIkQv.js → bsl-CcPijGZ5.js} +1 -1
  39. package/dist/app/assets/{c-Cw5181Rv.js → c-ypihM29I.js} +1 -1
  40. package/dist/app/assets/{c4Diagram-AHTNJAMY-BKyN5n0Y.js → c4Diagram-AHTNJAMY-CVQ-YBVO.js} +1 -1
  41. package/dist/app/assets/{cfscript-DHPNMvWS.js → cfscript-57UtmCol.js} +1 -1
  42. package/dist/app/assets/{chaiscript-Cd8c0hJ8.js → chaiscript-Bzv7uMwl.js} +1 -1
  43. package/dist/app/assets/channel-QFEl2WH8.js +1 -0
  44. package/dist/app/assets/{chunk-4BX2VUAB-CfLubn_X.js → chunk-4BX2VUAB-Dxfd4JRQ.js} +1 -1
  45. package/dist/app/assets/{chunk-4TB4RGXK-Bhehm3S4.js → chunk-4TB4RGXK-0tBP8iWY.js} +1 -1
  46. package/dist/app/assets/{chunk-55IACEB6-D0Zgi2qX.js → chunk-55IACEB6-C6Of3RNV.js} +1 -1
  47. package/dist/app/assets/{chunk-EDXVE4YY-DzMULs0l.js → chunk-EDXVE4YY-D9VnbCF6.js} +1 -1
  48. package/dist/app/assets/{chunk-FMBD7UC4-CEU9agAN.js → chunk-FMBD7UC4-C-jb70xY.js} +1 -1
  49. package/dist/app/assets/{chunk-OYMX7WX6-C-avxOs6.js → chunk-OYMX7WX6-DHv4g2zF.js} +1 -1
  50. package/dist/app/assets/{chunk-QZHKN3VN-C66xsvBW.js → chunk-QZHKN3VN-BVJ1du8l.js} +1 -1
  51. package/dist/app/assets/{chunk-YZCP3GAM-DZlwMcoL.js → chunk-YZCP3GAM-C9v1WHTx.js} +1 -1
  52. package/dist/app/assets/{cil-L3oWT8Nl.js → cil-D9cVdpCd.js} +1 -1
  53. package/dist/app/assets/classDiagram-6PBFFD2Q-CUn8MbgR.js +1 -0
  54. package/dist/app/assets/classDiagram-v2-HSJHXN6E-CUn8MbgR.js +1 -0
  55. package/dist/app/assets/{clike-CHF9NJQa.js → clike-M17MKmCg.js} +1 -1
  56. package/dist/app/assets/{clojure-YgRWUbgr.js → clojure-BP9wyv_O.js} +1 -1
  57. package/dist/app/assets/clone-BMPaQ6PL.js +1 -0
  58. package/dist/app/assets/{cmake-TK-Cvlxu.js → cmake-Co2PqOJx.js} +1 -1
  59. package/dist/app/assets/{cobol-XSbSVVcZ.js → cobol-CNBeDco-.js} +1 -1
  60. package/dist/app/assets/{coffeescript-HxNd9-Ob.js → coffeescript-DdmDPbXl.js} +1 -1
  61. package/dist/app/assets/{concurnas-DK3wUjjD.js → concurnas-C9VRiWa-.js} +1 -1
  62. package/dist/app/assets/{coq-B9Rq7NUE.js → coq-CYE7tqZa.js} +1 -1
  63. package/dist/app/assets/{core-B1vWjEfj.js → core-D4MD7_kt.js} +1 -1
  64. package/dist/app/assets/{cose-bilkent-S5V4N54A-4PebjqsX.js → cose-bilkent-S5V4N54A-Dxea2bnQ.js} +1 -1
  65. package/dist/app/assets/{cpp-DUWMh-8O.js → cpp-DWaMOtiP.js} +1 -1
  66. package/dist/app/assets/{crystal-rYgGF4lS.js → crystal-BtBXd6Fx.js} +1 -1
  67. package/dist/app/assets/{csharp-eqTMyksU.js → csharp-CrOHktb0.js} +1 -1
  68. package/dist/app/assets/{cshtml-DSv9-mpk.js → cshtml-CzjshIvK.js} +1 -1
  69. package/dist/app/assets/{csp-DyZfVzvb.js → csp-DnNBeWw0.js} +1 -1
  70. package/dist/app/assets/{css-extras-FP15zHq8.js → css-extras-BDArRWv3.js} +1 -1
  71. package/dist/app/assets/{css-DYXyUyJe.js → css-pohe_YML.js} +1 -1
  72. package/dist/app/assets/{csv-Bp1iUR7c.js → csv-BOXRdr2m.js} +1 -1
  73. package/dist/app/assets/{cypher-BjXgs7Y3.js → cypher-IsM8Hmhu.js} +1 -1
  74. package/dist/app/assets/{d-Bquc1S6a.js → d-BUE4Srvp.js} +1 -1
  75. package/dist/app/assets/{dagre-KV5264BT-D9OICDLb.js → dagre-KV5264BT-D9I1gn5M.js} +1 -1
  76. package/dist/app/assets/{dart-DrKyO7TC.js → dart-DKXx5vmY.js} +1 -1
  77. package/dist/app/assets/{dataweave-BgpsWzO7.js → dataweave-CZ-IeeGN.js} +1 -1
  78. package/dist/app/assets/{dax-BwP1SyCZ.js → dax-Cyyg-Qre.js} +1 -1
  79. package/dist/app/assets/{dhall-BA5nXB8V.js → dhall-CI9o_hcQ.js} +1 -1
  80. package/dist/app/assets/{diagram-5BDNPKRD-BIFTIy6n.js → diagram-5BDNPKRD-Da8AhEfW.js} +1 -1
  81. package/dist/app/assets/{diagram-G4DWMVQ6-BCVIBrZ2.js → diagram-G4DWMVQ6-u5xAUOB1.js} +1 -1
  82. package/dist/app/assets/{diagram-MMDJMWI5-43z4NaFN.js → diagram-MMDJMWI5-CRedReUg.js} +1 -1
  83. package/dist/app/assets/{diagram-TYMM5635-BDZjM1c_.js → diagram-TYMM5635-Btelw9Gj.js} +1 -1
  84. package/dist/app/assets/{diff-Yc6a7YOT.js → diff-BaJjRLPC.js} +1 -1
  85. package/dist/app/assets/{django-B61BBi1t.js → django-DKz8sLSB.js} +1 -1
  86. package/dist/app/assets/{dns-zone-file-DtXhOJHq.js → dns-zone-file-DB4bzm0m.js} +1 -1
  87. package/dist/app/assets/{docker-BLh9n10i.js → docker-f9TV7yVV.js} +1 -1
  88. package/dist/app/assets/{dot-BbSnn0Ap.js → dot-CItfl0YH.js} +1 -1
  89. package/dist/app/assets/{ebnf-D_ljHBdb.js → ebnf-4UWkoMwW.js} +1 -1
  90. package/dist/app/assets/{editorconfig-BQXrLGC5.js → editorconfig-DsQRKuSQ.js} +1 -1
  91. package/dist/app/assets/{eiffel-Cm3FUI5X.js → eiffel-BKzL5tZy.js} +1 -1
  92. package/dist/app/assets/{ejs-CIp2UdDw.js → ejs-FawjQT4F.js} +1 -1
  93. package/dist/app/assets/{elixir-DXlWBe5R.js → elixir-CYrsCeua.js} +1 -1
  94. package/dist/app/assets/{elm-ECxjLCR-.js → elm-BQbPKl6Y.js} +1 -1
  95. package/dist/app/assets/{erDiagram-SMLLAGMA-B9I89ndp.js → erDiagram-SMLLAGMA-nIXCbdu9.js} +1 -1
  96. package/dist/app/assets/{erb-FzgX8ydn.js → erb-D8td-3qG.js} +1 -1
  97. package/dist/app/assets/{erlang-CzvdSvoz.js → erlang-CVcUIOcL.js} +1 -1
  98. package/dist/app/assets/{etlua-C3Zsz3RA.js → etlua-Sp57LMlp.js} +1 -1
  99. package/dist/app/assets/{excel-formula-Cua38PQJ.js → excel-formula-C2xW1VqS.js} +1 -1
  100. package/dist/app/assets/{factor-CSAzXoQb.js → factor-B39cYmXr.js} +1 -1
  101. package/dist/app/assets/{false-NSFMCUjP.js → false-BXc89S7-.js} +1 -1
  102. package/dist/app/assets/{firestore-security-rules-BjNYwvNe.js → firestore-security-rules-D5XHnYii.js} +1 -1
  103. package/dist/app/assets/{flow-BuZaM8y6.js → flow-DvgodFNT.js} +1 -1
  104. package/dist/app/assets/{flowDiagram-DWJPFMVM-CWmW_muY.js → flowDiagram-DWJPFMVM-BRxtHyqr.js} +1 -1
  105. package/dist/app/assets/{fortran-Cc_f_mSH.js → fortran-C2uXAnB9.js} +1 -1
  106. package/dist/app/assets/{fsharp-IelQ4Z-Z.js → fsharp-D4MeNJsV.js} +1 -1
  107. package/dist/app/assets/{ftl-Ddl9DDyG.js → ftl-FdK7rzYa.js} +1 -1
  108. package/dist/app/assets/{ganttDiagram-T4ZO3ILL-CuR1J7dx.js → ganttDiagram-T4ZO3ILL-CxQPl5RJ.js} +1 -1
  109. package/dist/app/assets/{gap-D3W6p-Jp.js → gap-CqoRmA2e.js} +1 -1
  110. package/dist/app/assets/{gcode-Bn8O4UOx.js → gcode-Cbf6Hq0S.js} +1 -1
  111. package/dist/app/assets/{gdscript-B4nck3Az.js → gdscript-vUATu21P.js} +1 -1
  112. package/dist/app/assets/{gedcom-BCTZRsxn.js → gedcom-Dq_MXb_u.js} +1 -1
  113. package/dist/app/assets/{gherkin-CFCJQug9.js → gherkin-TnW-3H17.js} +1 -1
  114. package/dist/app/assets/{git-Dd2t83_l.js → git-ChiXZZK3.js} +1 -1
  115. package/dist/app/assets/{gitGraphDiagram-UUTBAWPF-DzscVnaS.js → gitGraphDiagram-UUTBAWPF-Bcj29y1k.js} +1 -1
  116. package/dist/app/assets/{glsl-NXGZDuA9.js → glsl-D73MB7QA.js} +1 -1
  117. package/dist/app/assets/{gml-DtS9_99j.js → gml-DKKhoV5Q.js} +1 -1
  118. package/dist/app/assets/{gn-C6VmNt4U.js → gn-xteKZDbd.js} +1 -1
  119. package/dist/app/assets/{go-otK-v_nb.js → go-gderB942.js} +1 -1
  120. package/dist/app/assets/{go-module-CmBM8SA1.js → go-module-Cxdn5g6K.js} +1 -1
  121. package/dist/app/assets/{graph-BelNBDAZ.js → graph-Dr0CyUTm.js} +1 -1
  122. package/dist/app/assets/{graphql-JPlPKrhh.js → graphql-B9ESkh7V.js} +1 -1
  123. package/dist/app/assets/{groovy-CkMUqzIt.js → groovy-D46SaIaB.js} +1 -1
  124. package/dist/app/assets/{haml-DwaIQOGd.js → haml-C-gOKeM2.js} +1 -1
  125. package/dist/app/assets/{handlebars-Ck6RB1iw.js → handlebars-WQgCAz-C.js} +1 -1
  126. package/dist/app/assets/{haskell-BxYLBxBa.js → haskell-DZKWHhbK.js} +1 -1
  127. package/dist/app/assets/{haxe-C4OMV9zJ.js → haxe-Do6EdaWm.js} +1 -1
  128. package/dist/app/assets/{hcl-DVznmODf.js → hcl-CW6MZD7W.js} +1 -1
  129. package/dist/app/assets/{hlsl-Z_ySkish.js → hlsl-BYgUfMru.js} +1 -1
  130. package/dist/app/assets/{hoon-UWT3k4H8.js → hoon-IqFoeyLn.js} +1 -1
  131. package/dist/app/assets/{hpkp-CXa39f7J.js → hpkp-BuV8JDpY.js} +1 -1
  132. package/dist/app/assets/{hsts-CJF4yNvU.js → hsts-DAvq0I49.js} +1 -1
  133. package/dist/app/assets/{http-BxOKxlr4.js → http-CCayShZc.js} +1 -1
  134. package/dist/app/assets/{ichigojam-Csb66zY2.js → ichigojam-IQlKAhBR.js} +1 -1
  135. package/dist/app/assets/{icon-DxphTQI9.js → icon-C1YOMBEH.js} +1 -1
  136. package/dist/app/assets/{icu-message-format-CSZfssuP.js → icu-message-format-CbkLI-kP.js} +1 -1
  137. package/dist/app/assets/{idris-BmXANiaa.js → idris-Db0sol3G.js} +1 -1
  138. package/dist/app/assets/{iecst-FfznJdjL.js → iecst-Rp9pN_Ps.js} +1 -1
  139. package/dist/app/assets/{ignore-C3IKkXMi.js → ignore-DSijMN4b.js} +1 -1
  140. package/dist/app/assets/index-EzE2l0pf.css +1 -0
  141. package/dist/app/assets/index-izi7yD-m.js +747 -0
  142. package/dist/app/assets/{infoDiagram-42DDH7IO-rTeQPEt4.js → infoDiagram-42DDH7IO-DP_5_HCg.js} +1 -1
  143. package/dist/app/assets/{inform7-Dk4gPo4b.js → inform7-BdTrQNcW.js} +1 -1
  144. package/dist/app/assets/{ini-CClGKGMe.js → ini-BL1YqQPe.js} +1 -1
  145. package/dist/app/assets/{io-6YtqLtET.js → io-ju4qnY4R.js} +1 -1
  146. package/dist/app/assets/{ishikawaDiagram-UXIWVN3A-BBnJ9iuN.js → ishikawaDiagram-UXIWVN3A-c-5weLZu.js} +1 -1
  147. package/dist/app/assets/{j-DBPrIcAG.js → j-BNgG1B_8.js} +1 -1
  148. package/dist/app/assets/{java-CopGP3Lu.js → java-BBM8kPUi.js} +1 -1
  149. package/dist/app/assets/{javadoc-C8F3ifW2.js → javadoc-DzqYwIEC.js} +1 -1
  150. package/dist/app/assets/{javadoclike-BNVFpoJC.js → javadoclike-CXHyoMho.js} +1 -1
  151. package/dist/app/assets/{javascript-BMkkas2q.js → javascript-DyOtAE59.js} +1 -1
  152. package/dist/app/assets/{javastacktrace-DuykBujE.js → javastacktrace-CfTMUgb0.js} +1 -1
  153. package/dist/app/assets/{jexl-BSWOm8s5.js → jexl-BmCWVTv_.js} +1 -1
  154. package/dist/app/assets/{jolie-CdkOmKFM.js → jolie-C3BdHGrF.js} +1 -1
  155. package/dist/app/assets/{journeyDiagram-VCZTEJTY-CRDpL_1T.js → journeyDiagram-VCZTEJTY-DAKBW1_0.js} +1 -1
  156. package/dist/app/assets/{jq-Nr0Kxpxc.js → jq-B4eKQbVT.js} +1 -1
  157. package/dist/app/assets/{js-extras-CA8iZ_E5.js → js-extras-B9Um65g1.js} +1 -1
  158. package/dist/app/assets/{js-templates-BoqcQW67.js → js-templates-B8LIGz8d.js} +1 -1
  159. package/dist/app/assets/{jsdoc-CeMFl6xP.js → jsdoc-X69feyNn.js} +1 -1
  160. package/dist/app/assets/{json-CrSHUueM.js → json-Ds9Y6npk.js} +1 -1
  161. package/dist/app/assets/{json5-BBfX460l.js → json5-BEpvRyGQ.js} +1 -1
  162. package/dist/app/assets/{jsonp-DHEqmGWL.js → jsonp-CI2Vwglg.js} +1 -1
  163. package/dist/app/assets/{jsstacktrace-BK3SuvsS.js → jsstacktrace-B_qFrkK8.js} +1 -1
  164. package/dist/app/assets/{jsx-CjR3dp14.js → jsx-C_Wki7pg.js} +1 -1
  165. package/dist/app/assets/{julia-BJJ6LUnI.js → julia-CGmxtkB0.js} +1 -1
  166. package/dist/app/assets/{kanban-definition-6JOO6SKY-Dztk4Auy.js → kanban-definition-6JOO6SKY-Bj8uidJb.js} +1 -1
  167. package/dist/app/assets/{keepalived-CjGUJvsk.js → keepalived-C8Mk-Wqp.js} +1 -1
  168. package/dist/app/assets/{keyman-Bogz-7f0.js → keyman-CMifeZZV.js} +1 -1
  169. package/dist/app/assets/{kotlin-DGdetcAk.js → kotlin-ogZAOqoN.js} +1 -1
  170. package/dist/app/assets/{kumir-Czhml4-j.js → kumir-BrGxaUVr.js} +1 -1
  171. package/dist/app/assets/{kusto-BuL9qwXk.js → kusto-DeyIYXML.js} +1 -1
  172. package/dist/app/assets/{latex-BAc_zS_4.js → latex-DwJWQSKl.js} +1 -1
  173. package/dist/app/assets/{latte-BzZFX_wH.js → latte-DiAT5mgQ.js} +1 -1
  174. package/dist/app/assets/{layout-DOHRtR3x.js → layout-Ci0rB0BF.js} +1 -1
  175. package/dist/app/assets/{less-DATW_Ot3.js → less-DAct2ixG.js} +1 -1
  176. package/dist/app/assets/{lilypond-DSmAdE7B.js → lilypond-CznC99Kp.js} +1 -1
  177. package/dist/app/assets/{linear-rr7FzlEM.js → linear-Db4iWNSq.js} +1 -1
  178. package/dist/app/assets/{liquid-CF8lqz9m.js → liquid-BxjgrxHp.js} +1 -1
  179. package/dist/app/assets/{lisp-BUPAsWUh.js → lisp-C4lgit6G.js} +1 -1
  180. package/dist/app/assets/{livescript-B8CIEQDH.js → livescript-BEQgCon6.js} +1 -1
  181. package/dist/app/assets/{llvm-DGaRc9w0.js → llvm-Xf0jCPO4.js} +1 -1
  182. package/dist/app/assets/{log-XuE3Wqn5.js → log-BiVfEwum.js} +1 -1
  183. package/dist/app/assets/{lolcode-Clk-p_j2.js → lolcode-BSO8DuGE.js} +1 -1
  184. package/dist/app/assets/{lua-BLczZbJa.js → lua-DGW916x5.js} +1 -1
  185. package/dist/app/assets/{magma-DTO3ftgF.js → magma-OhptpZ13.js} +1 -1
  186. package/dist/app/assets/{makefile-OSVaZHmV.js → makefile-DBnxpcUU.js} +1 -1
  187. package/dist/app/assets/{markdown-InD7dXs9.js → markdown-BznySwma.js} +1 -1
  188. package/dist/app/assets/{markup-BN6MlRZT.js → markup-DqRz3LJm.js} +1 -1
  189. package/dist/app/assets/{markup-templating-DRXAmI1c.js → markup-templating-BKB_GGuz.js} +1 -1
  190. package/dist/app/assets/{matlab-CV_q70_G.js → matlab-3N0TcL6N.js} +1 -1
  191. package/dist/app/assets/{maxscript-Ck_8H__C.js → maxscript-BZvlaoGH.js} +1 -1
  192. package/dist/app/assets/{mel-D9MU0rZa.js → mel-BSmK0T7H.js} +1 -1
  193. package/dist/app/assets/{mermaid-DshECBS6.js → mermaid-Duc2qb5F.js} +1 -1
  194. package/dist/app/assets/{min-CfLzpwyh.js → min-BKNYKdIk.js} +1 -1
  195. package/dist/app/assets/{mindmap-definition-QFDTVHPH-C7XGlydX.js → mindmap-definition-QFDTVHPH-CnWL0xVD.js} +1 -1
  196. package/dist/app/assets/{mizar-WBJ-SwIG.js → mizar-BI02SHrx.js} +1 -1
  197. package/dist/app/assets/{mongodb-CmzRTKBq.js → mongodb-CRQm09Xn.js} +1 -1
  198. package/dist/app/assets/{monkey-W1yB--1T.js → monkey-Dv34nuh4.js} +1 -1
  199. package/dist/app/assets/{moonscript-BD5hlCXn.js → moonscript-50xJ2oId.js} +1 -1
  200. package/dist/app/assets/{n1ql-CwugAEoM.js → n1ql-Cm4qd43r.js} +1 -1
  201. package/dist/app/assets/{n4js-tFC-Lsvd.js → n4js-LXxDuAtT.js} +1 -1
  202. package/dist/app/assets/{nand2tetris-hdl-hzvfBJxH.js → nand2tetris-hdl-CkSPhEoK.js} +1 -1
  203. package/dist/app/assets/{naniscript-DUtjoUL1.js → naniscript-CopSq9dX.js} +1 -1
  204. package/dist/app/assets/{nasm-Dcckq6ib.js → nasm-D7A7rGAF.js} +1 -1
  205. package/dist/app/assets/{neon-DeVv09BE.js → neon-BAKsC02_.js} +1 -1
  206. package/dist/app/assets/{nevod-CAq9Kfwt.js → nevod-C-euYOSr.js} +1 -1
  207. package/dist/app/assets/{nginx-C8GHDEqt.js → nginx-B9jALad5.js} +1 -1
  208. package/dist/app/assets/{nim-BqdyUedD.js → nim-BBHZHQ5E.js} +1 -1
  209. package/dist/app/assets/{nix-514mCcjs.js → nix-DmfkvvNO.js} +1 -1
  210. package/dist/app/assets/{nsis-CdKqXn3g.js → nsis-CiSC6aDO.js} +1 -1
  211. package/dist/app/assets/{objectivec-uPp8iMUn.js → objectivec-CZ2ovZFJ.js} +1 -1
  212. package/dist/app/assets/{ocaml-D4EB6rFL.js → ocaml-CyX9uBPK.js} +1 -1
  213. package/dist/app/assets/{opencl-BN8tmrp-.js → opencl-BSrZYM8c.js} +1 -1
  214. package/dist/app/assets/{openqasm-CZT9yVLH.js → openqasm-DOuul9tf.js} +1 -1
  215. package/dist/app/assets/{oz-xEnzbfGI.js → oz-rsJy_2_r.js} +1 -1
  216. package/dist/app/assets/{parigp-PN33G_ZS.js → parigp-DMZs3sMP.js} +1 -1
  217. package/dist/app/assets/{parser-YigtK2Gn.js → parser-CLeK_wYt.js} +1 -1
  218. package/dist/app/assets/{pascal-BSQHqJO2.js → pascal-DZ4qTuqN.js} +1 -1
  219. package/dist/app/assets/{pascaligo-B3om_nlX.js → pascaligo-D6ziPQJn.js} +1 -1
  220. package/dist/app/assets/{pcaxis-B_qwjIH4.js → pcaxis-Bsa4kJ1N.js} +1 -1
  221. package/dist/app/assets/{peoplecode-G3CTxh8q.js → peoplecode-BtULIv-H.js} +1 -1
  222. package/dist/app/assets/{perl-CBvGMSZZ.js → perl-CswAAlfX.js} +1 -1
  223. package/dist/app/assets/{php-DewJLtev.js → php-Bv-ALqgC.js} +1 -1
  224. package/dist/app/assets/{php-extras-BT2DdjGn.js → php-extras-CGQHigyg.js} +1 -1
  225. package/dist/app/assets/{phpdoc-DiQXOd9D.js → phpdoc-CbRxSWh6.js} +1 -1
  226. package/dist/app/assets/{pieDiagram-DEJITSTG-CYXmqIpD.js → pieDiagram-DEJITSTG-VWWiVQxO.js} +1 -1
  227. package/dist/app/assets/{plsql-BzUO3h3t.js → plsql-DQRexRDV.js} +1 -1
  228. package/dist/app/assets/{powerquery-D_713gdU.js → powerquery-B84pC27o.js} +1 -1
  229. package/dist/app/assets/{powershell-D7IGyPyT.js → powershell-CYB8PDOS.js} +1 -1
  230. package/dist/app/assets/{processing-CULfTuKk.js → processing-IV7AOKMt.js} +1 -1
  231. package/dist/app/assets/{prolog-DI8sHw_1.js → prolog-C5Umzi6Y.js} +1 -1
  232. package/dist/app/assets/{promql-DdWPpZzX.js → promql-DnQb00nJ.js} +1 -1
  233. package/dist/app/assets/{properties-UUBptvjg.js → properties-JtX62kym.js} +1 -1
  234. package/dist/app/assets/{protobuf-Yh4lBroy.js → protobuf-D0u54vfT.js} +1 -1
  235. package/dist/app/assets/{psl-CKuqp255.js → psl-D2wfxc3N.js} +1 -1
  236. package/dist/app/assets/{pug-Duz4hJlP.js → pug-Cfscfbjt.js} +1 -1
  237. package/dist/app/assets/{puppet-Tenfq4aE.js → puppet-DTE3iXOW.js} +1 -1
  238. package/dist/app/assets/{pure-CTE3YKFb.js → pure-YKO-tWRN.js} +1 -1
  239. package/dist/app/assets/{purebasic-BzV6ZqWW.js → purebasic-BjxfhqXa.js} +1 -1
  240. package/dist/app/assets/{purescript-CjSCYtGb.js → purescript-BYtsXeuA.js} +1 -1
  241. package/dist/app/assets/{q-BTX8RKFy.js → q-BGBZJwiX.js} +1 -1
  242. package/dist/app/assets/{qml-CGjBjP81.js → qml-DTmpu0_b.js} +1 -1
  243. package/dist/app/assets/{qore-5Gggmt2I.js → qore-DV3zUzln.js} +1 -1
  244. package/dist/app/assets/{qsharp-DhqE1FPx.js → qsharp-BB4ZU4l7.js} +1 -1
  245. package/dist/app/assets/{quadrantDiagram-34T5L4WZ-BbnPMKp-.js → quadrantDiagram-34T5L4WZ-DZe4FQWm.js} +1 -1
  246. package/dist/app/assets/{r-Dr0jr5tD.js → r-BuRdYuOg.js} +1 -1
  247. package/dist/app/assets/{racket-NVUa01EO.js → racket-BdOLCXmL.js} +1 -1
  248. package/dist/app/assets/{reason-Bx5CI0l0.js → reason-BCIhgqTr.js} +1 -1
  249. package/dist/app/assets/{regex-12879jLK.js → regex-CeDcXiBn.js} +1 -1
  250. package/dist/app/assets/{rego-w2Fhvb_N.js → rego-Bug6Gtky.js} +1 -1
  251. package/dist/app/assets/{renpy-gPxX0z3Q.js → renpy-C1LtsjtW.js} +1 -1
  252. package/dist/app/assets/{requirementDiagram-MS252O5E-BhOU7uOd.js → requirementDiagram-MS252O5E-BYaMMinK.js} +1 -1
  253. package/dist/app/assets/{rest-C39bU2b1.js → rest-Fa9SyY67.js} +1 -1
  254. package/dist/app/assets/{rip-RLtTVF0Y.js → rip-SetkIYoC.js} +1 -1
  255. package/dist/app/assets/{roboconf-BJckt4oD.js → roboconf-CRy7RXFK.js} +1 -1
  256. package/dist/app/assets/{robotframework-DCR96jiT.js → robotframework-DHo4R8pp.js} +1 -1
  257. package/dist/app/assets/{ruby-CRs8uxXB.js → ruby-DM2JwZlW.js} +1 -1
  258. package/dist/app/assets/{rust-C0bGL254.js → rust-_NNFafik.js} +1 -1
  259. package/dist/app/assets/{sankeyDiagram-XADWPNL6-CFgkd6GO.js → sankeyDiagram-XADWPNL6-DAunyA-1.js} +1 -1
  260. package/dist/app/assets/{sas-CkLtpL1M.js → sas-CAllZx8n.js} +1 -1
  261. package/dist/app/assets/{sass-FNfCYuQd.js → sass-Hf4UBtzK.js} +1 -1
  262. package/dist/app/assets/{scala-Dy5lip5O.js → scala-DkNiERTA.js} +1 -1
  263. package/dist/app/assets/{scheme-pkKED5As.js → scheme-cRBlcCac.js} +1 -1
  264. package/dist/app/assets/{scss-DrZ4F_S5.js → scss-D8mZ_Za-.js} +1 -1
  265. package/dist/app/assets/{sequenceDiagram-FGHM5R23-t5z2WRg9.js → sequenceDiagram-FGHM5R23-sNXmL4Cw.js} +1 -1
  266. package/dist/app/assets/{shell-session-tfqRzQ64.js → shell-session-DeKXiekb.js} +1 -1
  267. package/dist/app/assets/{smali-D9oJJF_a.js → smali-DBMpR0WA.js} +1 -1
  268. package/dist/app/assets/{smalltalk-FhicZwdZ.js → smalltalk-BPhQ9s3z.js} +1 -1
  269. package/dist/app/assets/{smarty-RTVkhvGe.js → smarty-BMg06VgP.js} +1 -1
  270. package/dist/app/assets/{sml-8jU1U62j.js → sml-DLGSWP51.js} +1 -1
  271. package/dist/app/assets/{solidity-DLvpuywG.js → solidity-DeQT3dsc.js} +1 -1
  272. package/dist/app/assets/{solution-file-BOwCbL9x.js → solution-file-rfNIkT7V.js} +1 -1
  273. package/dist/app/assets/{soy-Dye6FppK.js → soy-zYtC6_ht.js} +1 -1
  274. package/dist/app/assets/{sparql-BRIOTA6e.js → sparql-CGa1CKp5.js} +1 -1
  275. package/dist/app/assets/{splunk-spl-xjEKSM5T.js → splunk-spl-C8v7uxfM.js} +1 -1
  276. package/dist/app/assets/{sqf-BTXRZqz9.js → sqf-DPaz1Lai.js} +1 -1
  277. package/dist/app/assets/{sql-LIGcsz7H.js → sql-CRZBr2wA.js} +1 -1
  278. package/dist/app/assets/{squirrel-D1i-yP9F.js → squirrel-CrbdCeO4.js} +1 -1
  279. package/dist/app/assets/{stan-Bz-MTQlG.js → stan-BKYvxpSb.js} +1 -1
  280. package/dist/app/assets/{stateDiagram-FHFEXIEX-INV79XkW.js → stateDiagram-FHFEXIEX-D36OCRvJ.js} +1 -1
  281. package/dist/app/assets/stateDiagram-v2-QKLJ7IA2-DmqGcWux.js +1 -0
  282. package/dist/app/assets/{stylus-CPcHbGGR.js → stylus-Ci4_F8nK.js} +1 -1
  283. package/dist/app/assets/{swift-CMnIAhC_.js → swift-mmkHLTYT.js} +1 -1
  284. package/dist/app/assets/{systemd-CnQ86vtn.js → systemd-DAUIxyR2.js} +1 -1
  285. package/dist/app/assets/{t4-cs-ClADD8kZ.js → t4-cs-BED2tz-u.js} +1 -1
  286. package/dist/app/assets/{t4-templating-BxEXIn9V.js → t4-templating--ieaosVt.js} +1 -1
  287. package/dist/app/assets/{t4-vb-BuQFrDQM.js → t4-vb-Dq0Puemw.js} +1 -1
  288. package/dist/app/assets/{tap-D-OeTv7J.js → tap-C_XPd1SR.js} +1 -1
  289. package/dist/app/assets/{tcl-D4EWmvqA.js → tcl-DJZd1oZX.js} +1 -1
  290. package/dist/app/assets/{textile-vCa5WeBr.js → textile-wcSaXbdv.js} +1 -1
  291. package/dist/app/assets/{timeline-definition-GMOUNBTQ-CZVpkWZR.js → timeline-definition-GMOUNBTQ-BewoZYzR.js} +1 -1
  292. package/dist/app/assets/{toml-CyQfWyMg.js → toml-CKDZZOrE.js} +1 -1
  293. package/dist/app/assets/{tremor-DTpakXR3.js → tremor-B1-Zw3yS.js} +1 -1
  294. package/dist/app/assets/{tt2-I3k-jzpY.js → tt2-BHFaXCZF.js} +1 -1
  295. package/dist/app/assets/{turtle-BjS87MX7.js → turtle-KSw4upem.js} +1 -1
  296. package/dist/app/assets/{twig-BYK2hDMY.js → twig-BRBoP8KB.js} +1 -1
  297. package/dist/app/assets/{typescript-DNEOvUVG.js → typescript-bns4dUtY.js} +1 -1
  298. package/dist/app/assets/{typoscript-hqzFge6d.js → typoscript-BVmk6GiM.js} +1 -1
  299. package/dist/app/assets/{unrealscript-_-NzaZj0.js → unrealscript-hTYhevmS.js} +1 -1
  300. package/dist/app/assets/{uorazor-BMR9qMW5.js → uorazor-BY_i1glx.js} +1 -1
  301. package/dist/app/assets/{uri-BSGWfMxZ.js → uri-Cshg9KEA.js} +1 -1
  302. package/dist/app/assets/{v-CLtdeXIK.js → v-2HZBfvBQ.js} +1 -1
  303. package/dist/app/assets/{vala-wzCcqtKA.js → vala-DpwXQy33.js} +1 -1
  304. package/dist/app/assets/{vbnet-DGCLmXdC.js → vbnet-CzcanlBM.js} +1 -1
  305. package/dist/app/assets/{velocity-DX_5gTOq.js → velocity-CV3Erd1R.js} +1 -1
  306. package/dist/app/assets/{vennDiagram-DHZGUBPP-Dq1FXdcO.js → vennDiagram-DHZGUBPP-CYp9O0hw.js} +1 -1
  307. package/dist/app/assets/{verilog-DeAFTKrK.js → verilog-DUFfdhmC.js} +1 -1
  308. package/dist/app/assets/{vhdl-CgPp3m3I.js → vhdl-Ehst2swj.js} +1 -1
  309. package/dist/app/assets/{vim-ZY6C4NgO.js → vim-ChBxD9-s.js} +1 -1
  310. package/dist/app/assets/{visual-basic-DmV7laqn.js → visual-basic-DhxNPprf.js} +1 -1
  311. package/dist/app/assets/{wardley-RL74JXVD-OqiGOeix.js → wardley-RL74JXVD-ChpRMv2u.js} +1 -1
  312. package/dist/app/assets/{wardleyDiagram-NUSXRM2D-XXEOUAR6.js → wardleyDiagram-NUSXRM2D-CFpThRE-.js} +1 -1
  313. package/dist/app/assets/{warpscript-CST9Acbf.js → warpscript-Dx1Itmpb.js} +1 -1
  314. package/dist/app/assets/{wasm-D44TvCcf.js → wasm-BvTc7Cyo.js} +1 -1
  315. package/dist/app/assets/{web-idl-CUAX3ogm.js → web-idl-B43dy8xT.js} +1 -1
  316. package/dist/app/assets/{wiki-KNEqZQWK.js → wiki-C0vje4IO.js} +1 -1
  317. package/dist/app/assets/{wolfram-CZdD1bRd.js → wolfram-B1twTrAy.js} +1 -1
  318. package/dist/app/assets/{wren-PITvEkQ4.js → wren-CpwJ20dT.js} +1 -1
  319. package/dist/app/assets/{xeora-BM_ABt9y.js → xeora-Q9elMskQ.js} +1 -1
  320. package/dist/app/assets/{xml-doc-249eg8mF.js → xml-doc-eO6FH-U3.js} +1 -1
  321. package/dist/app/assets/{xojo-M3SASV_b.js → xojo-1Fr7QqPR.js} +1 -1
  322. package/dist/app/assets/{xquery-BWv2VkcM.js → xquery-BMmMoA1b.js} +1 -1
  323. package/dist/app/assets/{xychartDiagram-5P7HB3ND-CvXT15VO.js → xychartDiagram-5P7HB3ND-De8Xu1fj.js} +1 -1
  324. package/dist/app/assets/{yaml-B70AwQ7Y.js → yaml-34lcFD2P.js} +1 -1
  325. package/dist/app/assets/{yang-DffrsIpd.js → yang-DervT_oZ.js} +1 -1
  326. package/dist/app/assets/{zig-C9vlYfKL.js → zig-Cipb22UI.js} +1 -1
  327. package/dist/app/index.html +2 -2
  328. package/dist/index.cjs +2523 -635
  329. package/dist/index.js +2555 -636
  330. package/package.json +4 -4
  331. package/dist/app/assets/channel-Cx11sSAI.js +0 -1
  332. package/dist/app/assets/classDiagram-6PBFFD2Q-BQrwJXsB.js +0 -1
  333. package/dist/app/assets/classDiagram-v2-HSJHXN6E-BQrwJXsB.js +0 -1
  334. package/dist/app/assets/clone-DHPdZQ_6.js +0 -1
  335. package/dist/app/assets/index-D972kqET.css +0 -1
  336. package/dist/app/assets/index-DmMWBDJR.js +0 -747
  337. package/dist/app/assets/stateDiagram-v2-QKLJ7IA2-DkwGLXRp.js +0 -1
package/dist/index.cjs CHANGED
@@ -66,8 +66,8 @@ __export(index_exports, {
66
66
  module.exports = __toCommonJS(index_exports);
67
67
 
68
68
  // src/components/chat.tsx
69
- var React22 = __toESM(require("react"), 1);
70
- var import_lucide_react11 = require("lucide-react");
69
+ var React26 = __toESM(require("react"), 1);
70
+ var import_lucide_react15 = require("lucide-react");
71
71
 
72
72
  // src/lib/utils.ts
73
73
  var import_clsx = require("clsx");
@@ -681,6 +681,10 @@ function ParentMessengerProvider({
681
681
  }
682
682
  return;
683
683
  }
684
+ const requestHumanInput = params.planMode === true || params.state?.[import_chatkit_types2.STATE_VARIABLE_HUMAN]?.planMode === true ? {
685
+ ...humanInput,
686
+ planMode: true
687
+ } : humanInput;
684
688
  const newMessage = {
685
689
  id: createMessageId(),
686
690
  type: "human",
@@ -694,11 +698,11 @@ function ParentMessengerProvider({
694
698
  const requestOptions = buildInjectedRequestOptions({
695
699
  defaults: latestOptionsRef.current?.request,
696
700
  state: params.state,
697
- humanInput
701
+ humanInput: requestHumanInput
698
702
  });
699
703
  stream?.submit(
700
704
  {
701
- input: humanInput,
705
+ input: requestHumanInput,
702
706
  ...requestOptions.state ? { state: requestOptions.state } : {}
703
707
  },
704
708
  {
@@ -961,6 +965,11 @@ function getBusyComposerShortcutFollowUpMode(useQueueShortcut) {
961
965
  return useQueueShortcut ? "queue" : "steer";
962
966
  }
963
967
 
968
+ // src/lib/todos.ts
969
+ function countCompletedTodos(items) {
970
+ return items.filter((item) => item.status === "completed").length;
971
+ }
972
+
964
973
  // src/providers/Stream.tsx
965
974
  var import_jsx_runtime2 = require("react/jsx-runtime");
966
975
  var import_meta = {};
@@ -1115,6 +1124,9 @@ var en_US_default = {
1115
1124
  manualQueueHint: "Ready to send as a new run",
1116
1125
  steerHint: "Injects after the current tool call"
1117
1126
  },
1127
+ todos: {
1128
+ summary: "{{total}} tasks, {{completed}} completed"
1129
+ },
1118
1130
  errors: {
1119
1131
  loadMessages: "Failed to load thread messages",
1120
1132
  createThread: "Failed to create thread",
@@ -1146,8 +1158,22 @@ var en_US_default = {
1146
1158
  composer: {
1147
1159
  openMenu: "Open menu",
1148
1160
  addAttachment: "Add attachment",
1161
+ planMode: "Plan mode",
1149
1162
  removeReference: "Remove reference",
1150
- quoteSelection: "Quote selection"
1163
+ quoteSelection: "Quote selection",
1164
+ requestUserInput: {
1165
+ title: "Input requested",
1166
+ recommended: "Recommended",
1167
+ other: "Other",
1168
+ otherPlaceholder: "Type a custom answer",
1169
+ continue: "Continue",
1170
+ dismiss: "Dismiss",
1171
+ previousQuestion: "Previous question",
1172
+ nextQuestion: "Next question",
1173
+ questionProgress: "{{current}} of {{total}}",
1174
+ optionInfo: "Details for {{label}}",
1175
+ submit: "Continue"
1176
+ }
1151
1177
  },
1152
1178
  sheet: {
1153
1179
  close: "Close"
@@ -1174,7 +1200,58 @@ var en_US_default = {
1174
1200
  reasoning: "Reasoning",
1175
1201
  loading: "Loading",
1176
1202
  thinking: "Thinking",
1177
- answering: "Answering"
1203
+ answering: "Answering",
1204
+ requestUserInputResult: {
1205
+ title: "Selections confirmed",
1206
+ option: "Option",
1207
+ other: "Other"
1208
+ },
1209
+ toolGroup: {
1210
+ status: {
1211
+ running: "Processing",
1212
+ success: "Processed",
1213
+ fail: "Processing failed"
1214
+ },
1215
+ inputTitle: "Input",
1216
+ outputTitle: "Output",
1217
+ errorTitle: "Error",
1218
+ jsonTitle: "JSON",
1219
+ jsonTree: "Tree",
1220
+ jsonRaw: "Raw",
1221
+ copy: "Copy",
1222
+ copied: "Copied",
1223
+ separator: ", ",
1224
+ categories: {
1225
+ files: {
1226
+ one: "{{count}} file",
1227
+ other: "{{count}} files"
1228
+ },
1229
+ searches: {
1230
+ one: "{{count}} search",
1231
+ other: "{{count}} searches"
1232
+ },
1233
+ commands: {
1234
+ one: "{{count}} command",
1235
+ other: "{{count}} commands"
1236
+ },
1237
+ lists: {
1238
+ one: "{{count}} list",
1239
+ other: "{{count}} lists"
1240
+ },
1241
+ tasks: {
1242
+ one: "{{count}} task",
1243
+ other: "{{count}} tasks"
1244
+ },
1245
+ knowledges: {
1246
+ one: "{{count}} knowledge result",
1247
+ other: "{{count}} knowledge results"
1248
+ },
1249
+ tools: {
1250
+ one: "{{count}} tool",
1251
+ other: "{{count}} tools"
1252
+ }
1253
+ }
1254
+ }
1178
1255
  }
1179
1256
  };
1180
1257
 
@@ -1219,6 +1296,9 @@ var zh_CN_default = {
1219
1296
  manualQueueHint: "\u4FDD\u7559\u4E3A\u5F85\u53D1\u9001\uFF0C\u53EF\u624B\u52A8\u5F00\u542F\u65B0\u4E00\u8F6E",
1220
1297
  steerHint: "\u5F53\u524D\u5DE5\u5177\u8C03\u7528\u5B8C\u6210\u540E\u6CE8\u5165"
1221
1298
  },
1299
+ todos: {
1300
+ summary: "\u5171 {{total}} \u4E2A\u4EFB\u52A1\uFF0C\u5DF2\u7ECF\u5B8C\u6210 {{completed}} \u4E2A"
1301
+ },
1222
1302
  errors: {
1223
1303
  loadMessages: "\u52A0\u8F7D\u7EBF\u7A0B\u6D88\u606F\u5931\u8D25",
1224
1304
  createThread: "\u521B\u5EFA\u7EBF\u7A0B\u5931\u8D25",
@@ -1250,8 +1330,22 @@ var zh_CN_default = {
1250
1330
  composer: {
1251
1331
  openMenu: "\u6253\u5F00\u83DC\u5355",
1252
1332
  addAttachment: "\u6DFB\u52A0\u9644\u4EF6",
1333
+ planMode: "\u8BA1\u5212\u6A21\u5F0F",
1253
1334
  removeReference: "\u79FB\u9664\u5F15\u7528",
1254
- quoteSelection: "\u5F15\u7528\u9009\u4E2D\u5185\u5BB9"
1335
+ quoteSelection: "\u5F15\u7528\u9009\u4E2D\u5185\u5BB9",
1336
+ requestUserInput: {
1337
+ title: "\u9700\u8981\u4F60\u7684\u8F93\u5165",
1338
+ recommended: "\u63A8\u8350",
1339
+ other: "\u5176\u4ED6",
1340
+ otherPlaceholder: "\u8F93\u5165\u81EA\u5B9A\u4E49\u56DE\u7B54",
1341
+ continue: "\u7EE7\u7EED",
1342
+ dismiss: "\u5173\u95ED",
1343
+ previousQuestion: "\u4E0A\u4E00\u4E2A\u95EE\u9898",
1344
+ nextQuestion: "\u4E0B\u4E00\u4E2A\u95EE\u9898",
1345
+ questionProgress: "{{current}} / {{total}}",
1346
+ optionInfo: "{{label}} \u7684\u8BF4\u660E",
1347
+ submit: "\u7EE7\u7EED"
1348
+ }
1255
1349
  },
1256
1350
  sheet: {
1257
1351
  close: "\u5173\u95ED"
@@ -1278,7 +1372,58 @@ var zh_CN_default = {
1278
1372
  reasoning: "\u63A8\u7406",
1279
1373
  loading: "\u6B63\u5728\u52A0\u8F7D",
1280
1374
  thinking: "\u6B63\u5728\u601D\u8003",
1281
- answering: "\u6B63\u5728\u751F\u6210"
1375
+ answering: "\u6B63\u5728\u751F\u6210",
1376
+ requestUserInputResult: {
1377
+ title: "\u5DF2\u786E\u8BA4\u9009\u62E9",
1378
+ option: "\u9009\u9879",
1379
+ other: "\u5176\u4ED6"
1380
+ },
1381
+ toolGroup: {
1382
+ status: {
1383
+ running: "\u6B63\u5728\u5904\u7406",
1384
+ success: "\u5DF2\u5904\u7406",
1385
+ fail: "\u5904\u7406\u5931\u8D25"
1386
+ },
1387
+ inputTitle: "\u8F93\u5165",
1388
+ outputTitle: "\u8F93\u51FA",
1389
+ errorTitle: "\u9519\u8BEF",
1390
+ jsonTitle: "JSON",
1391
+ jsonTree: "\u6811\u5F62",
1392
+ jsonRaw: "\u539F\u59CB",
1393
+ copy: "\u590D\u5236",
1394
+ copied: "\u5DF2\u590D\u5236",
1395
+ separator: "\uFF0C",
1396
+ categories: {
1397
+ files: {
1398
+ one: "{{count}} \u4E2A\u6587\u4EF6",
1399
+ other: "{{count}} \u4E2A\u6587\u4EF6"
1400
+ },
1401
+ searches: {
1402
+ one: "{{count}} \u4E2A\u641C\u7D22",
1403
+ other: "{{count}} \u4E2A\u641C\u7D22"
1404
+ },
1405
+ commands: {
1406
+ one: "{{count}} \u4E2A\u547D\u4EE4",
1407
+ other: "{{count}} \u4E2A\u547D\u4EE4"
1408
+ },
1409
+ lists: {
1410
+ one: "{{count}} \u4E2A\u5217\u8868",
1411
+ other: "{{count}} \u4E2A\u5217\u8868"
1412
+ },
1413
+ tasks: {
1414
+ one: "{{count}} \u4E2A\u4EFB\u52A1",
1415
+ other: "{{count}} \u4E2A\u4EFB\u52A1"
1416
+ },
1417
+ knowledges: {
1418
+ one: "{{count}} \u4E2A\u77E5\u8BC6\u7ED3\u679C",
1419
+ other: "{{count}} \u4E2A\u77E5\u8BC6\u7ED3\u679C"
1420
+ },
1421
+ tools: {
1422
+ one: "{{count}} \u4E2A\u5DE5\u5177\u8C03\u7528",
1423
+ other: "{{count}} \u4E2A\u5DE5\u5177\u8C03\u7528"
1424
+ }
1425
+ }
1426
+ }
1282
1427
  }
1283
1428
  };
1284
1429
 
@@ -1714,6 +1859,8 @@ function ComposerMenu({
1714
1859
  onAttachmentClick,
1715
1860
  onToolSelect,
1716
1861
  selectedTool,
1862
+ planModeEnabled = false,
1863
+ onPlanModeChange,
1717
1864
  disabled = false
1718
1865
  }) {
1719
1866
  const { t } = useChatkitTranslation();
@@ -1722,9 +1869,6 @@ function ComposerMenu({
1722
1869
  const roundedClass = getRoundedClass(theme.radius);
1723
1870
  const attachmentsEnabled = composer?.attachments?.enabled ?? false;
1724
1871
  const tools = composer?.tools ?? [];
1725
- if (!attachmentsEnabled && tools.length === 0) {
1726
- return null;
1727
- }
1728
1872
  const handleAttachmentClick = () => {
1729
1873
  onAttachmentClick?.();
1730
1874
  setOpen(false);
@@ -1733,6 +1877,9 @@ function ComposerMenu({
1733
1877
  onToolSelect?.(tool);
1734
1878
  setOpen(false);
1735
1879
  };
1880
+ const handlePlanModeToggle = () => {
1881
+ onPlanModeChange?.(!planModeEnabled);
1882
+ };
1736
1883
  return /* @__PURE__ */ (0, import_jsx_runtime6.jsxs)(Popover, { open, onOpenChange: setOpen, children: [
1737
1884
  /* @__PURE__ */ (0, import_jsx_runtime6.jsx)(PopoverTrigger, { asChild: true, children: /* @__PURE__ */ (0, import_jsx_runtime6.jsxs)(
1738
1885
  Button,
@@ -1772,8 +1919,46 @@ function ComposerMenu({
1772
1919
  ]
1773
1920
  }
1774
1921
  ),
1775
- tools.length > 0 && /* @__PURE__ */ (0, import_jsx_runtime6.jsx)("div", { className: "my-1 h-px bg-border" })
1922
+ /* @__PURE__ */ (0, import_jsx_runtime6.jsx)("div", { className: "my-1 h-px bg-border" })
1776
1923
  ] }),
1924
+ /* @__PURE__ */ (0, import_jsx_runtime6.jsxs)(
1925
+ "button",
1926
+ {
1927
+ type: "button",
1928
+ role: "switch",
1929
+ "aria-checked": planModeEnabled,
1930
+ onClick: handlePlanModeToggle,
1931
+ className: cn(
1932
+ "flex items-center gap-3 px-3 py-2 text-sm hover:bg-muted transition-colors",
1933
+ roundedClass,
1934
+ planModeEnabled && "bg-muted"
1935
+ ),
1936
+ children: [
1937
+ /* @__PURE__ */ (0, import_jsx_runtime6.jsx)("span", { className: "flex h-6 w-6 items-center justify-center text-muted-foreground", children: /* @__PURE__ */ (0, import_jsx_runtime6.jsx)(import_lucide_react.ListChecks, { size: 16 }) }),
1938
+ /* @__PURE__ */ (0, import_jsx_runtime6.jsx)("span", { className: "min-w-0 flex-1 text-left", children: t("composer.planMode") }),
1939
+ /* @__PURE__ */ (0, import_jsx_runtime6.jsx)(
1940
+ "span",
1941
+ {
1942
+ className: cn(
1943
+ "relative inline-flex h-6 w-10 shrink-0 items-center rounded-full transition-colors",
1944
+ planModeEnabled ? "bg-primary" : "bg-muted-foreground/20"
1945
+ ),
1946
+ "aria-hidden": "true",
1947
+ children: /* @__PURE__ */ (0, import_jsx_runtime6.jsx)(
1948
+ "span",
1949
+ {
1950
+ className: cn(
1951
+ "inline-block h-5 w-5 rounded-full bg-background shadow-sm transition-transform",
1952
+ planModeEnabled ? "translate-x-[18px]" : "translate-x-0.5"
1953
+ )
1954
+ }
1955
+ )
1956
+ }
1957
+ )
1958
+ ]
1959
+ }
1960
+ ),
1961
+ tools.length > 0 && /* @__PURE__ */ (0, import_jsx_runtime6.jsx)("div", { className: "my-1 h-px bg-border" }),
1777
1962
  tools.map((tool) => /* @__PURE__ */ (0, import_jsx_runtime6.jsxs)(
1778
1963
  "button",
1779
1964
  {
@@ -2096,19 +2281,23 @@ function HistorySidebar({
2096
2281
  setOpen(false);
2097
2282
  };
2098
2283
  return /* @__PURE__ */ (0, import_jsx_runtime11.jsxs)(Sheet, { open, onOpenChange: setOpen, children: [
2099
- /* @__PURE__ */ (0, import_jsx_runtime11.jsx)(SheetTrigger, { asChild: true, children: /* @__PURE__ */ (0, import_jsx_runtime11.jsxs)(
2100
- Button,
2101
- {
2102
- variant: "ghost",
2103
- size: "icon",
2104
- disabled,
2105
- className: "h-8 w-8 cursor-pointer",
2106
- children: [
2107
- /* @__PURE__ */ (0, import_jsx_runtime11.jsx)(import_lucide_react4.History, { size: 16 }),
2108
- /* @__PURE__ */ (0, import_jsx_runtime11.jsx)("span", { className: "sr-only", children: t("history.threadHistory") })
2109
- ]
2110
- }
2111
- ) }),
2284
+ /* @__PURE__ */ (0, import_jsx_runtime11.jsxs)(Tooltip, { children: [
2285
+ /* @__PURE__ */ (0, import_jsx_runtime11.jsx)(TooltipTrigger, { asChild: true, children: /* @__PURE__ */ (0, import_jsx_runtime11.jsx)("span", { className: "inline-flex h-8 w-8", children: /* @__PURE__ */ (0, import_jsx_runtime11.jsx)(SheetTrigger, { asChild: true, children: /* @__PURE__ */ (0, import_jsx_runtime11.jsxs)(
2286
+ Button,
2287
+ {
2288
+ variant: "ghost",
2289
+ size: "icon",
2290
+ disabled,
2291
+ className: "h-8 w-8 cursor-pointer",
2292
+ "aria-label": t("history.threadHistory"),
2293
+ children: [
2294
+ /* @__PURE__ */ (0, import_jsx_runtime11.jsx)(import_lucide_react4.History, { size: 16 }),
2295
+ /* @__PURE__ */ (0, import_jsx_runtime11.jsx)("span", { className: "sr-only", children: t("history.threadHistory") })
2296
+ ]
2297
+ }
2298
+ ) }) }) }),
2299
+ /* @__PURE__ */ (0, import_jsx_runtime11.jsx)(TooltipContent, { side: "bottom", children: t("history.threadHistory") })
2300
+ ] }),
2112
2301
  /* @__PURE__ */ (0, import_jsx_runtime11.jsxs)(SheetContent, { side: "right", className: "w-80 p-0", children: [
2113
2302
  /* @__PURE__ */ (0, import_jsx_runtime11.jsx)(SheetHeader, { className: "border-b p-4", children: /* @__PURE__ */ (0, import_jsx_runtime11.jsx)(SheetTitle, { children: t("history.title") }) }),
2114
2303
  /* @__PURE__ */ (0, import_jsx_runtime11.jsx)("div", { className: "p-4", children: /* @__PURE__ */ (0, import_jsx_runtime11.jsxs)(
@@ -2197,6 +2386,7 @@ function PendingFollowUps({
2197
2386
  onSendNow,
2198
2387
  onEdit,
2199
2388
  onRemove,
2389
+ attachToComposer = true,
2200
2390
  className
2201
2391
  }) {
2202
2392
  const { t } = useChatkitTranslation();
@@ -2219,8 +2409,9 @@ function PendingFollowUps({
2219
2409
  "div",
2220
2410
  {
2221
2411
  className: cn(
2222
- "space-y-2 mx-2 p-2 border border-border border-b-0",
2223
- rounded.top,
2412
+ "space-y-2 mx-2 p-2 border border-border",
2413
+ attachToComposer ? "border-b-0" : null,
2414
+ attachToComposer ? rounded.top : rounded.panel,
2224
2415
  className
2225
2416
  ),
2226
2417
  children: /* @__PURE__ */ (0, import_jsx_runtime12.jsxs)("div", { className: "space-y-1", children: [
@@ -2451,162 +2642,899 @@ function PendingFollowUps({
2451
2642
  );
2452
2643
  }
2453
2644
 
2454
- // src/components/thread/messages/ai.tsx
2455
- var React15 = __toESM(require("react"), 1);
2456
- var import_lucide_react8 = require("lucide-react");
2457
-
2458
- // src/components/ui/badge.tsx
2645
+ // src/components/composer/pending-todos.tsx
2459
2646
  var React11 = __toESM(require("react"), 1);
2647
+ var import_lucide_react6 = require("lucide-react");
2460
2648
  var import_jsx_runtime13 = require("react/jsx-runtime");
2461
- var base = "inline-flex items-center rounded-full border border-transparent px-2.5 py-0.5 text-xs font-medium transition-colors focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring focus-visible:ring-offset-2 ring-offset-background";
2462
- var variants = {
2463
- default: "bg-primary text-primary-foreground",
2464
- secondary: "bg-secondary text-secondary-foreground",
2465
- outline: "border-input text-foreground"
2466
- };
2467
- var Badge = React11.forwardRef(
2468
- ({ className, variant = "default", ...props }, ref) => {
2469
- return /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("span", { ref, className: cn(base, variants[variant], className), ...props });
2649
+ function useRoundedClasses2() {
2650
+ const { theme } = useTheme();
2651
+ return {
2652
+ top: theme.radius ? {
2653
+ pill: "rounded-t-full",
2654
+ round: "rounded-t-xl",
2655
+ soft: "rounded-t-lg",
2656
+ sharp: "rounded-t-none"
2657
+ }[theme.radius] : "rounded-t-lg",
2658
+ panel: getRoundedClass(theme.radius, "rounded-lg")
2659
+ };
2660
+ }
2661
+ function TodoStatusIcon({ status }) {
2662
+ if (status === "completed") {
2663
+ return /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(import_lucide_react6.CheckCircle2, { className: "mt-1 h-4 w-4 shrink-0 text-emerald-600" });
2470
2664
  }
2471
- );
2472
- Badge.displayName = "Badge";
2473
-
2474
- // src/components/ui/card.tsx
2475
- var React12 = __toESM(require("react"), 1);
2476
- var import_jsx_runtime14 = require("react/jsx-runtime");
2477
- var Card = React12.forwardRef(
2478
- ({ className, ...props }, ref) => /* @__PURE__ */ (0, import_jsx_runtime14.jsx)(
2665
+ if (status === "in_progress") {
2666
+ return /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(import_lucide_react6.CircleDashed, { className: "mt-1 h-4 w-4 shrink-0 text-foreground/70" });
2667
+ }
2668
+ return /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(import_lucide_react6.Circle, { className: "mt-1 h-4 w-4 shrink-0 text-muted-foreground" });
2669
+ }
2670
+ function PendingTodos({
2671
+ snapshot,
2672
+ attachToComposer = true,
2673
+ className
2674
+ }) {
2675
+ const { t } = useChatkitTranslation();
2676
+ const rounded = useRoundedClasses2();
2677
+ const listId = React11.useId();
2678
+ const [isCollapsed, setIsCollapsed] = React11.useState(false);
2679
+ React11.useEffect(() => {
2680
+ setIsCollapsed(false);
2681
+ }, [snapshot?.componentId]);
2682
+ if (!snapshot || snapshot.items.length === 0) {
2683
+ return null;
2684
+ }
2685
+ const completedCount = countCompletedTodos(snapshot.items);
2686
+ return /* @__PURE__ */ (0, import_jsx_runtime13.jsxs)(
2479
2687
  "div",
2480
2688
  {
2481
- ref,
2689
+ "aria-live": "polite",
2482
2690
  className: cn(
2483
- "rounded-xl border bg-background/80 text-foreground shadow-[0_14px_40px_-30px_rgba(15,23,42,0.5)] backdrop-blur",
2691
+ "mx-2 border border-border bg-background/95 px-3 py-3 shadow-sm",
2692
+ attachToComposer ? "border-b-0" : null,
2693
+ attachToComposer ? rounded.top : rounded.panel,
2484
2694
  className
2485
2695
  ),
2486
- ...props
2696
+ children: [
2697
+ /* @__PURE__ */ (0, import_jsx_runtime13.jsxs)(
2698
+ "button",
2699
+ {
2700
+ type: "button",
2701
+ className: "flex w-full items-center justify-between gap-3 text-left",
2702
+ "aria-expanded": !isCollapsed,
2703
+ "aria-controls": listId,
2704
+ onClick: () => setIsCollapsed((prev) => !prev),
2705
+ children: [
2706
+ /* @__PURE__ */ (0, import_jsx_runtime13.jsxs)("div", { className: "flex min-w-0 items-center gap-2 text-sm font-medium text-foreground", children: [
2707
+ /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(import_lucide_react6.ListTodo, { className: "h-4 w-4 shrink-0 text-muted-foreground" }),
2708
+ /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("span", { className: "truncate", children: t("chat.todos.summary", {
2709
+ total: snapshot.items.length,
2710
+ completed: completedCount
2711
+ }) })
2712
+ ] }),
2713
+ /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("div", { className: "flex items-center shrink-0", children: /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(
2714
+ import_lucide_react6.ChevronDown,
2715
+ {
2716
+ className: cn(
2717
+ "h-4 w-4 text-muted-foreground transition-transform",
2718
+ isCollapsed ? null : "rotate-180"
2719
+ )
2720
+ }
2721
+ ) })
2722
+ ]
2723
+ }
2724
+ ),
2725
+ !isCollapsed && /* @__PURE__ */ (0, import_jsx_runtime13.jsx)("ol", { id: listId, className: "mt-3 space-y-2.5", children: snapshot.items.map((item, index) => /* @__PURE__ */ (0, import_jsx_runtime13.jsxs)(
2726
+ "li",
2727
+ {
2728
+ className: "grid min-w-0 grid-cols-[16px_24px_minmax(0,1fr)] items-start gap-2 overflow-hidden",
2729
+ children: [
2730
+ /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(TodoStatusIcon, { status: item.status }),
2731
+ /* @__PURE__ */ (0, import_jsx_runtime13.jsxs)(
2732
+ "span",
2733
+ {
2734
+ className: cn(
2735
+ "text-sm leading-6 text-foreground",
2736
+ item.status === "completed" ? "text-muted-foreground" : null
2737
+ ),
2738
+ children: [
2739
+ index + 1,
2740
+ "."
2741
+ ]
2742
+ }
2743
+ ),
2744
+ /* @__PURE__ */ (0, import_jsx_runtime13.jsx)(
2745
+ "span",
2746
+ {
2747
+ title: item.content,
2748
+ className: cn(
2749
+ "block min-w-0 truncate text-sm leading-6 text-foreground",
2750
+ item.status === "completed" ? "text-muted-foreground line-through" : item.status === "in_progress" ? "font-medium" : null
2751
+ ),
2752
+ children: item.content
2753
+ }
2754
+ )
2755
+ ]
2756
+ },
2757
+ item.id
2758
+ )) })
2759
+ ]
2487
2760
  }
2488
- )
2489
- );
2490
- Card.displayName = "Card";
2491
- var CardHeader = React12.forwardRef(
2492
- ({ className, ...props }, ref) => /* @__PURE__ */ (0, import_jsx_runtime14.jsx)("div", { ref, className: cn("flex flex-col gap-1.5 px-6 pt-6", className), ...props })
2493
- );
2494
- CardHeader.displayName = "CardHeader";
2495
- var CardTitle = React12.forwardRef(({ className, ...props }, ref) => /* @__PURE__ */ (0, import_jsx_runtime14.jsx)("h3", { ref, className: cn("text-lg font-semibold leading-tight", className), ...props }));
2496
- CardTitle.displayName = "CardTitle";
2497
- var CardDescription = React12.forwardRef(({ className, ...props }, ref) => /* @__PURE__ */ (0, import_jsx_runtime14.jsx)("p", { ref, className: cn("text-sm text-muted-foreground", className), ...props }));
2498
- CardDescription.displayName = "CardDescription";
2499
- var CardContent = React12.forwardRef(
2500
- ({ className, ...props }, ref) => /* @__PURE__ */ (0, import_jsx_runtime14.jsx)("div", { ref, className: cn("px-6 pb-6", className), ...props })
2501
- );
2502
- CardContent.displayName = "CardContent";
2503
- var CardFooter = React12.forwardRef(
2504
- ({ className, ...props }, ref) => /* @__PURE__ */ (0, import_jsx_runtime14.jsx)("div", { ref, className: cn("flex items-center px-6 pb-6", className), ...props })
2505
- );
2506
- CardFooter.displayName = "CardFooter";
2507
- var CardAction = React12.forwardRef(
2508
- ({ className, ...props }, ref) => /* @__PURE__ */ (0, import_jsx_runtime14.jsx)("div", { ref, className: cn("ml-auto flex items-center", className), ...props })
2509
- );
2510
- CardAction.displayName = "CardAction";
2511
-
2512
- // src/components/ui/tabs.tsx
2513
- var React13 = __toESM(require("react"), 1);
2514
- var import_jsx_runtime15 = require("react/jsx-runtime");
2515
- var TabsContext = React13.createContext(null);
2516
- function Tabs({ className, defaultValue, value, onValueChange, ...props }) {
2517
- const [internalValue, setInternalValue] = React13.useState(defaultValue ?? "");
2518
- const activeValue = value ?? internalValue;
2519
- const setValue = React13.useCallback(
2520
- (nextValue) => {
2521
- if (value === void 0) setInternalValue(nextValue);
2522
- onValueChange?.(nextValue);
2523
- },
2524
- [onValueChange, value]
2525
2761
  );
2526
- return /* @__PURE__ */ (0, import_jsx_runtime15.jsx)(TabsContext.Provider, { value: { value: activeValue, setValue }, children: /* @__PURE__ */ (0, import_jsx_runtime15.jsx)("div", { className: cn("w-full", className), ...props }) });
2527
2762
  }
2528
- var TabsList = React13.forwardRef(
2529
- ({ className, ...props }, ref) => /* @__PURE__ */ (0, import_jsx_runtime15.jsx)(
2530
- "div",
2531
- {
2532
- ref,
2533
- className: cn(
2534
- "inline-flex items-center justify-center rounded-lg bg-muted p-1 text-muted-foreground",
2535
- className
2536
- ),
2537
- role: "tablist",
2538
- ...props
2539
- }
2540
- )
2541
- );
2542
- TabsList.displayName = "TabsList";
2543
- var TabsTrigger = React13.forwardRef(
2544
- ({ className, value, onClick, ...props }, ref) => {
2545
- const context = React13.useContext(TabsContext);
2546
- if (!context) {
2547
- throw new Error("TabsTrigger must be used within Tabs");
2763
+
2764
+ // src/components/composer/request-user-input-panel.tsx
2765
+ var React12 = __toESM(require("react"), 1);
2766
+ var import_lucide_react7 = require("lucide-react");
2767
+ var import_jsx_runtime14 = require("react/jsx-runtime");
2768
+ function useRoundedClasses3() {
2769
+ const { theme } = useTheme();
2770
+ const density = theme.density ?? "normal";
2771
+ const densityClasses = {
2772
+ compact: {
2773
+ section: "px-3.5 py-2",
2774
+ eyebrow: "mb-0 text-[11px]",
2775
+ title: "text-[15px] leading-5",
2776
+ pager: "gap-1.5 text-xs",
2777
+ pagerButton: "h-6 w-6",
2778
+ pagerIcon: "h-3.5 w-3.5",
2779
+ choices: "mt-2.5 space-y-0.5",
2780
+ row: "min-h-8 grid-cols-[28px_minmax(0,1fr)_auto] gap-2 px-2.5 py-1",
2781
+ otherRow: "min-h-8 grid-cols-[28px_minmax(0,1fr)] gap-2 px-2.5 py-1",
2782
+ input: "h-6",
2783
+ footer: "mt-2.5 gap-2",
2784
+ dismissButton: "h-7",
2785
+ continueButton: "h-8 px-3.5",
2786
+ continueIcon: "h-5 min-w-5"
2787
+ },
2788
+ normal: {
2789
+ section: "px-4 py-2.5",
2790
+ eyebrow: "mb-0.5 text-xs",
2791
+ title: "text-base leading-5",
2792
+ pager: "gap-2 text-sm",
2793
+ pagerButton: "h-7 w-7",
2794
+ pagerIcon: "h-4 w-4",
2795
+ choices: "mt-3 space-y-0.5",
2796
+ row: "min-h-9 grid-cols-[30px_minmax(0,1fr)_auto] gap-2.5 px-2.5 py-1.5",
2797
+ otherRow: "min-h-9 grid-cols-[30px_minmax(0,1fr)] gap-2.5 px-2.5 py-1.5",
2798
+ input: "h-6",
2799
+ footer: "mt-3 gap-3",
2800
+ dismissButton: "h-7",
2801
+ continueButton: "h-8 px-4",
2802
+ continueIcon: "h-5 min-w-5"
2803
+ },
2804
+ spacious: {
2805
+ section: "px-5 py-3",
2806
+ eyebrow: "mb-0.5 text-xs",
2807
+ title: "text-base leading-5",
2808
+ pager: "gap-2 text-sm",
2809
+ pagerButton: "h-7 w-7",
2810
+ pagerIcon: "h-4 w-4",
2811
+ choices: "mt-4 space-y-1",
2812
+ row: "min-h-10 grid-cols-[32px_minmax(0,1fr)_auto] gap-3 px-3 py-2",
2813
+ otherRow: "min-h-10 grid-cols-[32px_minmax(0,1fr)] gap-3 px-3 py-2",
2814
+ input: "h-7",
2815
+ footer: "mt-4 gap-3",
2816
+ dismissButton: "h-8",
2817
+ continueButton: "h-9 px-4",
2818
+ continueIcon: "h-5 min-w-5"
2548
2819
  }
2549
- const isActive = context.value === value;
2550
- return /* @__PURE__ */ (0, import_jsx_runtime15.jsx)(
2551
- "button",
2552
- {
2553
- ref,
2554
- type: "button",
2555
- role: "tab",
2556
- "aria-selected": isActive,
2557
- "data-state": isActive ? "active" : "inactive",
2558
- className: cn(
2559
- "inline-flex items-center justify-center whitespace-nowrap rounded-md px-3 py-1 text-sm font-medium transition-all focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring focus-visible:ring-offset-2 ring-offset-background disabled:pointer-events-none disabled:opacity-50 data-[state=active]:bg-background data-[state=active]:text-foreground data-[state=active]:shadow-sm",
2560
- className
2561
- ),
2562
- onClick: (event) => {
2563
- context.setValue(value);
2564
- onClick?.(event);
2565
- },
2566
- ...props
2567
- }
2568
- );
2820
+ }[density] ?? {
2821
+ section: "px-4 py-2.5",
2822
+ eyebrow: "mb-0.5 text-xs",
2823
+ title: "text-base leading-5",
2824
+ pager: "gap-2 text-sm",
2825
+ pagerButton: "h-7 w-7",
2826
+ pagerIcon: "h-4 w-4",
2827
+ choices: "mt-3 space-y-0.5",
2828
+ row: "min-h-9 grid-cols-[30px_minmax(0,1fr)_auto] gap-2.5 px-2.5 py-1.5",
2829
+ otherRow: "min-h-9 grid-cols-[30px_minmax(0,1fr)] gap-2.5 px-2.5 py-1.5",
2830
+ input: "h-6",
2831
+ footer: "mt-3 gap-3",
2832
+ dismissButton: "h-7",
2833
+ continueButton: "h-8 px-4",
2834
+ continueIcon: "h-5 min-w-5"
2835
+ };
2836
+ return {
2837
+ top: theme.radius ? {
2838
+ pill: "rounded-t-3xl",
2839
+ round: "rounded-t-xl",
2840
+ soft: "rounded-t-lg",
2841
+ sharp: "rounded-t-none"
2842
+ }[theme.radius] : "rounded-t-lg",
2843
+ panel: getRoundedClass(theme.radius, "rounded-lg"),
2844
+ control: getRoundedClass(theme.radius, "rounded-md"),
2845
+ density: densityClasses
2846
+ };
2847
+ }
2848
+ function parseRecommendedLabel(label) {
2849
+ const recommendedPattern = /\s*(?:\((?:recommended)\)|(推荐))\s*$/i;
2850
+ return {
2851
+ label: label.replace(recommendedPattern, "").trim() || label,
2852
+ recommended: recommendedPattern.test(label)
2853
+ };
2854
+ }
2855
+ function getAnswerForQuestion(question, draft) {
2856
+ if (!draft) return null;
2857
+ if (draft.type === "other") {
2858
+ const value = draft.otherText.trim();
2859
+ if (!value) return null;
2860
+ return {
2861
+ id: question.id,
2862
+ question: question.question,
2863
+ type: "other",
2864
+ value
2865
+ };
2569
2866
  }
2570
- );
2571
- TabsTrigger.displayName = "TabsTrigger";
2572
- var TabsContent = React13.forwardRef(
2573
- ({ className, value, ...props }, ref) => {
2574
- const context = React13.useContext(TabsContext);
2575
- if (!context) {
2576
- throw new Error("TabsContent must be used within Tabs");
2577
- }
2578
- if (context.value !== value) return null;
2579
- return /* @__PURE__ */ (0, import_jsx_runtime15.jsx)(
2580
- "div",
2581
- {
2582
- ref,
2583
- role: "tabpanel",
2584
- className: cn(
2585
- "mt-4 focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring focus-visible:ring-offset-2 ring-offset-background",
2586
- className
2587
- ),
2588
- ...props
2589
- }
2867
+ const option = question.options[draft.optionIndex];
2868
+ if (!option) return null;
2869
+ return {
2870
+ id: question.id,
2871
+ question: question.question,
2872
+ type: "option",
2873
+ value: option.label,
2874
+ label: option.label,
2875
+ description: option.description
2876
+ };
2877
+ }
2878
+ function getSelectedChoiceIndex(question, draft) {
2879
+ if (!draft) return -1;
2880
+ if (draft.type === "other") return question.options.length;
2881
+ return draft.optionIndex;
2882
+ }
2883
+ function RequestUserInputPanel({
2884
+ request,
2885
+ onSubmit,
2886
+ onDismiss,
2887
+ attachToComposer = true,
2888
+ className
2889
+ }) {
2890
+ const { t } = useChatkitTranslation();
2891
+ const rounded = useRoundedClasses3();
2892
+ const [drafts, setDrafts] = React12.useState({});
2893
+ const [currentQuestionIndex, setCurrentQuestionIndex] = React12.useState(0);
2894
+ const otherInputRef = React12.useRef(null);
2895
+ const questions = request?.params.questions ?? [];
2896
+ React12.useEffect(() => {
2897
+ setDrafts({});
2898
+ setCurrentQuestionIndex(0);
2899
+ }, [request?.id]);
2900
+ React12.useEffect(() => {
2901
+ if (questions.length === 0) return;
2902
+ setCurrentQuestionIndex(
2903
+ (index) => Math.min(Math.max(index, 0), questions.length - 1)
2590
2904
  );
2591
- }
2592
- );
2593
- TabsContent.displayName = "TabsContent";
2594
-
2595
- // src/components/thread/markdown-text.tsx
2596
- var import_react_markdown = __toESM(require("react-markdown"), 1);
2597
- var import_remark_gfm = __toESM(require("remark-gfm"), 1);
2598
- var import_rehype_katex = __toESM(require("rehype-katex"), 1);
2599
- var import_remark_math = __toESM(require("remark-math"), 1);
2600
- var import_react6 = require("react");
2601
- var import_lucide_react7 = require("lucide-react");
2602
-
2603
- // src/components/thread/syntax-highlighter.tsx
2604
- var import_react_syntax_highlighter = require("react-syntax-highlighter");
2905
+ }, [questions.length]);
2906
+ const setQuestionDraft = React12.useCallback(
2907
+ (questionId, draft) => {
2908
+ setDrafts((previous) => ({
2909
+ ...previous,
2910
+ [questionId]: draft
2911
+ }));
2912
+ },
2913
+ []
2914
+ );
2915
+ const focusOtherInput = React12.useCallback(() => {
2916
+ window.setTimeout(() => otherInputRef.current?.focus(), 0);
2917
+ }, []);
2918
+ const selectOption = React12.useCallback(
2919
+ (question, optionIndex) => {
2920
+ const previousDraft = drafts[question.id];
2921
+ setQuestionDraft(question.id, {
2922
+ type: "option",
2923
+ optionIndex,
2924
+ otherText: previousDraft?.otherText ?? ""
2925
+ });
2926
+ },
2927
+ [drafts, setQuestionDraft]
2928
+ );
2929
+ const selectOther = React12.useCallback(
2930
+ (question, otherText2) => {
2931
+ const previousDraft = drafts[question.id];
2932
+ setQuestionDraft(question.id, {
2933
+ type: "other",
2934
+ otherText: otherText2 ?? (previousDraft?.type === "other" ? previousDraft.otherText : previousDraft?.otherText) ?? ""
2935
+ });
2936
+ focusOtherInput();
2937
+ },
2938
+ [drafts, focusOtherInput, setQuestionDraft]
2939
+ );
2940
+ const goToQuestion = React12.useCallback(
2941
+ (index) => {
2942
+ if (questions.length === 0) return;
2943
+ setCurrentQuestionIndex(
2944
+ Math.min(Math.max(index, 0), questions.length - 1)
2945
+ );
2946
+ },
2947
+ [questions.length]
2948
+ );
2949
+ const answers = React12.useMemo(
2950
+ () => questions.map((question) => getAnswerForQuestion(question, drafts[question.id])).filter((answer) => Boolean(answer)),
2951
+ [drafts, questions]
2952
+ );
2953
+ const canSubmit = answers.length === questions.length;
2954
+ const currentQuestion = questions[currentQuestionIndex] ?? null;
2955
+ const currentDraft = currentQuestion ? drafts[currentQuestion.id] : void 0;
2956
+ const currentAnswer = currentQuestion ? getAnswerForQuestion(currentQuestion, currentDraft) : null;
2957
+ const isLastQuestion = currentQuestionIndex === questions.length - 1;
2958
+ const buildAnswersFromDrafts = React12.useCallback(
2959
+ (nextDrafts) => questions.map((question) => getAnswerForQuestion(question, nextDrafts[question.id])).filter((answer) => Boolean(answer)),
2960
+ [questions]
2961
+ );
2962
+ const submitOrFocusFirstMissing = React12.useCallback(
2963
+ (nextDrafts) => {
2964
+ const nextAnswers = buildAnswersFromDrafts(nextDrafts);
2965
+ if (nextAnswers.length === questions.length) {
2966
+ onSubmit(nextAnswers);
2967
+ return;
2968
+ }
2969
+ const firstMissingIndex = questions.findIndex(
2970
+ (question) => !getAnswerForQuestion(question, nextDrafts[question.id])
2971
+ );
2972
+ if (firstMissingIndex >= 0) {
2973
+ goToQuestion(firstMissingIndex);
2974
+ }
2975
+ },
2976
+ [buildAnswersFromDrafts, goToQuestion, onSubmit, questions]
2977
+ );
2978
+ const activateOption = React12.useCallback(
2979
+ (question, optionIndex) => {
2980
+ const previousDraft = drafts[question.id];
2981
+ const nextDrafts = {
2982
+ ...drafts,
2983
+ [question.id]: {
2984
+ type: "option",
2985
+ optionIndex,
2986
+ otherText: previousDraft?.otherText ?? ""
2987
+ }
2988
+ };
2989
+ setDrafts(nextDrafts);
2990
+ if (isLastQuestion) {
2991
+ submitOrFocusFirstMissing(nextDrafts);
2992
+ return;
2993
+ }
2994
+ goToQuestion(currentQuestionIndex + 1);
2995
+ },
2996
+ [
2997
+ currentQuestionIndex,
2998
+ drafts,
2999
+ goToQuestion,
3000
+ isLastQuestion,
3001
+ submitOrFocusFirstMissing
3002
+ ]
3003
+ );
3004
+ const chooseChoiceByIndex = React12.useCallback(
3005
+ (choiceIndex) => {
3006
+ if (!currentQuestion) return;
3007
+ if (choiceIndex < 0) return;
3008
+ if (choiceIndex < currentQuestion.options.length) {
3009
+ selectOption(currentQuestion, choiceIndex);
3010
+ return;
3011
+ }
3012
+ if (choiceIndex === currentQuestion.options.length) {
3013
+ selectOther(currentQuestion);
3014
+ }
3015
+ },
3016
+ [currentQuestion, selectOption, selectOther]
3017
+ );
3018
+ const moveCurrentChoice = React12.useCallback(
3019
+ (direction) => {
3020
+ if (!currentQuestion) return;
3021
+ const choiceCount = currentQuestion.options.length + 1;
3022
+ const currentIndex = getSelectedChoiceIndex(currentQuestion, currentDraft);
3023
+ const nextIndex = currentIndex === -1 ? direction === 1 ? 0 : choiceCount - 1 : (currentIndex + direction + choiceCount) % choiceCount;
3024
+ chooseChoiceByIndex(nextIndex);
3025
+ },
3026
+ [chooseChoiceByIndex, currentDraft, currentQuestion]
3027
+ );
3028
+ const handleContinue = React12.useCallback(() => {
3029
+ if (!currentAnswer) return;
3030
+ if (!isLastQuestion) {
3031
+ goToQuestion(currentQuestionIndex + 1);
3032
+ return;
3033
+ }
3034
+ if (canSubmit) {
3035
+ onSubmit(answers);
3036
+ return;
3037
+ }
3038
+ const firstMissingIndex = questions.findIndex(
3039
+ (question) => !getAnswerForQuestion(question, drafts[question.id])
3040
+ );
3041
+ if (firstMissingIndex >= 0) {
3042
+ goToQuestion(firstMissingIndex);
3043
+ }
3044
+ }, [
3045
+ answers,
3046
+ canSubmit,
3047
+ currentAnswer,
3048
+ currentQuestionIndex,
3049
+ drafts,
3050
+ goToQuestion,
3051
+ isLastQuestion,
3052
+ onSubmit,
3053
+ questions
3054
+ ]);
3055
+ React12.useEffect(() => {
3056
+ if (!request) return;
3057
+ const handleKeyDown = (event) => {
3058
+ if (event.isComposing) return;
3059
+ const target = event.target;
3060
+ const targetTag = target?.tagName;
3061
+ const isTypingTarget = target?.isContentEditable || targetTag === "INPUT" || targetTag === "TEXTAREA" || targetTag === "SELECT";
3062
+ if (event.key === "Escape" || event.key === "Esc") {
3063
+ if (onDismiss) {
3064
+ event.preventDefault();
3065
+ onDismiss();
3066
+ }
3067
+ return;
3068
+ }
3069
+ if (isTypingTarget && event.key !== "Enter") {
3070
+ return;
3071
+ }
3072
+ if (event.key === "Enter") {
3073
+ event.preventDefault();
3074
+ handleContinue();
3075
+ return;
3076
+ }
3077
+ if (event.key === "ArrowLeft") {
3078
+ event.preventDefault();
3079
+ goToQuestion(currentQuestionIndex - 1);
3080
+ return;
3081
+ }
3082
+ if (event.key === "ArrowRight") {
3083
+ event.preventDefault();
3084
+ goToQuestion(currentQuestionIndex + 1);
3085
+ return;
3086
+ }
3087
+ if (event.key === "ArrowUp") {
3088
+ event.preventDefault();
3089
+ moveCurrentChoice(-1);
3090
+ return;
3091
+ }
3092
+ if (event.key === "ArrowDown") {
3093
+ event.preventDefault();
3094
+ moveCurrentChoice(1);
3095
+ return;
3096
+ }
3097
+ if (/^[1-9]$/.test(event.key)) {
3098
+ const choiceIndex = Number(event.key) - 1;
3099
+ if (currentQuestion && choiceIndex < currentQuestion.options.length + 1) {
3100
+ event.preventDefault();
3101
+ chooseChoiceByIndex(choiceIndex);
3102
+ }
3103
+ }
3104
+ };
3105
+ document.addEventListener("keydown", handleKeyDown);
3106
+ return () => document.removeEventListener("keydown", handleKeyDown);
3107
+ }, [
3108
+ chooseChoiceByIndex,
3109
+ currentQuestion,
3110
+ currentQuestionIndex,
3111
+ goToQuestion,
3112
+ handleContinue,
3113
+ moveCurrentChoice,
3114
+ onDismiss,
3115
+ request
3116
+ ]);
3117
+ if (!request || !currentQuestion) {
3118
+ return null;
3119
+ }
3120
+ const handleOtherTextChange = (value) => {
3121
+ setDrafts((previous) => ({
3122
+ ...previous,
3123
+ [currentQuestion.id]: {
3124
+ type: "other",
3125
+ otherText: value
3126
+ }
3127
+ }));
3128
+ };
3129
+ const otherText = currentDraft?.otherText ?? "";
3130
+ return /* @__PURE__ */ (0, import_jsx_runtime14.jsxs)(
3131
+ "section",
3132
+ {
3133
+ "aria-label": t("composer.requestUserInput.title"),
3134
+ "aria-live": "polite",
3135
+ className: cn(
3136
+ "mx-2 border border-border bg-background/95 shadow-sm",
3137
+ rounded.density.section,
3138
+ attachToComposer ? "border-b-0" : null,
3139
+ attachToComposer ? rounded.top : rounded.panel,
3140
+ className
3141
+ ),
3142
+ children: [
3143
+ /* @__PURE__ */ (0, import_jsx_runtime14.jsxs)("div", { className: "flex items-start justify-between gap-3", children: [
3144
+ /* @__PURE__ */ (0, import_jsx_runtime14.jsxs)("div", { className: "min-w-0", children: [
3145
+ /* @__PURE__ */ (0, import_jsx_runtime14.jsx)(
3146
+ "div",
3147
+ {
3148
+ className: cn(
3149
+ "font-medium text-muted-foreground",
3150
+ rounded.density.eyebrow
3151
+ ),
3152
+ children: currentQuestion.header
3153
+ }
3154
+ ),
3155
+ /* @__PURE__ */ (0, import_jsx_runtime14.jsx)(
3156
+ "h3",
3157
+ {
3158
+ className: cn(
3159
+ "font-semibold text-foreground",
3160
+ rounded.density.title
3161
+ ),
3162
+ children: currentQuestion.question
3163
+ }
3164
+ )
3165
+ ] }),
3166
+ questions.length > 1 ? /* @__PURE__ */ (0, import_jsx_runtime14.jsxs)(
3167
+ "div",
3168
+ {
3169
+ className: cn(
3170
+ "flex shrink-0 items-center font-medium text-muted-foreground",
3171
+ rounded.density.pager
3172
+ ),
3173
+ children: [
3174
+ /* @__PURE__ */ (0, import_jsx_runtime14.jsx)(
3175
+ "button",
3176
+ {
3177
+ type: "button",
3178
+ onClick: () => goToQuestion(currentQuestionIndex - 1),
3179
+ disabled: currentQuestionIndex === 0,
3180
+ className: cn(
3181
+ "inline-flex items-center justify-center rounded-full hover:bg-muted disabled:pointer-events-none disabled:opacity-35",
3182
+ rounded.density.pagerButton
3183
+ ),
3184
+ "aria-label": t("composer.requestUserInput.previousQuestion"),
3185
+ children: /* @__PURE__ */ (0, import_jsx_runtime14.jsx)(import_lucide_react7.ChevronLeft, { className: rounded.density.pagerIcon })
3186
+ }
3187
+ ),
3188
+ /* @__PURE__ */ (0, import_jsx_runtime14.jsx)("span", { className: "min-w-12 text-center", children: t("composer.requestUserInput.questionProgress", {
3189
+ current: currentQuestionIndex + 1,
3190
+ total: questions.length
3191
+ }) }),
3192
+ /* @__PURE__ */ (0, import_jsx_runtime14.jsx)(
3193
+ "button",
3194
+ {
3195
+ type: "button",
3196
+ onClick: () => goToQuestion(currentQuestionIndex + 1),
3197
+ disabled: currentQuestionIndex === questions.length - 1,
3198
+ className: cn(
3199
+ "inline-flex items-center justify-center rounded-full hover:bg-muted disabled:pointer-events-none disabled:opacity-35",
3200
+ rounded.density.pagerButton
3201
+ ),
3202
+ "aria-label": t("composer.requestUserInput.nextQuestion"),
3203
+ children: /* @__PURE__ */ (0, import_jsx_runtime14.jsx)(import_lucide_react7.ChevronRight, { className: rounded.density.pagerIcon })
3204
+ }
3205
+ )
3206
+ ]
3207
+ }
3208
+ ) : null
3209
+ ] }),
3210
+ /* @__PURE__ */ (0, import_jsx_runtime14.jsxs)("div", { className: rounded.density.choices, children: [
3211
+ currentQuestion.options.map((option, optionIndex) => {
3212
+ const selected = currentDraft?.type === "option" && currentDraft.optionIndex === optionIndex;
3213
+ const parsedLabel = parseRecommendedLabel(option.label);
3214
+ return /* @__PURE__ */ (0, import_jsx_runtime14.jsxs)(
3215
+ "div",
3216
+ {
3217
+ role: "button",
3218
+ tabIndex: 0,
3219
+ onClick: () => activateOption(currentQuestion, optionIndex),
3220
+ onKeyDown: (event) => {
3221
+ if (event.key === "Enter" || event.key === " ") {
3222
+ event.preventDefault();
3223
+ event.stopPropagation();
3224
+ activateOption(currentQuestion, optionIndex);
3225
+ }
3226
+ },
3227
+ "aria-pressed": selected,
3228
+ "aria-label": `${optionIndex + 1}. ${option.label}`,
3229
+ className: cn(
3230
+ "grid cursor-pointer items-center text-left transition-colors",
3231
+ rounded.density.row,
3232
+ rounded.panel,
3233
+ selected ? "bg-muted text-foreground" : "text-foreground/90 hover:bg-muted/55"
3234
+ ),
3235
+ children: [
3236
+ /* @__PURE__ */ (0, import_jsx_runtime14.jsxs)("span", { className: "text-sm font-semibold text-muted-foreground", children: [
3237
+ optionIndex + 1,
3238
+ "."
3239
+ ] }),
3240
+ /* @__PURE__ */ (0, import_jsx_runtime14.jsxs)("span", { className: "min-w-0", children: [
3241
+ /* @__PURE__ */ (0, import_jsx_runtime14.jsx)("span", { className: "inline min-w-0 text-sm font-semibold leading-5", children: parsedLabel.label }),
3242
+ parsedLabel.recommended ? /* @__PURE__ */ (0, import_jsx_runtime14.jsxs)("span", { className: "ml-1.5 inline-flex items-center gap-1 text-sm font-semibold text-primary", children: [
3243
+ /* @__PURE__ */ (0, import_jsx_runtime14.jsx)(import_lucide_react7.Check, { className: "h-3.5 w-3.5" }),
3244
+ "(",
3245
+ t("composer.requestUserInput.recommended"),
3246
+ ")"
3247
+ ] }) : null
3248
+ ] }),
3249
+ /* @__PURE__ */ (0, import_jsx_runtime14.jsxs)("span", { className: "flex items-center gap-2 text-muted-foreground", children: [
3250
+ option.description ? /* @__PURE__ */ (0, import_jsx_runtime14.jsxs)(Tooltip, { children: [
3251
+ /* @__PURE__ */ (0, import_jsx_runtime14.jsx)(TooltipTrigger, { asChild: true, children: /* @__PURE__ */ (0, import_jsx_runtime14.jsx)(
3252
+ "button",
3253
+ {
3254
+ type: "button",
3255
+ onClick: (event) => event.stopPropagation(),
3256
+ onKeyDown: (event) => event.stopPropagation(),
3257
+ title: option.description,
3258
+ className: "inline-flex h-7 w-7 items-center justify-center rounded-full hover:bg-background/80 hover:text-foreground",
3259
+ "aria-label": t("composer.requestUserInput.optionInfo", {
3260
+ label: parsedLabel.label
3261
+ }),
3262
+ children: /* @__PURE__ */ (0, import_jsx_runtime14.jsx)(import_lucide_react7.Info, { className: "h-4 w-4" })
3263
+ }
3264
+ ) }),
3265
+ /* @__PURE__ */ (0, import_jsx_runtime14.jsx)(
3266
+ TooltipContent,
3267
+ {
3268
+ side: "top",
3269
+ sideOffset: 6,
3270
+ className: "max-w-72 text-left leading-5",
3271
+ children: option.description
3272
+ }
3273
+ )
3274
+ ] }) : null,
3275
+ selected ? /* @__PURE__ */ (0, import_jsx_runtime14.jsxs)(
3276
+ "span",
3277
+ {
3278
+ "aria-hidden": "true",
3279
+ className: "hidden items-center gap-0.5 sm:flex",
3280
+ children: [
3281
+ /* @__PURE__ */ (0, import_jsx_runtime14.jsx)(import_lucide_react7.ArrowUp, { className: "h-4 w-4 opacity-45" }),
3282
+ /* @__PURE__ */ (0, import_jsx_runtime14.jsx)(import_lucide_react7.ArrowDown, { className: "h-4 w-4 opacity-45" })
3283
+ ]
3284
+ }
3285
+ ) : null
3286
+ ] })
3287
+ ]
3288
+ },
3289
+ `${currentQuestion.id}-${optionIndex}`
3290
+ );
3291
+ }),
3292
+ /* @__PURE__ */ (0, import_jsx_runtime14.jsxs)(
3293
+ "label",
3294
+ {
3295
+ className: cn(
3296
+ "grid items-center transition-colors",
3297
+ rounded.density.otherRow,
3298
+ rounded.panel,
3299
+ currentDraft?.type === "other" ? "bg-muted text-foreground" : "hover:bg-muted/55"
3300
+ ),
3301
+ children: [
3302
+ /* @__PURE__ */ (0, import_jsx_runtime14.jsxs)("span", { className: "text-sm font-semibold text-muted-foreground", children: [
3303
+ currentQuestion.options.length + 1,
3304
+ "."
3305
+ ] }),
3306
+ /* @__PURE__ */ (0, import_jsx_runtime14.jsx)("span", { className: "grid min-w-0 grid-cols-[auto_minmax(0,1fr)] items-center gap-3", children: /* @__PURE__ */ (0, import_jsx_runtime14.jsx)(
3307
+ "input",
3308
+ {
3309
+ ref: otherInputRef,
3310
+ value: otherText,
3311
+ onChange: (event) => handleOtherTextChange(event.target.value),
3312
+ onFocus: () => selectOther(currentQuestion, otherText),
3313
+ placeholder: t("composer.requestUserInput.otherPlaceholder"),
3314
+ className: cn(
3315
+ "min-w-0 bg-transparent text-sm text-foreground outline-none placeholder:text-muted-foreground",
3316
+ rounded.density.input
3317
+ )
3318
+ }
3319
+ ) })
3320
+ ]
3321
+ }
3322
+ )
3323
+ ] }),
3324
+ /* @__PURE__ */ (0, import_jsx_runtime14.jsxs)(
3325
+ "div",
3326
+ {
3327
+ className: cn(
3328
+ "flex items-center justify-end",
3329
+ rounded.density.footer
3330
+ ),
3331
+ children: [
3332
+ onDismiss ? /* @__PURE__ */ (0, import_jsx_runtime14.jsxs)(
3333
+ "button",
3334
+ {
3335
+ type: "button",
3336
+ onClick: onDismiss,
3337
+ className: cn(
3338
+ "inline-flex items-center gap-2 text-sm font-semibold text-muted-foreground transition-colors hover:text-foreground",
3339
+ rounded.density.dismissButton
3340
+ ),
3341
+ children: [
3342
+ t("composer.requestUserInput.dismiss"),
3343
+ /* @__PURE__ */ (0, import_jsx_runtime14.jsx)("kbd", { className: "rounded-full bg-muted px-2 py-1 text-xs font-semibold text-muted-foreground", children: "ESC" })
3344
+ ]
3345
+ }
3346
+ ) : null,
3347
+ /* @__PURE__ */ (0, import_jsx_runtime14.jsxs)(
3348
+ "button",
3349
+ {
3350
+ type: "button",
3351
+ disabled: !currentAnswer,
3352
+ onClick: handleContinue,
3353
+ className: cn(
3354
+ "inline-flex items-center gap-2 bg-primary text-sm font-semibold text-background transition-all",
3355
+ rounded.density.continueButton,
3356
+ "hover:bg-primary/90 disabled:cursor-not-allowed disabled:opacity-40",
3357
+ rounded.panel
3358
+ ),
3359
+ children: [
3360
+ t("composer.requestUserInput.continue"),
3361
+ /* @__PURE__ */ (0, import_jsx_runtime14.jsx)(
3362
+ "span",
3363
+ {
3364
+ className: cn(
3365
+ "inline-flex items-center justify-center rounded-full bg-background/20",
3366
+ rounded.density.continueIcon
3367
+ ),
3368
+ children: /* @__PURE__ */ (0, import_jsx_runtime14.jsx)(import_lucide_react7.CornerDownLeft, { className: "h-3.5 w-3.5" })
3369
+ }
3370
+ )
3371
+ ]
3372
+ }
3373
+ )
3374
+ ]
3375
+ }
3376
+ )
3377
+ ]
3378
+ }
3379
+ );
3380
+ }
3381
+
3382
+ // src/components/thread/messages/ai.tsx
3383
+ var React19 = __toESM(require("react"), 1);
3384
+ var import_lucide_react12 = require("lucide-react");
3385
+
3386
+ // src/components/ui/badge.tsx
3387
+ var React13 = __toESM(require("react"), 1);
3388
+ var import_jsx_runtime15 = require("react/jsx-runtime");
3389
+ var base = "inline-flex items-center rounded-full border border-transparent px-2.5 py-0.5 text-xs font-medium transition-colors focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring focus-visible:ring-offset-2 ring-offset-background";
3390
+ var variants = {
3391
+ default: "bg-primary text-primary-foreground",
3392
+ secondary: "bg-secondary text-secondary-foreground",
3393
+ outline: "border-input text-foreground"
3394
+ };
3395
+ var Badge = React13.forwardRef(
3396
+ ({ className, variant = "default", ...props }, ref) => {
3397
+ return /* @__PURE__ */ (0, import_jsx_runtime15.jsx)("span", { ref, className: cn(base, variants[variant], className), ...props });
3398
+ }
3399
+ );
3400
+ Badge.displayName = "Badge";
3401
+
3402
+ // src/components/ui/card.tsx
3403
+ var React14 = __toESM(require("react"), 1);
3404
+ var import_jsx_runtime16 = require("react/jsx-runtime");
3405
+ var Card = React14.forwardRef(
3406
+ ({ className, ...props }, ref) => /* @__PURE__ */ (0, import_jsx_runtime16.jsx)(
3407
+ "div",
3408
+ {
3409
+ ref,
3410
+ className: cn(
3411
+ "rounded-xl border bg-background/80 text-foreground shadow-[0_14px_40px_-30px_rgba(15,23,42,0.5)] backdrop-blur",
3412
+ className
3413
+ ),
3414
+ ...props
3415
+ }
3416
+ )
3417
+ );
3418
+ Card.displayName = "Card";
3419
+ var CardHeader = React14.forwardRef(
3420
+ ({ className, ...props }, ref) => /* @__PURE__ */ (0, import_jsx_runtime16.jsx)("div", { ref, className: cn("flex flex-col gap-1.5 px-6 pt-6", className), ...props })
3421
+ );
3422
+ CardHeader.displayName = "CardHeader";
3423
+ var CardTitle = React14.forwardRef(({ className, ...props }, ref) => /* @__PURE__ */ (0, import_jsx_runtime16.jsx)("h3", { ref, className: cn("text-lg font-semibold leading-tight", className), ...props }));
3424
+ CardTitle.displayName = "CardTitle";
3425
+ var CardDescription = React14.forwardRef(({ className, ...props }, ref) => /* @__PURE__ */ (0, import_jsx_runtime16.jsx)("p", { ref, className: cn("text-sm text-muted-foreground", className), ...props }));
3426
+ CardDescription.displayName = "CardDescription";
3427
+ var CardContent = React14.forwardRef(
3428
+ ({ className, ...props }, ref) => /* @__PURE__ */ (0, import_jsx_runtime16.jsx)("div", { ref, className: cn("px-6 pb-6", className), ...props })
3429
+ );
3430
+ CardContent.displayName = "CardContent";
3431
+ var CardFooter = React14.forwardRef(
3432
+ ({ className, ...props }, ref) => /* @__PURE__ */ (0, import_jsx_runtime16.jsx)("div", { ref, className: cn("flex items-center px-6 pb-6", className), ...props })
3433
+ );
3434
+ CardFooter.displayName = "CardFooter";
3435
+ var CardAction = React14.forwardRef(
3436
+ ({ className, ...props }, ref) => /* @__PURE__ */ (0, import_jsx_runtime16.jsx)("div", { ref, className: cn("ml-auto flex items-center", className), ...props })
3437
+ );
3438
+ CardAction.displayName = "CardAction";
3439
+
3440
+ // src/components/ui/tabs.tsx
3441
+ var React15 = __toESM(require("react"), 1);
3442
+ var import_jsx_runtime17 = require("react/jsx-runtime");
3443
+ var TabsContext = React15.createContext(null);
3444
+ function Tabs({ className, defaultValue, value, onValueChange, ...props }) {
3445
+ const [internalValue, setInternalValue] = React15.useState(defaultValue ?? "");
3446
+ const activeValue = value ?? internalValue;
3447
+ const setValue = React15.useCallback(
3448
+ (nextValue) => {
3449
+ if (value === void 0) setInternalValue(nextValue);
3450
+ onValueChange?.(nextValue);
3451
+ },
3452
+ [onValueChange, value]
3453
+ );
3454
+ return /* @__PURE__ */ (0, import_jsx_runtime17.jsx)(TabsContext.Provider, { value: { value: activeValue, setValue }, children: /* @__PURE__ */ (0, import_jsx_runtime17.jsx)("div", { className: cn("w-full", className), ...props }) });
3455
+ }
3456
+ var TabsList = React15.forwardRef(
3457
+ ({ className, ...props }, ref) => /* @__PURE__ */ (0, import_jsx_runtime17.jsx)(
3458
+ "div",
3459
+ {
3460
+ ref,
3461
+ className: cn(
3462
+ "inline-flex items-center justify-center rounded-lg bg-muted p-1 text-muted-foreground",
3463
+ className
3464
+ ),
3465
+ role: "tablist",
3466
+ ...props
3467
+ }
3468
+ )
3469
+ );
3470
+ TabsList.displayName = "TabsList";
3471
+ var TabsTrigger = React15.forwardRef(
3472
+ ({ className, value, onClick, ...props }, ref) => {
3473
+ const context = React15.useContext(TabsContext);
3474
+ if (!context) {
3475
+ throw new Error("TabsTrigger must be used within Tabs");
3476
+ }
3477
+ const isActive = context.value === value;
3478
+ return /* @__PURE__ */ (0, import_jsx_runtime17.jsx)(
3479
+ "button",
3480
+ {
3481
+ ref,
3482
+ type: "button",
3483
+ role: "tab",
3484
+ "aria-selected": isActive,
3485
+ "data-state": isActive ? "active" : "inactive",
3486
+ className: cn(
3487
+ "inline-flex items-center justify-center whitespace-nowrap rounded-md px-3 py-1 text-sm font-medium transition-all focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring focus-visible:ring-offset-2 ring-offset-background disabled:pointer-events-none disabled:opacity-50 data-[state=active]:bg-background data-[state=active]:text-foreground data-[state=active]:shadow-sm",
3488
+ className
3489
+ ),
3490
+ onClick: (event) => {
3491
+ context.setValue(value);
3492
+ onClick?.(event);
3493
+ },
3494
+ ...props
3495
+ }
3496
+ );
3497
+ }
3498
+ );
3499
+ TabsTrigger.displayName = "TabsTrigger";
3500
+ var TabsContent = React15.forwardRef(
3501
+ ({ className, value, ...props }, ref) => {
3502
+ const context = React15.useContext(TabsContext);
3503
+ if (!context) {
3504
+ throw new Error("TabsContent must be used within Tabs");
3505
+ }
3506
+ if (context.value !== value) return null;
3507
+ return /* @__PURE__ */ (0, import_jsx_runtime17.jsx)(
3508
+ "div",
3509
+ {
3510
+ ref,
3511
+ role: "tabpanel",
3512
+ className: cn(
3513
+ "mt-4 focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring focus-visible:ring-offset-2 ring-offset-background",
3514
+ className
3515
+ ),
3516
+ ...props
3517
+ }
3518
+ );
3519
+ }
3520
+ );
3521
+ TabsContent.displayName = "TabsContent";
3522
+
3523
+ // src/components/thread/markdown-text.tsx
3524
+ var import_react_markdown = __toESM(require("react-markdown"), 1);
3525
+ var import_remark_gfm = __toESM(require("remark-gfm"), 1);
3526
+ var import_rehype_katex = __toESM(require("rehype-katex"), 1);
3527
+ var import_remark_math = __toESM(require("remark-math"), 1);
3528
+ var import_react6 = require("react");
3529
+ var import_lucide_react9 = require("lucide-react");
3530
+
3531
+ // src/components/thread/syntax-highlighter.tsx
3532
+ var import_react_syntax_highlighter = require("react-syntax-highlighter");
2605
3533
  var import_tsx = __toESM(require("react-syntax-highlighter/dist/esm/languages/prism/tsx"), 1);
2606
3534
  var import_python = __toESM(require("react-syntax-highlighter/dist/esm/languages/prism/python"), 1);
2607
3535
  var import_prism = require("react-syntax-highlighter/dist/cjs/styles/prism");
2608
3536
  var import_react4 = require("react");
2609
- var import_jsx_runtime16 = require("react/jsx-runtime");
3537
+ var import_jsx_runtime18 = require("react/jsx-runtime");
2610
3538
  import_react_syntax_highlighter.PrismAsyncLight.registerLanguage("js", import_tsx.default);
2611
3539
  import_react_syntax_highlighter.PrismAsyncLight.registerLanguage("jsx", import_tsx.default);
2612
3540
  import_react_syntax_highlighter.PrismAsyncLight.registerLanguage("ts", import_tsx.default);
@@ -2617,7 +3545,7 @@ var SyntaxHighlighter = ({
2617
3545
  language,
2618
3546
  className
2619
3547
  }) => {
2620
- return /* @__PURE__ */ (0, import_jsx_runtime16.jsx)(
3548
+ return /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(
2621
3549
  import_react_syntax_highlighter.PrismAsyncLight,
2622
3550
  {
2623
3551
  language,
@@ -2637,15 +3565,15 @@ var SyntaxHighlighter = ({
2637
3565
  // src/components/thread/mermaid-block.tsx
2638
3566
  var Dialog = __toESM(require("@radix-ui/react-dialog"), 1);
2639
3567
  var import_mermaid = __toESM(require("mermaid"), 1);
2640
- var import_lucide_react6 = require("lucide-react");
2641
- var React14 = __toESM(require("react"), 1);
3568
+ var import_lucide_react8 = require("lucide-react");
3569
+ var React16 = __toESM(require("react"), 1);
2642
3570
 
2643
3571
  // src/components/thread/tooltip-icon-button.tsx
2644
3572
  var import_react5 = require("react");
2645
- var import_jsx_runtime17 = require("react/jsx-runtime");
3573
+ var import_jsx_runtime19 = require("react/jsx-runtime");
2646
3574
  var TooltipIconButton = (0, import_react5.forwardRef)(({ children, tooltip, side = "bottom", className, ...rest }, ref) => {
2647
- return /* @__PURE__ */ (0, import_jsx_runtime17.jsx)(TooltipProvider, { children: /* @__PURE__ */ (0, import_jsx_runtime17.jsxs)(Tooltip, { children: [
2648
- /* @__PURE__ */ (0, import_jsx_runtime17.jsx)(TooltipTrigger, { asChild: true, children: /* @__PURE__ */ (0, import_jsx_runtime17.jsxs)(
3575
+ return /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(TooltipProvider, { children: /* @__PURE__ */ (0, import_jsx_runtime19.jsxs)(Tooltip, { children: [
3576
+ /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(TooltipTrigger, { asChild: true, children: /* @__PURE__ */ (0, import_jsx_runtime19.jsxs)(
2649
3577
  Button,
2650
3578
  {
2651
3579
  variant: "ghost",
@@ -2655,17 +3583,17 @@ var TooltipIconButton = (0, import_react5.forwardRef)(({ children, tooltip, side
2655
3583
  ref,
2656
3584
  children: [
2657
3585
  children,
2658
- /* @__PURE__ */ (0, import_jsx_runtime17.jsx)("span", { className: "sr-only", children: tooltip })
3586
+ /* @__PURE__ */ (0, import_jsx_runtime19.jsx)("span", { className: "sr-only", children: tooltip })
2659
3587
  ]
2660
3588
  }
2661
3589
  ) }),
2662
- /* @__PURE__ */ (0, import_jsx_runtime17.jsx)(TooltipContent, { side, children: tooltip })
3590
+ /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(TooltipContent, { side, children: tooltip })
2663
3591
  ] }) });
2664
3592
  });
2665
3593
  TooltipIconButton.displayName = "TooltipIconButton";
2666
3594
 
2667
3595
  // src/components/thread/mermaid-block.tsx
2668
- var import_jsx_runtime18 = require("react/jsx-runtime");
3596
+ var import_jsx_runtime20 = require("react/jsx-runtime");
2669
3597
  var HEX_COLOR_PATTERN = /^#([\da-f]{3,8})$/i;
2670
3598
  var MERMAID_DIRECTIVE_PATTERN = /%{2}{\s*(?:(\w+)\s*:|(\w+))\s*(?:(\w+)|((?:(?!}%{2}).|\r?\n)*))?\s*(?:}%{2})?/gi;
2671
3599
  var MERMAID_FRONTMATTER_PATTERN = /^-{3}\s*[\n\r](.*?)[\n\r]-{3}\s*[\n\r]+/s;
@@ -2913,24 +3841,24 @@ function MermaidPreviewDialog({
2913
3841
  svgMarkup,
2914
3842
  title
2915
3843
  }) {
2916
- return /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(Dialog.Root, { open, onOpenChange, children: /* @__PURE__ */ (0, import_jsx_runtime18.jsxs)(Dialog.Portal, { children: [
2917
- /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(Dialog.Overlay, { className: "fixed inset-0 z-50 bg-black/60 backdrop-blur-sm data-[state=closed]:animate-out data-[state=open]:animate-in data-[state=closed]:fade-out-0 data-[state=open]:fade-in-0" }),
2918
- /* @__PURE__ */ (0, import_jsx_runtime18.jsxs)(Dialog.Content, { className: "fixed inset-[5vh] z-50 flex flex-col overflow-hidden rounded-3xl border border-border bg-background shadow-2xl outline-none data-[state=closed]:animate-out data-[state=open]:animate-in data-[state=closed]:zoom-out-95 data-[state=open]:zoom-in-95", children: [
2919
- /* @__PURE__ */ (0, import_jsx_runtime18.jsxs)("div", { className: "flex items-center justify-between gap-4 border-b border-border px-5 py-4", children: [
2920
- /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(Dialog.Title, { className: "text-base font-semibold text-foreground", children: title }),
2921
- /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(Dialog.Close, { asChild: true, children: /* @__PURE__ */ (0, import_jsx_runtime18.jsxs)(
3844
+ return /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(Dialog.Root, { open, onOpenChange, children: /* @__PURE__ */ (0, import_jsx_runtime20.jsxs)(Dialog.Portal, { children: [
3845
+ /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(Dialog.Overlay, { className: "fixed inset-0 z-50 bg-black/60 backdrop-blur-sm data-[state=closed]:animate-out data-[state=open]:animate-in data-[state=closed]:fade-out-0 data-[state=open]:fade-in-0" }),
3846
+ /* @__PURE__ */ (0, import_jsx_runtime20.jsxs)(Dialog.Content, { className: "fixed inset-[5vh] z-50 flex flex-col overflow-hidden rounded-3xl border border-border bg-background shadow-2xl outline-none data-[state=closed]:animate-out data-[state=open]:animate-in data-[state=closed]:zoom-out-95 data-[state=open]:zoom-in-95", children: [
3847
+ /* @__PURE__ */ (0, import_jsx_runtime20.jsxs)("div", { className: "flex items-center justify-between gap-4 border-b border-border px-5 py-4", children: [
3848
+ /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(Dialog.Title, { className: "text-base font-semibold text-foreground", children: title }),
3849
+ /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(Dialog.Close, { asChild: true, children: /* @__PURE__ */ (0, import_jsx_runtime20.jsxs)(
2922
3850
  "button",
2923
3851
  {
2924
3852
  type: "button",
2925
3853
  className: "inline-flex size-10 items-center justify-center rounded-full border border-border bg-card text-muted-foreground transition-colors hover:text-foreground",
2926
3854
  children: [
2927
- /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(import_lucide_react6.X, { className: "size-4" }),
2928
- /* @__PURE__ */ (0, import_jsx_runtime18.jsx)("span", { className: "sr-only", children: closeLabel })
3855
+ /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(import_lucide_react8.X, { className: "size-4" }),
3856
+ /* @__PURE__ */ (0, import_jsx_runtime20.jsx)("span", { className: "sr-only", children: closeLabel })
2929
3857
  ]
2930
3858
  }
2931
3859
  ) })
2932
3860
  ] }),
2933
- /* @__PURE__ */ (0, import_jsx_runtime18.jsx)("div", { className: "flex-1 overflow-auto bg-card p-6", children: /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(
3861
+ /* @__PURE__ */ (0, import_jsx_runtime20.jsx)("div", { className: "flex-1 overflow-auto bg-card p-6", children: /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(
2934
3862
  "div",
2935
3863
  {
2936
3864
  "data-slot": "mermaid-preview",
@@ -2944,24 +3872,24 @@ function MermaidPreviewDialog({
2944
3872
  function MermaidBlock({ code }) {
2945
3873
  const { t } = useChatkitTranslation();
2946
3874
  const { theme, isDarkMode } = useTheme();
2947
- const containerRef = React14.useRef(null);
2948
- const renderHostRef = React14.useRef(null);
2949
- const renderSequenceRef = React14.useRef(0);
2950
- const copyResetTimeoutRef = React14.useRef(null);
2951
- const diagramId = React14.useId().replace(/:/g, "");
2952
- const [activeTab, setActiveTab] = React14.useState("diagram");
2953
- const [isCopied, setIsCopied] = React14.useState(false);
2954
- const [isPreviewOpen, setIsPreviewOpen] = React14.useState(false);
2955
- const [isRendering, setIsRendering] = React14.useState(true);
2956
- const [renderError, setRenderError] = React14.useState(null);
2957
- const [svgMarkup, setSvgMarkup] = React14.useState(null);
2958
- const normalizedCode = React14.useMemo(() => normalizeMermaidCode(code), [code]);
2959
- const clearCopyResetTimeout = React14.useCallback(() => {
3875
+ const containerRef = React16.useRef(null);
3876
+ const renderHostRef = React16.useRef(null);
3877
+ const renderSequenceRef = React16.useRef(0);
3878
+ const copyResetTimeoutRef = React16.useRef(null);
3879
+ const diagramId = React16.useId().replace(/:/g, "");
3880
+ const [activeTab, setActiveTab] = React16.useState("diagram");
3881
+ const [isCopied, setIsCopied] = React16.useState(false);
3882
+ const [isPreviewOpen, setIsPreviewOpen] = React16.useState(false);
3883
+ const [isRendering, setIsRendering] = React16.useState(true);
3884
+ const [renderError, setRenderError] = React16.useState(null);
3885
+ const [svgMarkup, setSvgMarkup] = React16.useState(null);
3886
+ const normalizedCode = React16.useMemo(() => normalizeMermaidCode(code), [code]);
3887
+ const clearCopyResetTimeout = React16.useCallback(() => {
2960
3888
  if (copyResetTimeoutRef.current === null) return;
2961
3889
  window.clearTimeout(copyResetTimeoutRef.current);
2962
3890
  copyResetTimeoutRef.current = null;
2963
3891
  }, []);
2964
- React14.useEffect(() => {
3892
+ React16.useEffect(() => {
2965
3893
  let isActive = true;
2966
3894
  async function runRender() {
2967
3895
  const container = containerRef.current;
@@ -2999,17 +3927,17 @@ function MermaidBlock({ code }) {
2999
3927
  }
3000
3928
  };
3001
3929
  }, [diagramId, isDarkMode, normalizedCode, theme]);
3002
- React14.useEffect(() => {
3930
+ React16.useEffect(() => {
3003
3931
  clearCopyResetTimeout();
3004
3932
  setIsCopied(false);
3005
3933
  }, [activeTab, clearCopyResetTimeout, code]);
3006
- React14.useEffect(
3934
+ React16.useEffect(
3007
3935
  () => () => {
3008
3936
  clearCopyResetTimeout();
3009
3937
  },
3010
3938
  [clearCopyResetTimeout]
3011
3939
  );
3012
- const handleDownload = React14.useCallback(() => {
3940
+ const handleDownload = React16.useCallback(() => {
3013
3941
  if (!svgMarkup) return;
3014
3942
  const blob = new Blob([svgMarkup], {
3015
3943
  type: "image/svg+xml;charset=utf-8"
@@ -3023,7 +3951,7 @@ function MermaidBlock({ code }) {
3023
3951
  anchor.remove();
3024
3952
  window.URL.revokeObjectURL(url);
3025
3953
  }, [diagramId, svgMarkup]);
3026
- const handleCopyCode = React14.useCallback(() => {
3954
+ const handleCopyCode = React16.useCallback(() => {
3027
3955
  if (!code || isCopied) return;
3028
3956
  navigator.clipboard.writeText(code).then(() => {
3029
3957
  setIsCopied(true);
@@ -3037,21 +3965,21 @@ function MermaidBlock({ code }) {
3037
3965
  }, [clearCopyResetTimeout, code, isCopied]);
3038
3966
  const hasRenderedDiagram = svgMarkup !== null && !renderError;
3039
3967
  const statusMessage = isRendering ? t("markdown.mermaid.rendering") : t("markdown.mermaid.failed");
3040
- return /* @__PURE__ */ (0, import_jsx_runtime18.jsxs)(import_jsx_runtime18.Fragment, { children: [
3041
- /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(
3968
+ return /* @__PURE__ */ (0, import_jsx_runtime20.jsxs)(import_jsx_runtime20.Fragment, { children: [
3969
+ /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(
3042
3970
  Tabs,
3043
3971
  {
3044
3972
  className: "w-full",
3045
3973
  onValueChange: (value) => setActiveTab(value),
3046
3974
  value: activeTab,
3047
- children: /* @__PURE__ */ (0, import_jsx_runtime18.jsxs)(
3975
+ children: /* @__PURE__ */ (0, import_jsx_runtime20.jsxs)(
3048
3976
  "div",
3049
3977
  {
3050
3978
  ref: containerRef,
3051
3979
  "data-slot": "mermaid-block",
3052
3980
  className: "relative overflow-hidden text-card-foreground",
3053
3981
  children: [
3054
- /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(
3982
+ /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(
3055
3983
  "div",
3056
3984
  {
3057
3985
  ref: renderHostRef,
@@ -3060,62 +3988,62 @@ function MermaidBlock({ code }) {
3060
3988
  "data-slot": "mermaid-render-host"
3061
3989
  }
3062
3990
  ),
3063
- /* @__PURE__ */ (0, import_jsx_runtime18.jsxs)("div", { className: "flex flex-wrap items-center justify-between gap-3 px-4 py-3", children: [
3064
- /* @__PURE__ */ (0, import_jsx_runtime18.jsxs)("div", { className: "flex min-w-0 items-center gap-3", children: [
3065
- /* @__PURE__ */ (0, import_jsx_runtime18.jsx)("span", { className: "inline-flex size-9 shrink-0 items-center justify-center rounded-full bg-muted text-foreground", children: /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(import_lucide_react6.Code2Icon, { className: "size-4" }) }),
3066
- /* @__PURE__ */ (0, import_jsx_runtime18.jsx)("span", { className: "truncate text-base font-semibold text-foreground", children: t("markdown.mermaid.title") })
3991
+ /* @__PURE__ */ (0, import_jsx_runtime20.jsxs)("div", { className: "flex flex-wrap items-center justify-between gap-3 px-4 py-3", children: [
3992
+ /* @__PURE__ */ (0, import_jsx_runtime20.jsxs)("div", { className: "flex min-w-0 items-center gap-3", children: [
3993
+ /* @__PURE__ */ (0, import_jsx_runtime20.jsx)("span", { className: "inline-flex size-9 shrink-0 items-center justify-center rounded-full bg-muted text-foreground", children: /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(import_lucide_react8.Code2Icon, { className: "size-4" }) }),
3994
+ /* @__PURE__ */ (0, import_jsx_runtime20.jsx)("span", { className: "truncate text-base font-semibold text-foreground", children: t("markdown.mermaid.title") })
3067
3995
  ] }),
3068
- /* @__PURE__ */ (0, import_jsx_runtime18.jsxs)("div", { className: "flex shrink-0 items-center gap-2", children: [
3069
- /* @__PURE__ */ (0, import_jsx_runtime18.jsxs)("div", { className: "flex items-center gap-1", children: [
3070
- activeTab === "diagram" && hasRenderedDiagram ? /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(
3996
+ /* @__PURE__ */ (0, import_jsx_runtime20.jsxs)("div", { className: "flex shrink-0 items-center gap-2", children: [
3997
+ /* @__PURE__ */ (0, import_jsx_runtime20.jsxs)("div", { className: "flex items-center gap-1", children: [
3998
+ activeTab === "diagram" && hasRenderedDiagram ? /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(
3071
3999
  TooltipIconButton,
3072
4000
  {
3073
4001
  onClick: handleDownload,
3074
4002
  tooltip: t("markdown.mermaid.download"),
3075
- children: /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(import_lucide_react6.DownloadIcon, { className: "size-4" })
4003
+ children: /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(import_lucide_react8.DownloadIcon, { className: "size-4" })
3076
4004
  }
3077
4005
  ) : null,
3078
- activeTab === "diagram" && hasRenderedDiagram ? /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(
4006
+ activeTab === "diagram" && hasRenderedDiagram ? /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(
3079
4007
  TooltipIconButton,
3080
4008
  {
3081
4009
  onClick: () => setIsPreviewOpen(true),
3082
4010
  tooltip: t("markdown.mermaid.fullScreen"),
3083
- children: /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(import_lucide_react6.ExpandIcon, { className: "size-4" })
4011
+ children: /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(import_lucide_react8.ExpandIcon, { className: "size-4" })
3084
4012
  }
3085
4013
  ) : null,
3086
- activeTab === "code" ? /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(
4014
+ activeTab === "code" ? /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(
3087
4015
  TooltipIconButton,
3088
4016
  {
3089
4017
  onClick: handleCopyCode,
3090
4018
  tooltip: t("markdown.copy"),
3091
- children: isCopied ? /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(import_lucide_react6.CheckIcon, { className: "size-4" }) : /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(import_lucide_react6.CopyIcon, { className: "size-4" })
4019
+ children: isCopied ? /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(import_lucide_react8.CheckIcon, { className: "size-4" }) : /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(import_lucide_react8.CopyIcon, { className: "size-4" })
3092
4020
  }
3093
4021
  ) : null
3094
4022
  ] }),
3095
- /* @__PURE__ */ (0, import_jsx_runtime18.jsxs)(TabsList, { children: [
3096
- /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(TabsTrigger, { value: "diagram", children: t("markdown.mermaid.diagram") }),
3097
- /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(TabsTrigger, { value: "code", children: t("markdown.mermaid.code") })
4023
+ /* @__PURE__ */ (0, import_jsx_runtime20.jsxs)(TabsList, { children: [
4024
+ /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(TabsTrigger, { value: "diagram", children: t("markdown.mermaid.diagram") }),
4025
+ /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(TabsTrigger, { value: "code", children: t("markdown.mermaid.code") })
3098
4026
  ] })
3099
4027
  ] })
3100
4028
  ] }),
3101
- /* @__PURE__ */ (0, import_jsx_runtime18.jsxs)("div", { className: "border-t border-border pt-4", children: [
3102
- renderError ? /* @__PURE__ */ (0, import_jsx_runtime18.jsx)("p", { role: "alert", className: "mb-4 text-sm font-medium text-destructive", children: t("markdown.mermaid.failed") }) : null,
3103
- /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(TabsContent, { value: "diagram", className: "mt-0 space-y-4", children: /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(
4029
+ /* @__PURE__ */ (0, import_jsx_runtime20.jsxs)("div", { className: "border-t border-border pt-4", children: [
4030
+ renderError ? /* @__PURE__ */ (0, import_jsx_runtime20.jsx)("p", { role: "alert", className: "mb-4 text-sm font-medium text-destructive", children: t("markdown.mermaid.failed") }) : null,
4031
+ /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(TabsContent, { value: "diagram", className: "mt-0 space-y-4", children: /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(
3104
4032
  "div",
3105
4033
  {
3106
4034
  className: cn(
3107
4035
  "relative overflow-auto rounded-[calc(var(--radius)+0.5rem)] border border-border bg-background p-4",
3108
4036
  hasRenderedDiagram ? "[&_svg]:mx-auto [&_svg]:h-auto [&_svg]:w-full [&_svg]:max-w-none" : "min-h-[14rem]"
3109
4037
  ),
3110
- children: hasRenderedDiagram ? /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(
4038
+ children: hasRenderedDiagram ? /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(
3111
4039
  "div",
3112
4040
  {
3113
4041
  "data-slot": "mermaid-diagram",
3114
4042
  dangerouslySetInnerHTML: { __html: svgMarkup }
3115
4043
  }
3116
- ) : /* @__PURE__ */ (0, import_jsx_runtime18.jsxs)("div", { className: "flex min-h-[12rem] flex-col items-center justify-center gap-3 text-center text-muted-foreground", children: [
3117
- isRendering ? /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(import_lucide_react6.Loader2, { className: "size-5 animate-spin" }) : /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(import_lucide_react6.TriangleAlert, { className: "size-5 text-destructive" }),
3118
- /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(
4044
+ ) : /* @__PURE__ */ (0, import_jsx_runtime20.jsxs)("div", { className: "flex min-h-[12rem] flex-col items-center justify-center gap-3 text-center text-muted-foreground", children: [
4045
+ isRendering ? /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(import_lucide_react8.Loader2, { className: "size-5 animate-spin" }) : /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(import_lucide_react8.TriangleAlert, { className: "size-5 text-destructive" }),
4046
+ /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(
3119
4047
  "p",
3120
4048
  {
3121
4049
  className: cn("text-sm font-medium", !isRendering && "text-destructive"),
@@ -3126,12 +4054,12 @@ function MermaidBlock({ code }) {
3126
4054
  ] })
3127
4055
  }
3128
4056
  ) }),
3129
- /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(TabsContent, { value: "code", className: "mt-0", children: /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(
4057
+ /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(TabsContent, { value: "code", className: "mt-0", children: /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(
3130
4058
  "pre",
3131
4059
  {
3132
4060
  "data-slot": "mermaid-code",
3133
4061
  className: "overflow-x-auto rounded-[calc(var(--radius)+0.5rem)] border border-border bg-zinc-950 px-4 py-4 text-sm text-zinc-50",
3134
- children: /* @__PURE__ */ (0, import_jsx_runtime18.jsx)("code", { className: "block whitespace-pre font-mono", children: code })
4062
+ children: /* @__PURE__ */ (0, import_jsx_runtime20.jsx)("code", { className: "block whitespace-pre font-mono", children: code })
3135
4063
  }
3136
4064
  ) })
3137
4065
  ] })
@@ -3140,7 +4068,7 @@ function MermaidBlock({ code }) {
3140
4068
  )
3141
4069
  }
3142
4070
  ),
3143
- svgMarkup ? /* @__PURE__ */ (0, import_jsx_runtime18.jsx)(
4071
+ svgMarkup ? /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(
3144
4072
  MermaidPreviewDialog,
3145
4073
  {
3146
4074
  closeLabel: t("sheet.close"),
@@ -3155,7 +4083,13 @@ function MermaidBlock({ code }) {
3155
4083
 
3156
4084
  // src/components/thread/markdown-text.tsx
3157
4085
  var import_katex_min = require("katex/dist/katex.min.css");
3158
- var import_jsx_runtime19 = require("react/jsx-runtime");
4086
+ var import_jsx_runtime21 = require("react/jsx-runtime");
4087
+ var markdownTableMinWidth = "max(7rem, calc(8rem * var(--density-spacing, 1)))";
4088
+ var markdownTableCellPaddingInline = "calc(var(--density-padding, 1rem) * 1.25)";
4089
+ var markdownTableCellPaddingBlock = "max(0.5rem, calc(var(--density-padding, 1rem) * 0.75))";
4090
+ var markdownTableLineHeight = "max(1.375rem, calc(1.5rem * var(--density-spacing, 1)))";
4091
+ var markdownInlineCodePaddingInline = "max(0.25rem, calc(var(--density-gap, 0.5rem) * 0.75))";
4092
+ var markdownInlineCodePaddingBlock = "max(0.125rem, calc(var(--density-gap, 0.5rem) * 0.5))";
3159
4093
  var getTextContent = (children) => import_react6.Children.toArray(children).map((child) => {
3160
4094
  if (typeof child === "string" || typeof child === "number") {
3161
4095
  return String(child);
@@ -3184,23 +4118,23 @@ var CodeHeader = ({ language, code }) => {
3184
4118
  if (!code || isCopied) return;
3185
4119
  copyToClipboard(code);
3186
4120
  };
3187
- return /* @__PURE__ */ (0, import_jsx_runtime19.jsxs)("div", { className: "flex items-center justify-between gap-4 rounded-t-lg bg-zinc-900 px-4 py-2 text-sm font-semibold text-white", children: [
3188
- /* @__PURE__ */ (0, import_jsx_runtime19.jsx)("span", { className: "lowercase [&>span]:text-xs", children: language }),
3189
- /* @__PURE__ */ (0, import_jsx_runtime19.jsxs)(
4121
+ return /* @__PURE__ */ (0, import_jsx_runtime21.jsxs)("div", { className: "flex items-center justify-between gap-4 rounded-t-lg bg-zinc-900 px-4 py-2 text-sm font-semibold text-white", children: [
4122
+ /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("span", { className: "lowercase [&>span]:text-xs", children: language }),
4123
+ /* @__PURE__ */ (0, import_jsx_runtime21.jsxs)(
3190
4124
  TooltipIconButton,
3191
4125
  {
3192
4126
  tooltip: t("markdown.copy"),
3193
4127
  onClick: onCopy,
3194
4128
  children: [
3195
- !isCopied && /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(import_lucide_react7.CopyIcon, {}),
3196
- isCopied && /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(import_lucide_react7.CheckIcon, {})
4129
+ !isCopied && /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(import_lucide_react9.CopyIcon, {}),
4130
+ isCopied && /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(import_lucide_react9.CheckIcon, {})
3197
4131
  ]
3198
4132
  }
3199
4133
  )
3200
4134
  ] });
3201
4135
  };
3202
4136
  var defaultComponents = {
3203
- h1: ({ className, node: _node, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(
4137
+ h1: ({ className, node: _node, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
3204
4138
  "h1",
3205
4139
  {
3206
4140
  className: cn(
@@ -3210,7 +4144,7 @@ var defaultComponents = {
3210
4144
  ...props
3211
4145
  }
3212
4146
  ),
3213
- h2: ({ className, node: _node, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(
4147
+ h2: ({ className, node: _node, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
3214
4148
  "h2",
3215
4149
  {
3216
4150
  className: cn(
@@ -3220,7 +4154,7 @@ var defaultComponents = {
3220
4154
  ...props
3221
4155
  }
3222
4156
  ),
3223
- h3: ({ className, node: _node, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(
4157
+ h3: ({ className, node: _node, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
3224
4158
  "h3",
3225
4159
  {
3226
4160
  className: cn(
@@ -3230,7 +4164,7 @@ var defaultComponents = {
3230
4164
  ...props
3231
4165
  }
3232
4166
  ),
3233
- h4: ({ className, node: _node, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(
4167
+ h4: ({ className, node: _node, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
3234
4168
  "h4",
3235
4169
  {
3236
4170
  className: cn(
@@ -3240,7 +4174,7 @@ var defaultComponents = {
3240
4174
  ...props
3241
4175
  }
3242
4176
  ),
3243
- h5: ({ className, node: _node, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(
4177
+ h5: ({ className, node: _node, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
3244
4178
  "h5",
3245
4179
  {
3246
4180
  className: cn(
@@ -3250,21 +4184,21 @@ var defaultComponents = {
3250
4184
  ...props
3251
4185
  }
3252
4186
  ),
3253
- h6: ({ className, node: _node, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(
4187
+ h6: ({ className, node: _node, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
3254
4188
  "h6",
3255
4189
  {
3256
4190
  className: cn("my-4 font-semibold first:mt-0 last:mb-0", className),
3257
4191
  ...props
3258
4192
  }
3259
4193
  ),
3260
- p: ({ className, node: _node, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(
4194
+ p: ({ className, node: _node, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
3261
4195
  "p",
3262
4196
  {
3263
4197
  className: cn("mt-5 mb-5 leading-7 first:mt-0 last:mb-0", className),
3264
4198
  ...props
3265
4199
  }
3266
4200
  ),
3267
- a: ({ className, node: _node, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(
4201
+ a: ({ className, node: _node, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
3268
4202
  "a",
3269
4203
  {
3270
4204
  className: cn(
@@ -3280,7 +4214,7 @@ var defaultComponents = {
3280
4214
  className,
3281
4215
  node: _node,
3282
4216
  ...props
3283
- }) => /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(
4217
+ }) => /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
3284
4218
  "blockquote",
3285
4219
  {
3286
4220
  className: cn(
@@ -3290,21 +4224,21 @@ var defaultComponents = {
3290
4224
  ...props
3291
4225
  }
3292
4226
  ),
3293
- ul: ({ className, node: _node, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(
4227
+ ul: ({ className, node: _node, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
3294
4228
  "ul",
3295
4229
  {
3296
4230
  className: cn("my-5 list-outside list-disc pl-6 [&>li]:mt-2", className),
3297
4231
  ...props
3298
4232
  }
3299
4233
  ),
3300
- ol: ({ className, node: _node, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(
4234
+ ol: ({ className, node: _node, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
3301
4235
  "ol",
3302
4236
  {
3303
4237
  className: cn("my-5 list-outside list-decimal pl-8 [&>li]:mt-2", className),
3304
4238
  ...props
3305
4239
  }
3306
4240
  ),
3307
- hr: ({ className, node: _node, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(
4241
+ hr: ({ className, node: _node, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
3308
4242
  "hr",
3309
4243
  {
3310
4244
  className: cn("my-5 border-b", className),
@@ -3314,55 +4248,89 @@ var defaultComponents = {
3314
4248
  table: ({
3315
4249
  className,
3316
4250
  node: _node,
4251
+ style,
3317
4252
  ...props
3318
- }) => /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(
3319
- "table",
4253
+ }) => /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
4254
+ "div",
3320
4255
  {
3321
- className: cn(
3322
- "my-5 w-full border-separate border-spacing-0 overflow-y-auto",
3323
- className
3324
- ),
3325
- ...props
4256
+ "data-slot": "markdown-table-container",
4257
+ className: "my-5 max-w-full overflow-x-auto rounded-xl border border-border bg-background",
4258
+ children: /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
4259
+ "table",
4260
+ {
4261
+ className: cn(
4262
+ "min-w-full w-max border-separate border-spacing-0 text-sm",
4263
+ className
4264
+ ),
4265
+ style: {
4266
+ lineHeight: markdownTableLineHeight,
4267
+ ...style
4268
+ },
4269
+ ...props
4270
+ }
4271
+ )
3326
4272
  }
3327
4273
  ),
3328
- th: ({ className, node: _node, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(
4274
+ th: ({
4275
+ className,
4276
+ node: _node,
4277
+ style,
4278
+ ...props
4279
+ }) => /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
3329
4280
  "th",
3330
4281
  {
3331
4282
  className: cn(
3332
- "bg-muted border-border border-y border-l px-4 py-2 text-left font-bold first:rounded-tl-lg last:rounded-tr-lg last:border-r [&[align=center]]:text-center [&[align=right]]:text-right",
4283
+ "bg-muted/80 border-border border-l text-left align-top font-semibold whitespace-normal break-words first:border-l-0 first:rounded-tl-xl last:rounded-tr-xl [&[align=center]]:text-center [&[align=right]]:text-right",
3333
4284
  className
3334
4285
  ),
4286
+ style: {
4287
+ minWidth: markdownTableMinWidth,
4288
+ paddingInline: markdownTableCellPaddingInline,
4289
+ paddingBlock: markdownTableCellPaddingBlock,
4290
+ ...style
4291
+ },
3335
4292
  ...props
3336
4293
  }
3337
4294
  ),
3338
- td: ({ className, node: _node, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(
4295
+ td: ({
4296
+ className,
4297
+ node: _node,
4298
+ style,
4299
+ ...props
4300
+ }) => /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
3339
4301
  "td",
3340
4302
  {
3341
4303
  className: cn(
3342
- "border-border border-b border-l px-4 py-2 text-left last:border-r [&[align=center]]:text-center [&[align=right]]:text-right",
4304
+ "border-border border-t border-l text-left align-top whitespace-normal break-words first:border-l-0 [&[align=center]]:text-center [&[align=right]]:text-right [&_code]:break-words [&_code]:whitespace-pre-wrap [&_code]:[overflow-wrap:anywhere]",
3343
4305
  className
3344
4306
  ),
4307
+ style: {
4308
+ minWidth: markdownTableMinWidth,
4309
+ paddingInline: markdownTableCellPaddingInline,
4310
+ paddingBlock: markdownTableCellPaddingBlock,
4311
+ ...style
4312
+ },
3345
4313
  ...props
3346
4314
  }
3347
4315
  ),
3348
- tr: ({ className, node: _node, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(
4316
+ tr: ({ className, node: _node, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
3349
4317
  "tr",
3350
4318
  {
3351
4319
  className: cn(
3352
- "m-0 p-0 even:bg-muted/50 [&:last-child>td:first-child]:rounded-bl-lg [&:last-child>td:last-child]:rounded-br-lg",
4320
+ "m-0 p-0 even:bg-muted/30 [&:last-child>td:first-child]:rounded-bl-xl [&:last-child>td:last-child]:rounded-br-xl",
3353
4321
  className
3354
4322
  ),
3355
4323
  ...props
3356
4324
  }
3357
4325
  ),
3358
- sup: ({ className, node: _node, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(
4326
+ sup: ({ className, node: _node, ...props }) => /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
3359
4327
  "sup",
3360
4328
  {
3361
4329
  className: cn("[&>a]:text-xs [&>a]:no-underline", className),
3362
4330
  ...props
3363
4331
  }
3364
4332
  ),
3365
- pre: ({ className, children, node: _node }) => import_react6.Children.toArray(children).length === 1 && (isMermaidBlockChild(import_react6.Children.toArray(children)[0]) || isMermaidCodeElement(import_react6.Children.toArray(children)[0])) ? /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(import_jsx_runtime19.Fragment, { children }) : /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(
4333
+ pre: ({ className, children, node: _node }) => import_react6.Children.toArray(children).length === 1 && (isMermaidBlockChild(import_react6.Children.toArray(children)[0]) || isMermaidCodeElement(import_react6.Children.toArray(children)[0])) ? /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(import_jsx_runtime21.Fragment, { children }) : /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
3366
4334
  "div",
3367
4335
  {
3368
4336
  className: cn(
@@ -3376,6 +4344,7 @@ var defaultComponents = {
3376
4344
  className,
3377
4345
  children,
3378
4346
  node: _node,
4347
+ style,
3379
4348
  ...props
3380
4349
  }) => {
3381
4350
  const match = /language-([\w-]+)/.exec(className || "");
@@ -3385,17 +4354,17 @@ var defaultComponents = {
3385
4354
  const language = match[1];
3386
4355
  const normalizedCode = code.replace(/\n$/, "");
3387
4356
  if (language === "mermaid") {
3388
- return /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(MermaidBlock, { code: normalizedCode });
4357
+ return /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(MermaidBlock, { code: normalizedCode });
3389
4358
  }
3390
- return /* @__PURE__ */ (0, import_jsx_runtime19.jsxs)(import_jsx_runtime19.Fragment, { children: [
3391
- /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(
4359
+ return /* @__PURE__ */ (0, import_jsx_runtime21.jsxs)(import_jsx_runtime21.Fragment, { children: [
4360
+ /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
3392
4361
  CodeHeader,
3393
4362
  {
3394
4363
  language,
3395
4364
  code: normalizedCode
3396
4365
  }
3397
4366
  ),
3398
- /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(
4367
+ /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
3399
4368
  SyntaxHighlighter,
3400
4369
  {
3401
4370
  language,
@@ -3406,58 +4375,861 @@ var defaultComponents = {
3406
4375
  ] });
3407
4376
  }
3408
4377
  if (isBlockCode) {
3409
- return /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(
4378
+ return /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
3410
4379
  "code",
3411
4380
  {
3412
4381
  className: cn(
3413
4382
  "block min-w-full whitespace-pre px-4 py-4 font-mono text-inherit",
3414
4383
  className
3415
4384
  ),
3416
- ...props,
3417
- children: code.replace(/\n$/, "")
3418
- }
3419
- );
4385
+ ...props,
4386
+ children: code.replace(/\n$/, "")
4387
+ }
4388
+ );
4389
+ }
4390
+ return /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
4391
+ "code",
4392
+ {
4393
+ className: cn(
4394
+ "bg-muted rounded font-mono text-[0.9em] font-semibold whitespace-pre-wrap [overflow-wrap:anywhere]",
4395
+ className
4396
+ ),
4397
+ style: {
4398
+ paddingInline: markdownInlineCodePaddingInline,
4399
+ paddingBlock: markdownInlineCodePaddingBlock,
4400
+ ...style
4401
+ },
4402
+ ...props,
4403
+ children
4404
+ }
4405
+ );
4406
+ }
4407
+ };
4408
+ var MarkdownTextImpl = ({ children }) => {
4409
+ return /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("div", { className: "markdown-content", children: /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
4410
+ import_react_markdown.default,
4411
+ {
4412
+ remarkPlugins: [import_remark_gfm.default, import_remark_math.default],
4413
+ rehypePlugins: [import_rehype_katex.default],
4414
+ components: defaultComponents,
4415
+ children
4416
+ }
4417
+ ) });
4418
+ };
4419
+ var MarkdownText = (0, import_react6.memo)(MarkdownTextImpl);
4420
+
4421
+ // src/components/thread/messages/tool-component-group.tsx
4422
+ var React17 = __toESM(require("react"), 1);
4423
+ var import_lucide_react10 = require("lucide-react");
4424
+
4425
+ // src/i18n/localized-text.ts
4426
+ function resolveLocalizedText(value, language) {
4427
+ if (typeof value === "string") {
4428
+ const trimmed = value.trim();
4429
+ return trimmed || null;
4430
+ }
4431
+ if (!value || typeof value !== "object") return null;
4432
+ const localized = value;
4433
+ const normalizedLanguage = language.trim();
4434
+ const underscoredLanguage = normalizedLanguage.replace(/-/g, "_");
4435
+ const languagePrefix = normalizedLanguage.split("-")[0];
4436
+ const preferredKeys = normalizedLanguage.startsWith("zh") ? [
4437
+ normalizedLanguage,
4438
+ underscoredLanguage,
4439
+ "zh_Hans",
4440
+ "zh-Hans",
4441
+ "zh_CN",
4442
+ "zh-CN",
4443
+ "zh",
4444
+ "en_US",
4445
+ "en-US",
4446
+ "en"
4447
+ ] : [
4448
+ normalizedLanguage,
4449
+ underscoredLanguage,
4450
+ "en_US",
4451
+ "en-US",
4452
+ "en",
4453
+ languagePrefix,
4454
+ "zh_Hans",
4455
+ "zh-Hans",
4456
+ "zh_CN",
4457
+ "zh-CN",
4458
+ "zh"
4459
+ ];
4460
+ for (const key of preferredKeys) {
4461
+ const candidate = localized[key];
4462
+ if (typeof candidate === "string" && candidate.trim()) {
4463
+ return candidate.trim();
4464
+ }
4465
+ }
4466
+ for (const candidate of Object.values(localized)) {
4467
+ if (typeof candidate === "string" && candidate.trim()) {
4468
+ return candidate.trim();
4469
+ }
4470
+ }
4471
+ return null;
4472
+ }
4473
+
4474
+ // src/components/thread/messages/tool-component-group.tsx
4475
+ var import_jsx_runtime22 = require("react/jsx-runtime");
4476
+ var toolStatusConfig = {
4477
+ success: {
4478
+ iconClass: "border-green-500 text-green-700",
4479
+ icon: import_lucide_react10.CheckCircle2
4480
+ },
4481
+ fail: {
4482
+ iconClass: "border-red-500 text-red-700",
4483
+ icon: import_lucide_react10.XCircle
4484
+ },
4485
+ running: {
4486
+ iconClass: "border-blue-500 text-blue-700",
4487
+ icon: import_lucide_react10.Loader2
4488
+ }
4489
+ };
4490
+ var TOOL_GROUP_CATEGORY_ORDER = [
4491
+ "files",
4492
+ "searches",
4493
+ "commands",
4494
+ "lists",
4495
+ "tasks",
4496
+ "knowledges",
4497
+ "tools"
4498
+ ];
4499
+ var TOOL_GROUP_TOKEN_CATEGORY = {
4500
+ file: "files",
4501
+ files: "files",
4502
+ web_search: "searches",
4503
+ search: "searches",
4504
+ searches: "searches",
4505
+ program: "commands",
4506
+ command: "commands",
4507
+ commands: "commands",
4508
+ shell: "commands",
4509
+ terminal: "commands",
4510
+ list: "lists",
4511
+ lists: "lists",
4512
+ task: "tasks",
4513
+ tasks: "tasks",
4514
+ todo: "tasks",
4515
+ todos: "tasks",
4516
+ knowledge: "knowledges",
4517
+ knowledges: "knowledges",
4518
+ retriever: "knowledges",
4519
+ retrieval: "knowledges",
4520
+ tool: "tools",
4521
+ tools: "tools"
4522
+ };
4523
+ var TOOL_CALL_OUTPUT_RENDERERS = {};
4524
+ function getToolStepData(content) {
4525
+ return content.data ?? {};
4526
+ }
4527
+ function safeJson(value) {
4528
+ try {
4529
+ return JSON.stringify(value, null, 2) ?? String(value);
4530
+ } catch {
4531
+ return String(value);
4532
+ }
4533
+ }
4534
+ function formatDisplayValue(value) {
4535
+ return typeof value === "string" ? value : safeJson(value);
4536
+ }
4537
+ function parseStepDate(value) {
4538
+ if (value instanceof Date) {
4539
+ const timestamp2 = value.getTime();
4540
+ return Number.isNaN(timestamp2) ? null : timestamp2;
4541
+ }
4542
+ if (typeof value !== "string") {
4543
+ return null;
4544
+ }
4545
+ const timestamp = Date.parse(value);
4546
+ return Number.isNaN(timestamp) ? null : timestamp;
4547
+ }
4548
+ function formatStepDuration(durationMs) {
4549
+ if (durationMs < 1e3) {
4550
+ return `${durationMs}ms`;
4551
+ }
4552
+ if (durationMs < 1e4) {
4553
+ return `${(durationMs / 1e3).toFixed(1)}s`;
4554
+ }
4555
+ if (durationMs < 6e4) {
4556
+ return `${Math.round(durationMs / 1e3)}s`;
4557
+ }
4558
+ const hours = Math.floor(durationMs / 36e5);
4559
+ const minutes = Math.floor(durationMs % 36e5 / 6e4);
4560
+ const seconds = Math.floor(durationMs % 6e4 / 1e3);
4561
+ if (hours > 0) {
4562
+ return `${hours}h ${minutes}m ${seconds}s`;
4563
+ }
4564
+ return `${minutes}m ${seconds}s`;
4565
+ }
4566
+ function useToolStepDurationLabel(data) {
4567
+ const [durationNow, setDurationNow] = React17.useState(() => Date.now());
4568
+ const createdAt = parseStepDate(data.created_date);
4569
+ const endedAt = parseStepDate(data.end_date);
4570
+ const status = data.status;
4571
+ React17.useEffect(() => {
4572
+ if (status !== "running" || createdAt === null || endedAt !== null) {
4573
+ return;
4574
+ }
4575
+ setDurationNow(Date.now());
4576
+ const timer = window.setInterval(() => {
4577
+ setDurationNow(Date.now());
4578
+ }, 100);
4579
+ return () => {
4580
+ window.clearInterval(timer);
4581
+ };
4582
+ }, [createdAt, endedAt, status]);
4583
+ if (createdAt === null) return null;
4584
+ const durationMs = Math.max(0, (endedAt ?? durationNow) - createdAt);
4585
+ return formatStepDuration(durationMs);
4586
+ }
4587
+ function isJsonObjectValue(value) {
4588
+ return value !== null && typeof value === "object" && !Array.isArray(value);
4589
+ }
4590
+ function canUseAsJsonValue(value) {
4591
+ if (value === null) return true;
4592
+ if (typeof value === "string" || typeof value === "number" || typeof value === "boolean") {
4593
+ return true;
4594
+ }
4595
+ if (Array.isArray(value)) {
4596
+ return value.every(canUseAsJsonValue);
4597
+ }
4598
+ if (typeof value === "object") {
4599
+ return Object.values(value).every(canUseAsJsonValue);
4600
+ }
4601
+ return false;
4602
+ }
4603
+ function parseJsonString(value) {
4604
+ const trimmed = value.trim();
4605
+ if (!trimmed) return null;
4606
+ const first = trimmed[0];
4607
+ if (first !== "{" && first !== "[") return null;
4608
+ try {
4609
+ const parsed = JSON.parse(trimmed);
4610
+ return canUseAsJsonValue(parsed) ? parsed : null;
4611
+ } catch {
4612
+ return null;
4613
+ }
4614
+ }
4615
+ function detectJsonValue(value) {
4616
+ if (typeof value === "string") {
4617
+ const parsed = parseJsonString(value);
4618
+ if (parsed !== null) {
4619
+ return {
4620
+ kind: "json",
4621
+ value: parsed,
4622
+ raw: safeJson(parsed)
4623
+ };
4624
+ }
4625
+ return { kind: "text", text: value };
4626
+ }
4627
+ if (canUseAsJsonValue(value) && value !== null && typeof value === "object") {
4628
+ return {
4629
+ kind: "json",
4630
+ value,
4631
+ raw: safeJson(value)
4632
+ };
4633
+ }
4634
+ return { kind: "text", text: formatDisplayValue(value) };
4635
+ }
4636
+ function isComponentContent(content) {
4637
+ return content.type === "component";
4638
+ }
4639
+ function isTextContent(content) {
4640
+ return content.type === "text";
4641
+ }
4642
+ function isReasoningContent(content) {
4643
+ return content.type === "reasoning";
4644
+ }
4645
+ function isWidgetComponent(content) {
4646
+ const data = content.data;
4647
+ return data?.type === "Widget" && Array.isArray(data.widgets);
4648
+ }
4649
+ function isGroupableToolComponent(content) {
4650
+ if (!content || typeof content === "string") return false;
4651
+ return isComponentContent(content) && !isWidgetComponent(content) && content.data?.category === "Tool";
4652
+ }
4653
+ function isSkippableToolGroupSeparator(content) {
4654
+ if (typeof content === "string") return !content.trim();
4655
+ if (!content) return true;
4656
+ if (isTextContent(content)) {
4657
+ return !content.text?.trim();
4658
+ }
4659
+ if (isReasoningContent(content)) {
4660
+ return !content.text?.trim();
4661
+ }
4662
+ return false;
4663
+ }
4664
+ function normalizeToolToken(value) {
4665
+ if (typeof value !== "string") return null;
4666
+ const normalized = value.trim().toLowerCase().replace(/[\s-]+/g, "_");
4667
+ return normalized || null;
4668
+ }
4669
+ function classifyToolToken(value) {
4670
+ const normalized = normalizeToolToken(
4671
+ typeof value === "string" ? value : resolveLocalizedText(value, "en-US")
4672
+ );
4673
+ if (!normalized) return null;
4674
+ const directMatch = TOOL_GROUP_TOKEN_CATEGORY[normalized];
4675
+ if (directMatch) return directMatch;
4676
+ if (normalized.includes("search")) return "searches";
4677
+ if (normalized.includes("file")) return "files";
4678
+ if (normalized.includes("command") || normalized.includes("cmd") || normalized.includes("program") || normalized.includes("exec") || normalized.startsWith("run_") || normalized.includes("_run")) {
4679
+ return "commands";
4680
+ }
4681
+ if (normalized.includes("list")) return "lists";
4682
+ if (normalized.includes("task") || normalized.includes("todo")) return "tasks";
4683
+ if (normalized.includes("knowledge") || normalized.includes("retriever")) {
4684
+ return "knowledges";
4685
+ }
4686
+ return null;
4687
+ }
4688
+ function getToolGroupCategory(content) {
4689
+ const data = getToolStepData(content);
4690
+ return classifyToolToken(data.type) ?? classifyToolToken(data.tool) ?? classifyToolToken(data.title) ?? classifyToolToken(data.message) ?? "tools";
4691
+ }
4692
+ function getToolGroupCategoryCounts(items) {
4693
+ return items.reduce((counts, item) => {
4694
+ const category = getToolGroupCategory(item);
4695
+ counts[category] = (counts[category] ?? 0) + 1;
4696
+ return counts;
4697
+ }, {});
4698
+ }
4699
+ function getToolGroupDisplayStatus(items) {
4700
+ if (items.some((item) => getToolStepData(item).status === "fail")) {
4701
+ return "fail";
4702
+ }
4703
+ return "success";
4704
+ }
4705
+ function getToolActivityLabel(content, language) {
4706
+ const data = getToolStepData(content);
4707
+ const runningCandidates = [data.message, data.title, data.tool, data.type];
4708
+ const completedCandidates = [data.title, data.message, data.tool, data.type];
4709
+ const candidates = data.status === "running" ? runningCandidates : completedCandidates;
4710
+ for (const candidate of candidates) {
4711
+ const label = resolveLocalizedText(candidate, language);
4712
+ if (label) return label;
4713
+ }
4714
+ return "Tool";
4715
+ }
4716
+ function flushPendingTools(units, pendingTools) {
4717
+ if (pendingTools.length === 0) return;
4718
+ units.push({
4719
+ type: "tool-group",
4720
+ items: pendingTools.map((tool) => tool.item),
4721
+ startIndex: pendingTools[0].index
4722
+ });
4723
+ pendingTools.length = 0;
4724
+ }
4725
+ function buildToolComponentRenderUnits(content, options) {
4726
+ const units = [];
4727
+ const pendingTools = [];
4728
+ content.forEach((item, index) => {
4729
+ if (isGroupableToolComponent(item) && options?.shouldGroupComponent?.(item) !== false) {
4730
+ pendingTools.push({ item, index });
4731
+ return;
4732
+ }
4733
+ if (isSkippableToolGroupSeparator(item)) {
4734
+ return;
4735
+ }
4736
+ if (item === void 0) {
4737
+ return;
4738
+ }
4739
+ flushPendingTools(units, pendingTools);
4740
+ units.push({ type: "item", item, index });
4741
+ });
4742
+ flushPendingTools(units, pendingTools);
4743
+ return units;
4744
+ }
4745
+ function getToolCallOutputRenderer(data) {
4746
+ const keys = [data.tool, data.type].filter(
4747
+ (value) => typeof value === "string" && Boolean(value.trim())
4748
+ );
4749
+ for (const key of keys) {
4750
+ const renderer = TOOL_CALL_OUTPUT_RENDERERS[key];
4751
+ if (renderer) return renderer;
4752
+ }
4753
+ return DefaultToolCallOutput;
4754
+ }
4755
+ function getJsonValueSummary(value) {
4756
+ if (Array.isArray(value)) {
4757
+ return `Array(${value.length})`;
4758
+ }
4759
+ if (isJsonObjectValue(value)) {
4760
+ return `Object(${Object.keys(value).length})`;
4761
+ }
4762
+ return "JSON";
4763
+ }
4764
+ function formatJsonPrimitive(value) {
4765
+ if (value === null) return "null";
4766
+ if (typeof value === "string") return JSON.stringify(value);
4767
+ return String(value);
4768
+ }
4769
+ function JsonTreeNode({
4770
+ label,
4771
+ value,
4772
+ depth = 0
4773
+ }) {
4774
+ const isArray = Array.isArray(value);
4775
+ const isObject = isJsonObjectValue(value);
4776
+ const isExpandable = isArray || isObject;
4777
+ const [isExpanded, setIsExpanded] = React17.useState(depth < 2);
4778
+ if (!isExpandable) {
4779
+ return /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)("div", { className: "flex min-w-0 gap-2 leading-6", children: [
4780
+ label ? /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)("span", { className: "shrink-0 font-medium text-foreground/80", children: [
4781
+ label,
4782
+ ":"
4783
+ ] }) : null,
4784
+ /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
4785
+ "span",
4786
+ {
4787
+ className: cn(
4788
+ "min-w-0 wrap-break-word",
4789
+ typeof value === "string" ? "text-emerald-700" : typeof value === "number" ? "text-blue-700" : typeof value === "boolean" ? "text-purple-700" : "text-muted-foreground"
4790
+ ),
4791
+ children: formatJsonPrimitive(value)
4792
+ }
4793
+ )
4794
+ ] });
4795
+ }
4796
+ const entries = isArray ? value.map((item, index) => [String(index), item]) : Object.entries(value);
4797
+ const summary = isArray ? `Array(${value.length})` : `Object(${entries.length})`;
4798
+ return /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)("div", { className: "min-w-0", children: [
4799
+ /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)(
4800
+ "button",
4801
+ {
4802
+ type: "button",
4803
+ className: "flex min-w-0 items-center gap-1 leading-6 text-left hover:text-foreground",
4804
+ "aria-expanded": isExpanded,
4805
+ onClick: () => setIsExpanded((prev) => !prev),
4806
+ children: [
4807
+ /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
4808
+ import_lucide_react10.ChevronRight,
4809
+ {
4810
+ "aria-hidden": "true",
4811
+ className: cn(
4812
+ "h-3.5 w-3.5 shrink-0 text-muted-foreground transition-transform",
4813
+ isExpanded && "rotate-90"
4814
+ )
4815
+ }
4816
+ ),
4817
+ label ? /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)("span", { className: "min-w-0 truncate font-medium text-foreground/80", children: [
4818
+ label,
4819
+ ":"
4820
+ ] }) : null,
4821
+ /* @__PURE__ */ (0, import_jsx_runtime22.jsx)("span", { className: "shrink-0 text-muted-foreground", children: summary })
4822
+ ]
4823
+ }
4824
+ ),
4825
+ isExpanded ? /* @__PURE__ */ (0, import_jsx_runtime22.jsx)("div", { className: "ml-4 border-l border-border/70 pl-3", children: entries.map(([entryLabel, entryValue]) => /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
4826
+ JsonTreeNode,
4827
+ {
4828
+ label: entryLabel,
4829
+ value: entryValue,
4830
+ depth: depth + 1
4831
+ },
4832
+ entryLabel
4833
+ )) }) : null
4834
+ ] });
4835
+ }
4836
+ function JsonTreeView({ value }) {
4837
+ return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)("div", { className: "min-w-0 font-mono text-[11px]", children: /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(JsonTreeNode, { value }) });
4838
+ }
4839
+ function RawJsonBlock({ raw }) {
4840
+ return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)("pre", { className: "whitespace-pre-wrap wrap-break-word font-mono text-[11px]", children: raw });
4841
+ }
4842
+ function PlainTextBlock({ value, destructive = false }) {
4843
+ return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
4844
+ "pre",
4845
+ {
4846
+ className: cn(
4847
+ "whitespace-pre-wrap wrap-break-word",
4848
+ destructive && "text-destructive"
4849
+ ),
4850
+ children: value
3420
4851
  }
3421
- return /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(
3422
- "code",
4852
+ );
4853
+ }
4854
+ function ToolCallCopyButton({ value }) {
4855
+ const { t } = useChatkitTranslation();
4856
+ const [isCopied, setIsCopied] = React17.useState(false);
4857
+ const resetTimeoutRef = React17.useRef(null);
4858
+ const clearResetTimeout = React17.useCallback(() => {
4859
+ if (resetTimeoutRef.current === null) return;
4860
+ window.clearTimeout(resetTimeoutRef.current);
4861
+ resetTimeoutRef.current = null;
4862
+ }, []);
4863
+ React17.useEffect(() => clearResetTimeout, [clearResetTimeout]);
4864
+ const handleCopy = React17.useCallback(() => {
4865
+ if (typeof navigator === "undefined" || !navigator.clipboard) return;
4866
+ void navigator.clipboard.writeText(value).then(() => {
4867
+ setIsCopied(true);
4868
+ clearResetTimeout();
4869
+ resetTimeoutRef.current = window.setTimeout(() => {
4870
+ setIsCopied(false);
4871
+ resetTimeoutRef.current = null;
4872
+ }, 1500);
4873
+ }).catch(() => void 0);
4874
+ }, [clearResetTimeout, value]);
4875
+ const label = isCopied ? t("message.toolGroup.copied") : t("message.toolGroup.copy");
4876
+ return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
4877
+ "button",
4878
+ {
4879
+ type: "button",
4880
+ className: "inline-flex h-6 w-6 shrink-0 items-center justify-center rounded-md text-muted-foreground transition-colors hover:bg-background hover:text-foreground focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring/40",
4881
+ "aria-label": label,
4882
+ title: label,
4883
+ onClick: handleCopy,
4884
+ children: isCopied ? /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(import_lucide_react10.Check, { className: "h-3.5 w-3.5", "aria-hidden": "true" }) : /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(import_lucide_react10.Copy, { className: "h-3.5 w-3.5", "aria-hidden": "true" })
4885
+ }
4886
+ );
4887
+ }
4888
+ function ToolCallValueBlock({
4889
+ value,
4890
+ destructive = false
4891
+ }) {
4892
+ const { t } = useChatkitTranslation();
4893
+ const detected = detectJsonValue(value);
4894
+ if (detected.kind === "text") {
4895
+ return /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)("div", { className: "min-w-0 space-y-1", children: [
4896
+ /* @__PURE__ */ (0, import_jsx_runtime22.jsx)("div", { className: "flex justify-end", children: /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(ToolCallCopyButton, { value: detected.text }) }),
4897
+ /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(PlainTextBlock, { value: detected.text, destructive })
4898
+ ] });
4899
+ }
4900
+ return /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)(Tabs, { defaultValue: "tree", className: "min-w-0", children: [
4901
+ /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)("div", { className: "mb-2 flex min-w-0 items-center justify-between gap-2", children: [
4902
+ /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)("span", { className: "min-w-0 truncate text-[11px] text-muted-foreground", children: [
4903
+ t("message.toolGroup.jsonTitle"),
4904
+ " \xB7 ",
4905
+ getJsonValueSummary(detected.value)
4906
+ ] }),
4907
+ /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)("div", { className: "flex shrink-0 items-center gap-1", children: [
4908
+ /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(ToolCallCopyButton, { value: detected.raw }),
4909
+ /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)(TabsList, { className: "rounded-md p-0.5", children: [
4910
+ /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(TabsTrigger, { className: "px-2 py-0.5 text-[11px]", value: "tree", children: t("message.toolGroup.jsonTree") }),
4911
+ /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(TabsTrigger, { className: "px-2 py-0.5 text-[11px]", value: "raw", children: t("message.toolGroup.jsonRaw") })
4912
+ ] })
4913
+ ] })
4914
+ ] }),
4915
+ /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(TabsContent, { value: "tree", className: "mt-0", children: /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(JsonTreeView, { value: detected.value }) }),
4916
+ /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(TabsContent, { value: "raw", className: "mt-0", children: /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(RawJsonBlock, { raw: detected.raw }) })
4917
+ ] });
4918
+ }
4919
+ function DefaultToolCallOutput({ data }) {
4920
+ const { t } = useChatkitTranslation();
4921
+ const output = data.output ?? null;
4922
+ const error = data.error ?? null;
4923
+ if (error) {
4924
+ return /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)("div", { className: "space-y-1", children: [
4925
+ /* @__PURE__ */ (0, import_jsx_runtime22.jsx)("div", { className: "text-[11px] font-medium text-destructive", children: t("message.toolGroup.errorTitle") }),
4926
+ /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(ToolCallValueBlock, { value: error, destructive: true })
4927
+ ] });
4928
+ }
4929
+ if (output === null) return null;
4930
+ return /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)("div", { className: "space-y-1", children: [
4931
+ /* @__PURE__ */ (0, import_jsx_runtime22.jsx)("div", { className: "text-[11px] font-medium text-muted-foreground", children: t("message.toolGroup.outputTitle") }),
4932
+ /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(ToolCallValueBlock, { value: output })
4933
+ ] });
4934
+ }
4935
+ function ToolCallDetails({ content }) {
4936
+ const { t } = useChatkitTranslation();
4937
+ const data = getToolStepData(content);
4938
+ const OutputRenderer = getToolCallOutputRenderer(data);
4939
+ const hasInput = data.input !== void 0 && data.input !== null;
4940
+ const hasOutput = data.error !== void 0 || data.output !== void 0;
4941
+ if (!hasInput && !hasOutput) return null;
4942
+ return /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)("div", { className: "ml-6 mt-1 max-h-60 overflow-auto rounded-md bg-muted/30 px-3 py-2 text-xs text-muted-foreground", children: [
4943
+ hasInput && /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)("div", { className: "space-y-1", children: [
4944
+ /* @__PURE__ */ (0, import_jsx_runtime22.jsx)("div", { className: "text-[11px] font-medium text-muted-foreground", children: t("message.toolGroup.inputTitle") }),
4945
+ /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(ToolCallValueBlock, { value: data.input })
4946
+ ] }),
4947
+ hasInput && hasOutput ? /* @__PURE__ */ (0, import_jsx_runtime22.jsx)("div", { className: "h-2" }) : null,
4948
+ hasOutput ? /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(OutputRenderer, { content, data }) : null
4949
+ ] });
4950
+ }
4951
+ function ToolCallRow({ content }) {
4952
+ const { i18n: i18n2 } = useChatkitTranslation();
4953
+ const data = getToolStepData(content);
4954
+ const status = data.status;
4955
+ const itemConfig = status ? toolStatusConfig[status] : null;
4956
+ const ItemStatusIcon = itemConfig?.icon;
4957
+ const hasError = status === "fail" || Boolean(data.error);
4958
+ const label = getToolActivityLabel(content, i18n2.language);
4959
+ const detailsId = React17.useId();
4960
+ const hasDetails = data.input !== void 0 || data.error !== void 0 || data.output !== void 0;
4961
+ const durationLabel = useToolStepDurationLabel(data);
4962
+ const [isExpanded, setIsExpanded] = React17.useState(false);
4963
+ React17.useEffect(() => {
4964
+ if (status === "running" && data.output !== void 0) {
4965
+ setIsExpanded(true);
4966
+ }
4967
+ }, [data.output, status]);
4968
+ return /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)("li", { className: "min-w-0", children: [
4969
+ /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)(
4970
+ "button",
3423
4971
  {
4972
+ type: "button",
3424
4973
  className: cn(
3425
- "bg-muted rounded px-1.5 py-0.5 font-mono text-[0.9em] font-semibold break-all",
3426
- className
4974
+ "flex w-full min-w-0 items-center gap-2 text-left text-sm leading-6 text-muted-foreground",
4975
+ hasDetails && "cursor-pointer hover:text-foreground",
4976
+ hasError && "text-destructive hover:text-destructive"
3427
4977
  ),
3428
- ...props,
3429
- children
4978
+ "aria-expanded": hasDetails ? isExpanded : void 0,
4979
+ "aria-controls": hasDetails ? detailsId : void 0,
4980
+ disabled: !hasDetails,
4981
+ onClick: () => {
4982
+ if (hasDetails) setIsExpanded((prev) => !prev);
4983
+ },
4984
+ children: [
4985
+ ItemStatusIcon ? /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
4986
+ ItemStatusIcon,
4987
+ {
4988
+ className: cn(
4989
+ "h-3.5 w-3.5 shrink-0",
4990
+ itemConfig?.iconClass,
4991
+ status === "running" && "animate-spin"
4992
+ )
4993
+ }
4994
+ ) : /* @__PURE__ */ (0, import_jsx_runtime22.jsx)("span", { className: "h-3.5 w-3.5 shrink-0", "aria-hidden": "true" }),
4995
+ /* @__PURE__ */ (0, import_jsx_runtime22.jsx)("span", { className: "min-w-0 flex-1 truncate", title: label, children: label }),
4996
+ durationLabel ? /* @__PURE__ */ (0, import_jsx_runtime22.jsx)("span", { className: "shrink-0 text-[11px] tabular-nums text-muted-foreground/80", children: durationLabel }) : null,
4997
+ hasDetails ? /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
4998
+ import_lucide_react10.ChevronRight,
4999
+ {
5000
+ "aria-hidden": "true",
5001
+ className: cn(
5002
+ "h-3.5 w-3.5 shrink-0 text-muted-foreground transition-transform",
5003
+ isExpanded && "rotate-90"
5004
+ )
5005
+ }
5006
+ ) : null
5007
+ ]
3430
5008
  }
3431
- );
5009
+ ),
5010
+ hasDetails && isExpanded ? /* @__PURE__ */ (0, import_jsx_runtime22.jsx)("div", { id: detailsId, children: /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(ToolCallDetails, { content }) }) : null
5011
+ ] });
5012
+ }
5013
+ function ToolComponentGroup({
5014
+ items,
5015
+ hasFollowingItem
5016
+ }) {
5017
+ const { t } = useChatkitTranslation();
5018
+ const contentId = React17.useId();
5019
+ const groupStatus = getToolGroupDisplayStatus(items);
5020
+ const [isExpanded, setIsExpanded] = React17.useState(!hasFollowingItem);
5021
+ const categoryCounts = getToolGroupCategoryCounts(items);
5022
+ const categorySummary = TOOL_GROUP_CATEGORY_ORDER.flatMap((category) => {
5023
+ const count = categoryCounts[category] ?? 0;
5024
+ if (count === 0) return [];
5025
+ return [
5026
+ t(
5027
+ `message.toolGroup.categories.${category}.${count === 1 ? "one" : "other"}`,
5028
+ { count }
5029
+ )
5030
+ ];
5031
+ }).join(t("message.toolGroup.separator"));
5032
+ const summary = `${t(`message.toolGroup.status.${groupStatus}`)} ${categorySummary}`;
5033
+ const config = toolStatusConfig[groupStatus];
5034
+ const StatusIcon = config.icon;
5035
+ React17.useEffect(() => {
5036
+ setIsExpanded(!hasFollowingItem);
5037
+ }, [hasFollowingItem, items.length]);
5038
+ return /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)("div", { className: "px-1 py-1", children: [
5039
+ /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)(
5040
+ "button",
5041
+ {
5042
+ type: "button",
5043
+ className: "flex w-full items-center justify-between gap-3 text-left opacity-60 hover:opacity-100 disabled:pointer-events-none data-[state=open]:bg-muted",
5044
+ "aria-expanded": isExpanded,
5045
+ "aria-controls": contentId,
5046
+ onClick: () => setIsExpanded((prev) => !prev),
5047
+ children: [
5048
+ /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)("div", { className: "flex min-w-0 items-center gap-2 text-sm font-medium text-muted-foreground", children: [
5049
+ /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
5050
+ StatusIcon,
5051
+ {
5052
+ className: cn(
5053
+ "h-4 w-4 shrink-0",
5054
+ config.iconClass
5055
+ )
5056
+ }
5057
+ ),
5058
+ /* @__PURE__ */ (0, import_jsx_runtime22.jsx)("span", { className: "truncate", children: summary })
5059
+ ] }),
5060
+ /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
5061
+ import_lucide_react10.ChevronRight,
5062
+ {
5063
+ "aria-hidden": "true",
5064
+ className: cn(
5065
+ "h-4 w-4 shrink-0 text-muted-foreground transition-transform",
5066
+ isExpanded && "rotate-90"
5067
+ )
5068
+ }
5069
+ )
5070
+ ]
5071
+ }
5072
+ ),
5073
+ isExpanded && /* @__PURE__ */ (0, import_jsx_runtime22.jsx)("ul", { id: contentId, className: "mt-2 max-h-[200px] space-y-1.5 overflow-y-auto pr-1", children: items.map((item, index) => /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(ToolCallRow, { content: item }, item.id ?? `tool-item-${index}`)) })
5074
+ ] });
5075
+ }
5076
+
5077
+ // src/components/thread/messages/request-user-input-result-card.tsx
5078
+ var React18 = require("react");
5079
+ var import_chatkit_types4 = require("@xpert-ai/chatkit-types");
5080
+ var import_lucide_react11 = require("lucide-react");
5081
+ var import_jsx_runtime23 = require("react/jsx-runtime");
5082
+ function isRecord2(value) {
5083
+ return !!value && typeof value === "object" && !Array.isArray(value);
5084
+ }
5085
+ function readString(record, keys) {
5086
+ for (const key of keys) {
5087
+ const value = record[key];
5088
+ if (typeof value === "string" && value.trim()) {
5089
+ return value.trim();
5090
+ }
3432
5091
  }
3433
- };
3434
- var MarkdownTextImpl = ({ children }) => {
3435
- return /* @__PURE__ */ (0, import_jsx_runtime19.jsx)("div", { className: "markdown-content", children: /* @__PURE__ */ (0, import_jsx_runtime19.jsx)(
3436
- import_react_markdown.default,
5092
+ return null;
5093
+ }
5094
+ function getToolCallId(value) {
5095
+ if (!isRecord2(value)) return null;
5096
+ return readString(value, ["id"]);
5097
+ }
5098
+ function getToolCallName(value) {
5099
+ if (!isRecord2(value)) return null;
5100
+ return readString(value, ["name"]);
5101
+ }
5102
+ function pushClientToolCallsFromRecord(record, calls) {
5103
+ const clientToolCalls = record.clientToolCalls;
5104
+ if (Array.isArray(clientToolCalls)) {
5105
+ calls.push(...clientToolCalls);
5106
+ }
5107
+ }
5108
+ function collectPotentialToolCalls(messages) {
5109
+ const calls = [];
5110
+ const messageList = Array.isArray(messages) ? messages : [messages];
5111
+ for (const message of messageList) {
5112
+ const rawMessage = message;
5113
+ pushClientToolCallsFromRecord(rawMessage, calls);
5114
+ }
5115
+ return calls;
5116
+ }
5117
+ function findRequestUserInputClientToolCallById(messages, id) {
5118
+ if (!id) return null;
5119
+ return collectPotentialToolCalls(messages).find(
5120
+ (call) => getToolCallId(call) === id && getToolCallName(call) === import_chatkit_types4.REQUEST_USER_INPUT_TOOL_NAME
5121
+ ) ?? null;
5122
+ }
5123
+ function normalizeAnswer(value) {
5124
+ if (!isRecord2(value)) return null;
5125
+ const id = readString(value, ["id"]);
5126
+ const question = readString(value, ["question"]);
5127
+ const answerValue = readString(value, ["value"]);
5128
+ const type = readString(value, ["type"]);
5129
+ if (!id || !question || !answerValue || type !== "option" && type !== "other") {
5130
+ return null;
5131
+ }
5132
+ const label = readString(value, ["label"]);
5133
+ const description = readString(value, ["description"]);
5134
+ return {
5135
+ id,
5136
+ question,
5137
+ value: answerValue,
5138
+ type,
5139
+ ...label ? { label } : {},
5140
+ ...description ? { description } : {}
5141
+ };
5142
+ }
5143
+ function parseResultOutput(output) {
5144
+ let result = output;
5145
+ if (typeof output === "string") {
5146
+ try {
5147
+ result = JSON.parse(output);
5148
+ } catch {
5149
+ return null;
5150
+ }
5151
+ }
5152
+ if (!isRecord2(result) || !Array.isArray(result.answers)) {
5153
+ return null;
5154
+ }
5155
+ const answers = result.answers.map(normalizeAnswer);
5156
+ if (answers.some((answer) => answer === null)) {
5157
+ return null;
5158
+ }
5159
+ return answers;
5160
+ }
5161
+ function getRequestUserInputResultCardData(content, messages) {
5162
+ const data = isRecord2(content.data) ? content.data : null;
5163
+ if (data?.status !== "success") {
5164
+ return null;
5165
+ }
5166
+ const toolCall = findRequestUserInputClientToolCallById(messages, content.id);
5167
+ if (!toolCall) {
5168
+ return null;
5169
+ }
5170
+ const answers = parseResultOutput(data.output);
5171
+ if (!answers || answers.length === 0) {
5172
+ return null;
5173
+ }
5174
+ return {
5175
+ toolCallId: content.id,
5176
+ answers
5177
+ };
5178
+ }
5179
+ function RequestUserInputResultCard({
5180
+ result,
5181
+ className
5182
+ }) {
5183
+ const { t } = useChatkitTranslation();
5184
+ return /* @__PURE__ */ (0, import_jsx_runtime23.jsxs)(
5185
+ "section",
3437
5186
  {
3438
- remarkPlugins: [import_remark_gfm.default, import_remark_math.default],
3439
- rehypePlugins: [import_rehype_katex.default],
3440
- components: defaultComponents,
3441
- children
5187
+ "aria-label": t("message.requestUserInputResult.title"),
5188
+ className: cn(
5189
+ "rounded-lg border border-border bg-muted/25 px-3 py-2.5",
5190
+ className
5191
+ ),
5192
+ children: [
5193
+ /* @__PURE__ */ (0, import_jsx_runtime23.jsxs)("div", { className: "mb-2 flex items-center gap-2 text-sm font-semibold text-foreground", children: [
5194
+ /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(import_lucide_react11.CheckCircle2, { className: "h-4 w-4 text-primary" }),
5195
+ /* @__PURE__ */ (0, import_jsx_runtime23.jsx)("span", { children: t("message.requestUserInputResult.title") })
5196
+ ] }),
5197
+ /* @__PURE__ */ (0, import_jsx_runtime23.jsx)("div", { className: "space-y-2", children: result.answers.map((answer, index) => /* @__PURE__ */ (0, import_jsx_runtime23.jsxs)(
5198
+ "div",
5199
+ {
5200
+ className: "rounded-md bg-background/70 px-2.5 py-2",
5201
+ children: [
5202
+ /* @__PURE__ */ (0, import_jsx_runtime23.jsx)("div", { className: "text-xs font-medium leading-5 text-muted-foreground", children: answer.question }),
5203
+ /* @__PURE__ */ (0, import_jsx_runtime23.jsxs)("div", { className: "mt-0.5 flex min-w-0 flex-wrap items-center gap-1.5", children: [
5204
+ /* @__PURE__ */ (0, import_jsx_runtime23.jsx)("span", { className: "min-w-0 wrap-break-word text-sm font-semibold text-foreground", children: answer.label ?? answer.value }),
5205
+ /* @__PURE__ */ (0, import_jsx_runtime23.jsx)("span", { className: "rounded-full bg-muted px-1.5 py-0.5 text-[11px] font-medium text-muted-foreground", children: t(
5206
+ answer.type === "other" ? "message.requestUserInputResult.other" : "message.requestUserInputResult.option"
5207
+ ) })
5208
+ ] }),
5209
+ answer.description ? /* @__PURE__ */ (0, import_jsx_runtime23.jsx)("div", { className: "mt-1 text-xs leading-5 text-muted-foreground", children: answer.description }) : null
5210
+ ]
5211
+ },
5212
+ `${answer.id}-${index}`
5213
+ )) })
5214
+ ]
3442
5215
  }
3443
- ) });
3444
- };
3445
- var MarkdownText = (0, import_react6.memo)(MarkdownTextImpl);
5216
+ );
5217
+ }
3446
5218
 
3447
5219
  // src/components/thread/messages/widget.tsx
3448
5220
  var import_a2ui_react = require("@xpert-ai/a2ui-react");
3449
- var import_jsx_runtime20 = require("react/jsx-runtime");
5221
+ var import_jsx_runtime24 = require("react/jsx-runtime");
3450
5222
  function WidgetMessage({ messageId, data }) {
3451
5223
  const widgets = Array.isArray(data.widgets) ? data.widgets : [];
3452
5224
  if (widgets.length === 0) return null;
3453
5225
  const baseSurfaceId = `widget-${messageId}`;
3454
- return /* @__PURE__ */ (0, import_jsx_runtime20.jsx)("div", { className: "space-y-3", children: widgets.map((widget, index) => {
5226
+ return /* @__PURE__ */ (0, import_jsx_runtime24.jsx)("div", { className: "space-y-3", children: widgets.map((widget, index) => {
3455
5227
  const config = widget?.config;
3456
5228
  if (!config || typeof config !== "object") {
3457
5229
  return null;
3458
5230
  }
3459
5231
  const surfaceId = widgets.length > 1 ? `${baseSurfaceId}-${index}` : baseSurfaceId;
3460
- return /* @__PURE__ */ (0, import_jsx_runtime20.jsx)(
5232
+ return /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(
3461
5233
  import_a2ui_react.SurfaceRenderer,
3462
5234
  {
3463
5235
  surfaceId,
@@ -3469,58 +5241,44 @@ function WidgetMessage({ messageId, data }) {
3469
5241
  }
3470
5242
 
3471
5243
  // src/components/thread/messages/ai.tsx
3472
- var import_jsx_runtime21 = require("react/jsx-runtime");
3473
- function isTextContent(content) {
5244
+ var import_jsx_runtime25 = require("react/jsx-runtime");
5245
+ function isTextContent2(content) {
3474
5246
  return content.type === "text";
3475
5247
  }
3476
- function isReasoningContent(content) {
5248
+ function isReasoningContent2(content) {
3477
5249
  return content.type === "reasoning";
3478
5250
  }
3479
5251
  function isImageContent(content) {
3480
5252
  return content.type === "image_url";
3481
5253
  }
3482
- function isComponentContent(content) {
5254
+ function isComponentContent2(content) {
3483
5255
  return content.type === "component";
3484
5256
  }
3485
- var statusConfig = {
3486
- success: {
3487
- iconClass: "border-green-500 text-green-700",
3488
- icon: import_lucide_react8.CheckCircle2
3489
- },
3490
- fail: {
3491
- iconClass: "border-red-500 text-red-700",
3492
- icon: import_lucide_react8.XCircle
3493
- },
3494
- running: {
3495
- iconClass: "border-blue-500 text-blue-700",
3496
- icon: import_lucide_react8.Loader2
3497
- }
3498
- };
3499
- function isWidgetComponent(content) {
5257
+ function isWidgetComponent2(content) {
3500
5258
  const data = content.data;
3501
5259
  return data?.type === "Widget" && Array.isArray(data.widgets);
3502
5260
  }
3503
5261
  function isMemoryContent(content) {
3504
5262
  return content.type === "memory";
3505
5263
  }
3506
- function safeJson(value) {
5264
+ function safeJson2(value) {
3507
5265
  try {
3508
5266
  return JSON.stringify(value, null, 2);
3509
5267
  } catch {
3510
5268
  return String(value);
3511
5269
  }
3512
5270
  }
3513
- function formatDisplayValue(value) {
3514
- return typeof value === "string" ? value : safeJson(value);
5271
+ function formatDisplayValue2(value) {
5272
+ return typeof value === "string" ? value : safeJson2(value);
3515
5273
  }
3516
5274
  function ReasoningBlock({ reasoning }) {
3517
5275
  const blocks = reasoning.filter((item) => item.text?.trim());
3518
5276
  if (blocks.length === 0) return null;
3519
- return /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("div", { className: "space-y-2", children: blocks.map((item, index) => /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
5277
+ return /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("div", { className: "space-y-2", children: blocks.map((item, index) => /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(
3520
5278
  "div",
3521
5279
  {
3522
5280
  className: "rounded-lg border bg-muted/40 p-3 text-xs text-muted-foreground",
3523
- children: /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("p", { className: "whitespace-pre-wrap wrap-break-word leading-relaxed", children: item.text })
5281
+ children: /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("p", { className: "whitespace-pre-wrap wrap-break-word leading-relaxed", children: item.text })
3524
5282
  },
3525
5283
  item.id ?? `reasoning-${index}`
3526
5284
  )) });
@@ -3528,40 +5286,87 @@ function ReasoningBlock({ reasoning }) {
3528
5286
  function ImageBlock({ content }) {
3529
5287
  const imageUrl = typeof content.image_url === "string" ? content.image_url : typeof content.image_url?.url === "string" ? content.image_url.url : null;
3530
5288
  if (!imageUrl) {
3531
- return /* @__PURE__ */ (0, import_jsx_runtime21.jsxs)(Card, { children: [
3532
- /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(CardHeader, { className: "space-y-1", children: /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(CardTitle, { className: "text-sm", children: "Image" }) }),
3533
- /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(CardContent, { className: "text-xs text-muted-foreground", children: safeJson(content) })
5289
+ return /* @__PURE__ */ (0, import_jsx_runtime25.jsxs)(Card, { children: [
5290
+ /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(CardHeader, { className: "space-y-1", children: /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(CardTitle, { className: "text-sm", children: "Image" }) }),
5291
+ /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(CardContent, { className: "text-xs text-muted-foreground", children: safeJson2(content) })
3534
5292
  ] });
3535
5293
  }
3536
- return /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("figure", { className: "overflow-hidden rounded-lg border bg-background", children: /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("img", { src: imageUrl, alt: "Assistant output", className: "h-auto w-full object-cover" }) });
5294
+ return /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("figure", { className: "overflow-hidden rounded-lg border bg-background", children: /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("img", { src: imageUrl, alt: "Assistant output", className: "h-auto w-full object-cover" }) });
3537
5295
  }
3538
5296
  function MemoryBlock({ content }) {
3539
- return /* @__PURE__ */ (0, import_jsx_runtime21.jsxs)(Card, { children: [
3540
- /* @__PURE__ */ (0, import_jsx_runtime21.jsxs)(CardHeader, { className: "flex flex-row items-center justify-between gap-2", children: [
3541
- /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(CardTitle, { className: "text-sm", children: "Memory" }),
3542
- /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(Badge, { variant: "secondary", children: "Memory" })
5297
+ return /* @__PURE__ */ (0, import_jsx_runtime25.jsxs)(Card, { children: [
5298
+ /* @__PURE__ */ (0, import_jsx_runtime25.jsxs)(CardHeader, { className: "flex flex-row items-center justify-between gap-2", children: [
5299
+ /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(CardTitle, { className: "text-sm", children: "Memory" }),
5300
+ /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(Badge, { variant: "secondary", children: "Memory" })
3543
5301
  ] }),
3544
- /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(CardContent, { className: "text-xs text-muted-foreground", children: /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("pre", { className: "whitespace-pre-wrap wrap-break-word", children: safeJson(content.data ?? []) }) })
5302
+ /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(CardContent, { className: "text-xs text-muted-foreground", children: /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("pre", { className: "whitespace-pre-wrap wrap-break-word", children: safeJson2(content.data ?? []) }) })
3545
5303
  ] });
3546
5304
  }
5305
+ function parseStepDate2(value) {
5306
+ if (value instanceof Date) {
5307
+ const timestamp2 = value.getTime();
5308
+ return Number.isNaN(timestamp2) ? null : timestamp2;
5309
+ }
5310
+ if (typeof value !== "string") {
5311
+ return null;
5312
+ }
5313
+ const timestamp = Date.parse(value);
5314
+ return Number.isNaN(timestamp) ? null : timestamp;
5315
+ }
5316
+ function formatStepDuration2(durationMs) {
5317
+ if (durationMs < 1e3) {
5318
+ return `${durationMs}ms`;
5319
+ }
5320
+ if (durationMs < 1e4) {
5321
+ return `${(durationMs / 1e3).toFixed(1)}s`;
5322
+ }
5323
+ if (durationMs < 6e4) {
5324
+ return `${Math.round(durationMs / 1e3)}s`;
5325
+ }
5326
+ const hours = Math.floor(durationMs / 36e5);
5327
+ const minutes = Math.floor(durationMs % 36e5 / 6e4);
5328
+ const seconds = Math.floor(durationMs % 6e4 / 1e3);
5329
+ if (hours > 0) {
5330
+ return `${hours}h ${minutes}m ${seconds}s`;
5331
+ }
5332
+ return `${minutes}m ${seconds}s`;
5333
+ }
3547
5334
  function ComponentBlock({ content }) {
3548
- const [isExpanded, setIsExpanded] = React15.useState(false);
3549
- const contentRef = React15.useRef(null);
3550
- const shouldAutoScrollRef = React15.useRef(true);
3551
- const previousScrollTopRef = React15.useRef(0);
3552
- const data = content.data ?? {};
5335
+ const { i18n: i18n2 } = useChatkitTranslation();
5336
+ const [isExpanded, setIsExpanded] = React19.useState(false);
5337
+ const contentRef = React19.useRef(null);
5338
+ const shouldAutoScrollRef = React19.useRef(true);
5339
+ const previousScrollTopRef = React19.useRef(0);
5340
+ const [durationNow, setDurationNow] = React19.useState(() => Date.now());
5341
+ const data = getToolStepData(content);
3553
5342
  const category = data.category ?? "Component";
3554
- const title = data.tool && category === "Tool" ? data.tool : data.title ?? data.type ?? "Component";
5343
+ const title = getToolActivityLabel(content, i18n2.language);
3555
5344
  const status = data.status ?? null;
3556
5345
  const message = data.message ?? null;
3557
5346
  const output = data.output ?? null;
3558
5347
  const error = data.error ?? null;
3559
5348
  const fallback = message ?? output ?? data.data ?? data;
3560
5349
  const hasOutput = message !== null || output !== null;
3561
- React15.useEffect(() => {
5350
+ const createdAt = parseStepDate2(data.created_date);
5351
+ const endedAt = parseStepDate2(data.end_date);
5352
+ const durationMs = createdAt === null ? null : Math.max(0, (endedAt ?? durationNow) - createdAt);
5353
+ const durationLabel = durationMs === null ? null : formatStepDuration2(durationMs);
5354
+ React19.useEffect(() => {
3562
5355
  if (status === "running" && output !== null) setIsExpanded(true);
3563
5356
  }, [status, output]);
3564
- React15.useEffect(() => {
5357
+ React19.useEffect(() => {
5358
+ if (status !== "running" || createdAt === null || endedAt !== null) {
5359
+ return;
5360
+ }
5361
+ setDurationNow(Date.now());
5362
+ const timer = window.setInterval(() => {
5363
+ setDurationNow(Date.now());
5364
+ }, 100);
5365
+ return () => {
5366
+ window.clearInterval(timer);
5367
+ };
5368
+ }, [createdAt, endedAt, status]);
5369
+ React19.useEffect(() => {
3565
5370
  const element = contentRef.current;
3566
5371
  if (!element) return;
3567
5372
  previousScrollTopRef.current = element.scrollTop;
@@ -3581,7 +5386,7 @@ function ComponentBlock({ content }) {
3581
5386
  element.removeEventListener("scroll", updateAutoScrollState);
3582
5387
  };
3583
5388
  }, [isExpanded]);
3584
- React15.useEffect(() => {
5389
+ React19.useEffect(() => {
3585
5390
  if (status !== "running") {
3586
5391
  shouldAutoScrollRef.current = true;
3587
5392
  return;
@@ -3592,23 +5397,27 @@ function ComponentBlock({ content }) {
3592
5397
  }
3593
5398
  element.scrollTop = element.scrollHeight;
3594
5399
  }, [isExpanded, output, status]);
3595
- const config = status ? statusConfig[status] : null;
5400
+ const config = status ? toolStatusConfig[status] : null;
3596
5401
  const StatusIcon = config?.icon;
3597
- return /* @__PURE__ */ (0, import_jsx_runtime21.jsxs)(Card, { children: [
3598
- /* @__PURE__ */ (0, import_jsx_runtime21.jsxs)(CardHeader, { className: "flex flex-row items-center justify-between gap-2 px-2 py-1 cursor-pointer", onClick: () => setIsExpanded(!isExpanded), children: [
3599
- /* @__PURE__ */ (0, import_jsx_runtime21.jsxs)("div", { className: "flex items-center space-x-1 flex-1 min-w-0", children: [
3600
- status && StatusIcon && /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(StatusIcon, { className: cn("h-4 w-4", config?.iconClass, status === "running" && "animate-spin") }),
3601
- /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(CardTitle, { className: "text-sm truncate", children: title })
5402
+ return /* @__PURE__ */ (0, import_jsx_runtime25.jsxs)(Card, { children: [
5403
+ /* @__PURE__ */ (0, import_jsx_runtime25.jsxs)(CardHeader, { className: "flex flex-row items-center justify-between gap-2 px-2 py-1 cursor-pointer", onClick: () => setIsExpanded(!isExpanded), children: [
5404
+ /* @__PURE__ */ (0, import_jsx_runtime25.jsxs)("div", { className: "flex items-center space-x-1 flex-1 min-w-0", children: [
5405
+ status && StatusIcon && /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(StatusIcon, { className: cn("h-4 w-4", config?.iconClass, status === "running" && "animate-spin") }),
5406
+ /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(CardTitle, { className: "text-sm truncate", children: title })
3602
5407
  ] }),
3603
- /* @__PURE__ */ (0, import_jsx_runtime21.jsxs)("div", { className: "flex flex-wrap items-center gap-2 shrink-0", children: [
3604
- /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(Badge, { variant: "secondary", className: "rounded-lg px-1.5", children: category }),
3605
- /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
5408
+ /* @__PURE__ */ (0, import_jsx_runtime25.jsxs)("div", { className: "flex flex-wrap items-center gap-2 shrink-0", children: [
5409
+ durationLabel && /* @__PURE__ */ (0, import_jsx_runtime25.jsxs)("div", { className: "inline-flex items-center gap-1 text-[11px] text-muted-foreground tabular-nums", children: [
5410
+ /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(import_lucide_react12.Clock3, { className: "h-3 w-3" }),
5411
+ /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("span", { children: durationLabel })
5412
+ ] }),
5413
+ /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(Badge, { variant: "secondary", className: "rounded-lg px-1.5", children: category }),
5414
+ /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(
3606
5415
  "button",
3607
5416
  {
3608
5417
  className: "text-muted-foreground hover:text-foreground transition-colors",
3609
5418
  "aria-label": isExpanded ? "Collapse" : "Expand",
3610
- children: /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(
3611
- import_lucide_react8.ChevronDown,
5419
+ children: /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(
5420
+ import_lucide_react12.ChevronDown,
3612
5421
  {
3613
5422
  className: cn("h-4 w-4 transition-transform", isExpanded && "rotate-180")
3614
5423
  }
@@ -3617,55 +5426,83 @@ function ComponentBlock({ content }) {
3617
5426
  )
3618
5427
  ] })
3619
5428
  ] }),
3620
- isExpanded && /* @__PURE__ */ (0, import_jsx_runtime21.jsxs)(CardContent, { ref: contentRef, className: "text-xs text-muted-foreground max-h-60 overflow-auto", children: [
3621
- data.input && /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("pre", { className: "whitespace-pre-wrap wrap-break-word", children: formatDisplayValue(data.input) }),
3622
- error ? /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("pre", { className: "whitespace-pre-wrap wrap-break-word text-destructive", children: formatDisplayValue(error) }) : hasOutput && /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("pre", { className: "whitespace-pre-wrap wrap-break-word", children: formatDisplayValue(fallback) })
5429
+ isExpanded && /* @__PURE__ */ (0, import_jsx_runtime25.jsxs)(CardContent, { ref: contentRef, className: "text-xs text-muted-foreground max-h-60 overflow-auto", children: [
5430
+ data.input && /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("pre", { className: "whitespace-pre-wrap wrap-break-word", children: formatDisplayValue2(data.input) }),
5431
+ error ? /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("pre", { className: "whitespace-pre-wrap wrap-break-word text-destructive", children: formatDisplayValue2(error) }) : hasOutput && /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("pre", { className: "whitespace-pre-wrap wrap-break-word", children: formatDisplayValue2(fallback) })
3623
5432
  ] })
3624
5433
  ] });
3625
5434
  }
3626
5435
  function UnknownBlock({ content }) {
3627
- return /* @__PURE__ */ (0, import_jsx_runtime21.jsxs)(Card, { children: [
3628
- /* @__PURE__ */ (0, import_jsx_runtime21.jsxs)(CardHeader, { className: "flex flex-row items-center justify-between gap-2", children: [
3629
- /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(CardTitle, { className: "text-sm", children: "Assistant Content" }),
3630
- /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(Badge, { variant: "outline", children: content.type ?? "unknown" })
5436
+ return /* @__PURE__ */ (0, import_jsx_runtime25.jsxs)(Card, { children: [
5437
+ /* @__PURE__ */ (0, import_jsx_runtime25.jsxs)(CardHeader, { className: "flex flex-row items-center justify-between gap-2", children: [
5438
+ /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(CardTitle, { className: "text-sm", children: "Assistant Content" }),
5439
+ /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(Badge, { variant: "outline", children: content.type ?? "unknown" })
3631
5440
  ] }),
3632
- /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(CardContent, { className: "text-xs text-muted-foreground", children: /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("pre", { className: "whitespace-pre-wrap break-words", children: safeJson(content) }) })
5441
+ /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(CardContent, { className: "text-xs text-muted-foreground", children: /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("pre", { className: "whitespace-pre-wrap break-words", children: safeJson2(content) }) })
3633
5442
  ] });
3634
5443
  }
3635
- function renderContentItem(content, index, messageId) {
5444
+ function renderContentItem(content, index, message, lookupMessages) {
5445
+ const messageId = message.id;
3636
5446
  if (typeof content === "string") {
3637
- return /* @__PURE__ */ (0, import_jsx_runtime21.jsxs)("div", { children: [
3638
- /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(MarkdownText, { children: content }),
3639
- ";"
3640
- ] }, `text-${index}`);
5447
+ return /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("div", { children: /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(MarkdownText, { children: content }) }, `text-${index}`);
3641
5448
  }
3642
- if (isTextContent(content)) {
3643
- return /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("div", { children: /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(MarkdownText, { children: content.text }) }, content.id ?? `text-${index}`);
5449
+ if (isTextContent2(content)) {
5450
+ return /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("div", { children: /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(MarkdownText, { children: content.text }) }, content.id ?? `text-${index}`);
3644
5451
  }
3645
- if (isReasoningContent(content)) {
3646
- return /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("div", { children: /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(ReasoningBlock, { reasoning: [content] }) }, content.id ?? `reasoning-${index}`);
5452
+ if (isReasoningContent2(content)) {
5453
+ return /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("div", { children: /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(ReasoningBlock, { reasoning: [content] }) }, content.id ?? `reasoning-${index}`);
3647
5454
  }
3648
5455
  if (isImageContent(content)) {
3649
- return /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("div", { children: /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(ImageBlock, { content }) }, content.id ?? `image-${index}`);
5456
+ return /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("div", { children: /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(ImageBlock, { content }) }, content.id ?? `image-${index}`);
3650
5457
  }
3651
- if (isComponentContent(content)) {
3652
- if (isWidgetComponent(content)) {
3653
- return /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("div", { children: /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(WidgetMessage, { messageId, data: content.data }) }, content.id ?? `widget-${index}`);
5458
+ if (isComponentContent2(content)) {
5459
+ const requestUserInputResult = getRequestUserInputResultCardData(
5460
+ content,
5461
+ lookupMessages
5462
+ );
5463
+ if (requestUserInputResult) {
5464
+ return /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("div", { children: /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(RequestUserInputResultCard, { result: requestUserInputResult }) }, content.id ?? `request-user-input-result-${index}`);
5465
+ }
5466
+ if (isWidgetComponent2(content)) {
5467
+ return /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("div", { children: /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(WidgetMessage, { messageId, data: content.data }) }, content.id ?? `widget-${index}`);
3654
5468
  }
3655
- return /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("div", { children: /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(ComponentBlock, { content }) }, content.id ?? `component-${index}`);
5469
+ return /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("div", { children: /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(ComponentBlock, { content }) }, content.id ?? `component-${index}`);
3656
5470
  }
3657
5471
  if (isMemoryContent(content)) {
3658
- return /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("div", { children: /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(MemoryBlock, { content }) }, content.id ?? `memory-${index}`);
5472
+ return /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("div", { children: /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(MemoryBlock, { content }) }, content.id ?? `memory-${index}`);
5473
+ }
5474
+ return /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("div", { children: /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(UnknownBlock, { content }) }, content.id ?? `unknown-${index}`);
5475
+ }
5476
+ function renderContentUnit(unit, message, lookupMessages, hasFollowingItem) {
5477
+ if (unit.type === "item") {
5478
+ return renderContentItem(unit.item, unit.index, message, lookupMessages);
3659
5479
  }
3660
- return /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("div", { children: /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(UnknownBlock, { content }) }, content.id ?? `unknown-${index}`);
5480
+ return /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(
5481
+ "div",
5482
+ {
5483
+ children: /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(ToolComponentGroup, { items: unit.items, hasFollowingItem })
5484
+ },
5485
+ `tool-group-${unit.startIndex}-${unit.items[0]?.id ?? "tool"}-${unit.items.length}`
5486
+ );
3661
5487
  }
3662
- function renderContent(content, messageId) {
5488
+ function renderContent(message, lookupMessages) {
5489
+ const content = message.content;
3663
5490
  if (typeof content === "string") {
3664
5491
  if (!content.trim()) return null;
3665
- return /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(MarkdownText, { children: content });
5492
+ return /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(MarkdownText, { children: content });
3666
5493
  }
3667
5494
  if (!Array.isArray(content) || content.length === 0) return null;
3668
- return /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("div", { className: "space-y-3", children: content.map((item, index) => renderContentItem(item, index, messageId)) });
5495
+ const renderUnits = buildToolComponentRenderUnits(content, {
5496
+ shouldGroupComponent: (item) => getRequestUserInputResultCardData(item, lookupMessages) === null
5497
+ });
5498
+ return /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("div", { className: "space-y-3", children: renderUnits.map(
5499
+ (unit, index) => renderContentUnit(
5500
+ unit,
5501
+ message,
5502
+ lookupMessages,
5503
+ index < renderUnits.length - 1
5504
+ )
5505
+ ) });
3669
5506
  }
3670
5507
  function AssistantStreamingIndicator({
3671
5508
  status,
@@ -3677,23 +5514,24 @@ function AssistantStreamingIndicator({
3677
5514
  thinking: t("message.thinking"),
3678
5515
  answering: t("message.answering")
3679
5516
  };
3680
- return /* @__PURE__ */ (0, import_jsx_runtime21.jsxs)("div", { className: cn("flex items-center gap-2 text-xs text-muted-foreground", className), children: [
3681
- status === "loading" && /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(import_lucide_react8.Loader2, { className: "h-3.5 w-3.5 animate-spin" }),
3682
- status === "thinking" && /* @__PURE__ */ (0, import_jsx_runtime21.jsxs)("div", { className: "flex items-end gap-1", "aria-hidden": "true", children: [
3683
- /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("span", { className: "h-1.5 w-1.5 rounded-full bg-current animate-bounce [animation-delay:-0.3s]" }),
3684
- /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("span", { className: "h-1.5 w-1.5 rounded-full bg-current animate-bounce [animation-delay:-0.15s]" }),
3685
- /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("span", { className: "h-1.5 w-1.5 rounded-full bg-current animate-bounce" })
5517
+ return /* @__PURE__ */ (0, import_jsx_runtime25.jsxs)("div", { className: cn("flex items-center gap-2 text-xs text-muted-foreground", className), children: [
5518
+ status === "loading" && /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(import_lucide_react12.Loader2, { className: "h-3.5 w-3.5 animate-spin" }),
5519
+ status === "thinking" && /* @__PURE__ */ (0, import_jsx_runtime25.jsxs)("div", { className: "flex items-end gap-1", "aria-hidden": "true", children: [
5520
+ /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("span", { className: "h-1.5 w-1.5 rounded-full bg-current animate-bounce [animation-delay:-0.3s]" }),
5521
+ /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("span", { className: "h-1.5 w-1.5 rounded-full bg-current animate-bounce [animation-delay:-0.15s]" }),
5522
+ /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("span", { className: "h-1.5 w-1.5 rounded-full bg-current animate-bounce" })
3686
5523
  ] }),
3687
- status === "answering" && /* @__PURE__ */ (0, import_jsx_runtime21.jsxs)("div", { className: "flex items-end gap-1", "aria-hidden": "true", children: [
3688
- /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("span", { className: "h-2 w-0.5 rounded-full bg-current animate-pulse [animation-delay:-0.25s]" }),
3689
- /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("span", { className: "h-3 w-0.5 rounded-full bg-current animate-pulse [animation-delay:-0.1s]" }),
3690
- /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("span", { className: "h-2.5 w-0.5 rounded-full bg-current animate-pulse" })
5524
+ status === "answering" && /* @__PURE__ */ (0, import_jsx_runtime25.jsxs)("div", { className: "flex items-end gap-1", "aria-hidden": "true", children: [
5525
+ /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("span", { className: "h-2 w-0.5 rounded-full bg-current animate-pulse [animation-delay:-0.25s]" }),
5526
+ /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("span", { className: "h-3 w-0.5 rounded-full bg-current animate-pulse [animation-delay:-0.1s]" }),
5527
+ /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("span", { className: "h-2.5 w-0.5 rounded-full bg-current animate-pulse" })
3691
5528
  ] }),
3692
- /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("span", { children: labelMap[status] })
5529
+ /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("span", { children: labelMap[status] })
3693
5530
  ] });
3694
5531
  }
3695
5532
  function AssistantMessage({
3696
5533
  message,
5534
+ messages,
3697
5535
  className,
3698
5536
  isStreaming = false,
3699
5537
  streamingStatus
@@ -3702,43 +5540,44 @@ function AssistantMessage({
3702
5540
  const hasContent = hasRenderableMessageContent(message.content);
3703
5541
  const hasReasoning = hasRenderableReasoning(message.reasoning);
3704
5542
  const resolvedStreamingStatus = streamingStatus ?? getAssistantStreamingStatus(message, isStreaming);
3705
- const answerNode = renderContent(message.content, message.id);
3706
- const reasoningNode = hasReasoning ? /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(ReasoningBlock, { reasoning: message.reasoning ?? [] }) : null;
5543
+ const lookupMessages = messages?.length ? messages : [message];
5544
+ const answerNode = renderContent(message, lookupMessages);
5545
+ const reasoningNode = hasReasoning ? /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(ReasoningBlock, { reasoning: message.reasoning ?? [] }) : null;
3707
5546
  if (!hasRenderableAssistantMessage(message) && !resolvedStreamingStatus) return null;
3708
5547
  const streamingClass = isStreaming ? "streaming-active" : "";
3709
5548
  if (!hasRenderableAssistantMessage(message) && resolvedStreamingStatus) {
3710
- return /* @__PURE__ */ (0, import_jsx_runtime21.jsx)("div", { className: cn("space-y-3", streamingClass, className), children: /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(AssistantStreamingIndicator, { status: resolvedStreamingStatus }) });
5549
+ return /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("div", { className: cn("space-y-3", streamingClass, className), children: /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(AssistantStreamingIndicator, { status: resolvedStreamingStatus }) });
3711
5550
  }
3712
5551
  if (hasContent && hasReasoning) {
3713
- return /* @__PURE__ */ (0, import_jsx_runtime21.jsxs)("div", { className: cn("space-y-3", streamingClass, className), children: [
3714
- /* @__PURE__ */ (0, import_jsx_runtime21.jsxs)(
5552
+ return /* @__PURE__ */ (0, import_jsx_runtime25.jsxs)("div", { className: cn("space-y-3", streamingClass, className), children: [
5553
+ /* @__PURE__ */ (0, import_jsx_runtime25.jsxs)(
3715
5554
  Tabs,
3716
5555
  {
3717
5556
  defaultValue: message.status === "reasoning" ? "reasoning" : "answer",
3718
5557
  className: "w-full",
3719
5558
  children: [
3720
- /* @__PURE__ */ (0, import_jsx_runtime21.jsxs)(TabsList, { className: "", children: [
3721
- /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(TabsTrigger, { value: "answer", children: t("message.answer") }),
3722
- /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(TabsTrigger, { value: "reasoning", children: t("message.reasoning") })
5559
+ /* @__PURE__ */ (0, import_jsx_runtime25.jsxs)(TabsList, { className: "", children: [
5560
+ /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(TabsTrigger, { value: "answer", children: t("message.answer") }),
5561
+ /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(TabsTrigger, { value: "reasoning", children: t("message.reasoning") })
3723
5562
  ] }),
3724
- /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(TabsContent, { value: "answer", className: "space-y-3", children: answerNode }),
3725
- /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(TabsContent, { value: "reasoning", className: "space-y-3", children: reasoningNode })
5563
+ /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(TabsContent, { value: "answer", className: "space-y-3", children: answerNode }),
5564
+ /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(TabsContent, { value: "reasoning", className: "space-y-3", children: reasoningNode })
3726
5565
  ]
3727
5566
  }
3728
5567
  ),
3729
- resolvedStreamingStatus ? /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(AssistantStreamingIndicator, { status: resolvedStreamingStatus }) : null
5568
+ resolvedStreamingStatus ? /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(AssistantStreamingIndicator, { status: resolvedStreamingStatus }) : null
3730
5569
  ] });
3731
5570
  }
3732
- return /* @__PURE__ */ (0, import_jsx_runtime21.jsxs)("div", { className: cn("space-y-3", streamingClass, className), children: [
5571
+ return /* @__PURE__ */ (0, import_jsx_runtime25.jsxs)("div", { className: cn("space-y-3", streamingClass, className), children: [
3733
5572
  hasReasoning ? reasoningNode : answerNode,
3734
- resolvedStreamingStatus ? /* @__PURE__ */ (0, import_jsx_runtime21.jsx)(AssistantStreamingIndicator, { status: resolvedStreamingStatus }) : null
5573
+ resolvedStreamingStatus ? /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(AssistantStreamingIndicator, { status: resolvedStreamingStatus }) : null
3735
5574
  ] });
3736
5575
  }
3737
5576
 
3738
5577
  // src/components/thread/MessageActions.tsx
3739
- var React16 = __toESM(require("react"), 1);
3740
- var import_lucide_react9 = require("lucide-react");
3741
- var import_jsx_runtime22 = require("react/jsx-runtime");
5578
+ var React20 = __toESM(require("react"), 1);
5579
+ var import_lucide_react13 = require("lucide-react");
5580
+ var import_jsx_runtime26 = require("react/jsx-runtime");
3742
5581
  function MessageActions({
3743
5582
  content,
3744
5583
  isAssistant = false,
@@ -3747,7 +5586,7 @@ function MessageActions({
3747
5586
  className
3748
5587
  }) {
3749
5588
  const { t } = useChatkitTranslation();
3750
- const [copied, setCopied] = React16.useState(false);
5589
+ const [copied, setCopied] = React20.useState(false);
3751
5590
  const handleCopy = async () => {
3752
5591
  try {
3753
5592
  await navigator.clipboard.writeText(content);
@@ -3760,7 +5599,7 @@ function MessageActions({
3760
5599
  if (isStreaming) {
3761
5600
  return null;
3762
5601
  }
3763
- return /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)(
5602
+ return /* @__PURE__ */ (0, import_jsx_runtime26.jsxs)(
3764
5603
  "div",
3765
5604
  {
3766
5605
  className: cn(
@@ -3768,7 +5607,7 @@ function MessageActions({
3768
5607
  className
3769
5608
  ),
3770
5609
  children: [
3771
- /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
5610
+ /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
3772
5611
  "button",
3773
5612
  {
3774
5613
  type: "button",
@@ -3778,17 +5617,17 @@ function MessageActions({
3778
5617
  copied && "text-green-500"
3779
5618
  ),
3780
5619
  title: copied ? t("messageActions.copied") : t("messageActions.copy"),
3781
- children: copied ? /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(import_lucide_react9.Check, { size: 14 }) : /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(import_lucide_react9.Copy, { size: 14 })
5620
+ children: copied ? /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(import_lucide_react13.Check, { size: 14 }) : /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(import_lucide_react13.Copy, { size: 14 })
3782
5621
  }
3783
5622
  ),
3784
- isAssistant && onRetry && /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
5623
+ isAssistant && onRetry && /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
3785
5624
  "button",
3786
5625
  {
3787
5626
  type: "button",
3788
5627
  onClick: onRetry,
3789
5628
  className: "p-1.5 rounded-md text-muted-foreground hover:text-foreground hover:bg-muted transition-colors",
3790
5629
  title: t("messageActions.regenerate"),
3791
- children: /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(import_lucide_react9.RefreshCw, { size: 14 })
5630
+ children: /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(import_lucide_react13.RefreshCw, { size: 14 })
3792
5631
  }
3793
5632
  )
3794
5633
  ]
@@ -3797,20 +5636,20 @@ function MessageActions({
3797
5636
  }
3798
5637
 
3799
5638
  // src/components/thread/StartScreen.tsx
3800
- var React17 = require("react");
3801
- var import_lucide_react10 = require("lucide-react");
3802
- var import_jsx_runtime23 = require("react/jsx-runtime");
5639
+ var React21 = require("react");
5640
+ var import_lucide_react14 = require("lucide-react");
5641
+ var import_jsx_runtime27 = require("react/jsx-runtime");
3803
5642
  function getIconComponent2(icon) {
3804
5643
  const iconMap = {
3805
- "circle-question": /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(import_lucide_react10.HelpCircle, { size: 20 }),
3806
- "lightbulb": /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(import_lucide_react10.Lightbulb, { size: 20 }),
3807
- "sparkle": /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(import_lucide_react10.Sparkles, { size: 20 }),
3808
- "write": /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(import_lucide_react10.Pencil, { size: 20 }),
3809
- "search": /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(import_lucide_react10.Search, { size: 20 }),
3810
- "globe": /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(import_lucide_react10.Globe, { size: 20 }),
3811
- "book-open": /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(import_lucide_react10.BookOpen, { size: 20 }),
3812
- "compass": /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(import_lucide_react10.Compass, { size: 20 }),
3813
- "bolt": /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(import_lucide_react10.Zap, { size: 20 })
5644
+ "circle-question": /* @__PURE__ */ (0, import_jsx_runtime27.jsx)(import_lucide_react14.HelpCircle, { size: 20 }),
5645
+ "lightbulb": /* @__PURE__ */ (0, import_jsx_runtime27.jsx)(import_lucide_react14.Lightbulb, { size: 20 }),
5646
+ "sparkle": /* @__PURE__ */ (0, import_jsx_runtime27.jsx)(import_lucide_react14.Sparkles, { size: 20 }),
5647
+ "write": /* @__PURE__ */ (0, import_jsx_runtime27.jsx)(import_lucide_react14.Pencil, { size: 20 }),
5648
+ "search": /* @__PURE__ */ (0, import_jsx_runtime27.jsx)(import_lucide_react14.Search, { size: 20 }),
5649
+ "globe": /* @__PURE__ */ (0, import_jsx_runtime27.jsx)(import_lucide_react14.Globe, { size: 20 }),
5650
+ "book-open": /* @__PURE__ */ (0, import_jsx_runtime27.jsx)(import_lucide_react14.BookOpen, { size: 20 }),
5651
+ "compass": /* @__PURE__ */ (0, import_jsx_runtime27.jsx)(import_lucide_react14.Compass, { size: 20 }),
5652
+ "bolt": /* @__PURE__ */ (0, import_jsx_runtime27.jsx)(import_lucide_react14.Zap, { size: 20 })
3814
5653
  };
3815
5654
  return icon ? iconMap[icon] || iconMap["sparkle"] : iconMap["sparkle"];
3816
5655
  }
@@ -3818,9 +5657,9 @@ function StartScreen({ startScreen, onPromptClick, className }) {
3818
5657
  const { t } = useChatkitTranslation();
3819
5658
  const greeting = startScreen?.greeting ?? t("startScreen.greeting");
3820
5659
  const prompts = startScreen?.prompts ?? [];
3821
- return /* @__PURE__ */ (0, import_jsx_runtime23.jsxs)("div", { className: cn("flex flex-col items-center justify-center py-12 px-4", className), children: [
3822
- /* @__PURE__ */ (0, import_jsx_runtime23.jsx)("div", { className: "mb-8 text-center", children: /* @__PURE__ */ (0, import_jsx_runtime23.jsx)("h2", { className: "text-2xl font-semibold text-foreground mb-2", children: greeting }) }),
3823
- prompts.length > 0 && /* @__PURE__ */ (0, import_jsx_runtime23.jsx)("div", { className: "w-full max-w-2xl", children: /* @__PURE__ */ (0, import_jsx_runtime23.jsx)("div", { className: "grid grid-cols-1 sm:grid-cols-2 gap-3", children: prompts.map((item, index) => /* @__PURE__ */ (0, import_jsx_runtime23.jsxs)(
5660
+ return /* @__PURE__ */ (0, import_jsx_runtime27.jsxs)("div", { className: cn("flex flex-col items-center justify-center py-12 px-4", className), children: [
5661
+ /* @__PURE__ */ (0, import_jsx_runtime27.jsx)("div", { className: "mb-8 text-center", children: /* @__PURE__ */ (0, import_jsx_runtime27.jsx)("h2", { className: "text-2xl font-semibold text-foreground mb-2", children: greeting }) }),
5662
+ prompts.length > 0 && /* @__PURE__ */ (0, import_jsx_runtime27.jsx)("div", { className: "w-full max-w-2xl", children: /* @__PURE__ */ (0, import_jsx_runtime27.jsx)("div", { className: "grid grid-cols-1 sm:grid-cols-2 gap-3", children: prompts.map((item, index) => /* @__PURE__ */ (0, import_jsx_runtime27.jsxs)(
3824
5663
  "button",
3825
5664
  {
3826
5665
  type: "button",
@@ -3831,8 +5670,8 @@ function StartScreen({ startScreen, onPromptClick, className }) {
3831
5670
  "focus:outline-none focus:ring-2 focus:ring-primary/20"
3832
5671
  ),
3833
5672
  children: [
3834
- /* @__PURE__ */ (0, import_jsx_runtime23.jsx)("span", { className: "flex h-10 w-10 shrink-0 items-center justify-center rounded-lg bg-primary/10 text-primary", children: getIconComponent2(item.icon) }),
3835
- /* @__PURE__ */ (0, import_jsx_runtime23.jsx)("span", { className: "text-sm font-medium text-foreground", children: item.label })
5673
+ /* @__PURE__ */ (0, import_jsx_runtime27.jsx)("span", { className: "flex h-10 w-10 shrink-0 items-center justify-center rounded-lg bg-primary/10 text-primary", children: getIconComponent2(item.icon) }),
5674
+ /* @__PURE__ */ (0, import_jsx_runtime27.jsx)("span", { className: "text-sm font-medium text-foreground", children: item.label })
3836
5675
  ]
3837
5676
  },
3838
5677
  `prompt-${index}`
@@ -3841,13 +5680,13 @@ function StartScreen({ startScreen, onPromptClick, className }) {
3841
5680
  }
3842
5681
 
3843
5682
  // src/components/ui/chatkit-avatar.tsx
3844
- var React19 = require("react");
5683
+ var React23 = require("react");
3845
5684
 
3846
5685
  // src/components/ui/avatar.tsx
3847
- var React18 = __toESM(require("react"), 1);
5686
+ var React22 = __toESM(require("react"), 1);
3848
5687
  var AvatarPrimitive = __toESM(require("@radix-ui/react-avatar"), 1);
3849
- var import_jsx_runtime24 = require("react/jsx-runtime");
3850
- var Avatar = React18.forwardRef(({ className, ...props }, ref) => /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(
5688
+ var import_jsx_runtime28 = require("react/jsx-runtime");
5689
+ var Avatar = React22.forwardRef(({ className, ...props }, ref) => /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
3851
5690
  AvatarPrimitive.Root,
3852
5691
  {
3853
5692
  ref,
@@ -3859,7 +5698,7 @@ var Avatar = React18.forwardRef(({ className, ...props }, ref) => /* @__PURE__ *
3859
5698
  }
3860
5699
  ));
3861
5700
  Avatar.displayName = AvatarPrimitive.Root.displayName;
3862
- var AvatarImage = React18.forwardRef(({ className, ...props }, ref) => /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(
5701
+ var AvatarImage = React22.forwardRef(({ className, ...props }, ref) => /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
3863
5702
  AvatarPrimitive.Image,
3864
5703
  {
3865
5704
  ref,
@@ -3868,7 +5707,7 @@ var AvatarImage = React18.forwardRef(({ className, ...props }, ref) => /* @__PUR
3868
5707
  }
3869
5708
  ));
3870
5709
  AvatarImage.displayName = AvatarPrimitive.Image.displayName;
3871
- var AvatarFallback = React18.forwardRef(({ className, ...props }, ref) => /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(
5710
+ var AvatarFallback = React22.forwardRef(({ className, ...props }, ref) => /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
3872
5711
  AvatarPrimitive.Fallback,
3873
5712
  {
3874
5713
  ref,
@@ -3882,7 +5721,7 @@ var AvatarFallback = React18.forwardRef(({ className, ...props }, ref) => /* @__
3882
5721
  AvatarFallback.displayName = AvatarPrimitive.Fallback.displayName;
3883
5722
 
3884
5723
  // src/components/ui/chatkit-avatar.tsx
3885
- var import_jsx_runtime25 = require("react/jsx-runtime");
5724
+ var import_jsx_runtime29 = require("react/jsx-runtime");
3886
5725
  function asRecord(value) {
3887
5726
  return value && typeof value === "object" ? value : null;
3888
5727
  }
@@ -3955,21 +5794,21 @@ function ChatkitAvatar({
3955
5794
  const fallbackStyle = {
3956
5795
  ...avatar?.background ? { background: avatar.background } : {}
3957
5796
  };
3958
- return /* @__PURE__ */ (0, import_jsx_runtime25.jsxs)(Avatar, { className: cn(roundedClass, className), style, ...props, children: [
3959
- avatar?.url ? /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(AvatarImage, { className: imageClassName, src: avatar.url, alt: label }) : null,
3960
- /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(
5797
+ return /* @__PURE__ */ (0, import_jsx_runtime29.jsxs)(Avatar, { className: cn(roundedClass, className), style, ...props, children: [
5798
+ avatar?.url ? /* @__PURE__ */ (0, import_jsx_runtime29.jsx)(AvatarImage, { className: imageClassName, src: avatar.url, alt: label }) : null,
5799
+ /* @__PURE__ */ (0, import_jsx_runtime29.jsx)(
3961
5800
  AvatarFallback,
3962
5801
  {
3963
5802
  className: cn(roundedClass, "text-sm font-medium text-foreground", fallbackClassName),
3964
5803
  style: fallbackStyle,
3965
- children: emojiCharacter ? /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("span", { className: "text-[1.1em] leading-none", style: emojiStyle, children: emojiCharacter }) : fallbackText
5804
+ children: emojiCharacter ? /* @__PURE__ */ (0, import_jsx_runtime29.jsx)("span", { className: "text-[1.1em] leading-none", style: emojiStyle, children: emojiCharacter }) : fallbackText
3966
5805
  }
3967
5806
  )
3968
5807
  ] });
3969
5808
  }
3970
5809
 
3971
5810
  // src/hooks/useThreads.ts
3972
- var React20 = __toESM(require("react"), 1);
5811
+ var React24 = __toESM(require("react"), 1);
3973
5812
  var DEFAULT_LIMIT = 50;
3974
5813
  var getThreadTitle = (threadRecord) => {
3975
5814
  const title = threadRecord.title?.trim();
@@ -4007,16 +5846,16 @@ function useThreads(limit = DEFAULT_LIMIT) {
4007
5846
  isReady,
4008
5847
  isLoading: isStreamLoading
4009
5848
  } = useStreamContext();
4010
- const [threadRecords, setThreadRecords] = React20.useState([]);
4011
- const [isLoading, setIsLoading] = React20.useState(false);
4012
- const [error, setError] = React20.useState(null);
4013
- const upsertThreadRecord = React20.useCallback((threadRecord) => {
5849
+ const [threadRecords, setThreadRecords] = React24.useState([]);
5850
+ const [isLoading, setIsLoading] = React24.useState(false);
5851
+ const [error, setError] = React24.useState(null);
5852
+ const upsertThreadRecord = React24.useCallback((threadRecord) => {
4014
5853
  setThreadRecords((prev) => {
4015
5854
  const next = prev.filter((item) => item.id !== threadRecord.id);
4016
5855
  return sortThreadRecords([threadRecord, ...next]);
4017
5856
  });
4018
5857
  }, []);
4019
- const refreshThreads = React20.useCallback(async () => {
5858
+ const refreshThreads = React24.useCallback(async () => {
4020
5859
  setIsLoading(true);
4021
5860
  setError(null);
4022
5861
  try {
@@ -4032,7 +5871,7 @@ function useThreads(limit = DEFAULT_LIMIT) {
4032
5871
  setIsLoading(false);
4033
5872
  }
4034
5873
  }, [client, limit, assistantId]);
4035
- const createThread = React20.useCallback(
5874
+ const createThread = React24.useCallback(
4036
5875
  async (input) => {
4037
5876
  setError(null);
4038
5877
  const payload = {};
@@ -4046,7 +5885,7 @@ function useThreads(limit = DEFAULT_LIMIT) {
4046
5885
  },
4047
5886
  [client, upsertThreadRecord]
4048
5887
  );
4049
- const updateThread = React20.useCallback(
5888
+ const updateThread = React24.useCallback(
4050
5889
  async (recordId, payload) => {
4051
5890
  setError(null);
4052
5891
  const updated = await client.conversations.update(recordId, payload);
@@ -4055,7 +5894,7 @@ function useThreads(limit = DEFAULT_LIMIT) {
4055
5894
  },
4056
5895
  [client, upsertThreadRecord]
4057
5896
  );
4058
- const deleteThread = React20.useCallback(
5897
+ const deleteThread = React24.useCallback(
4059
5898
  async (recordId) => {
4060
5899
  setError(null);
4061
5900
  await client.conversations.delete(recordId);
@@ -4063,11 +5902,11 @@ function useThreads(limit = DEFAULT_LIMIT) {
4063
5902
  },
4064
5903
  [client]
4065
5904
  );
4066
- React20.useEffect(() => {
5905
+ React24.useEffect(() => {
4067
5906
  if (!isReady) return;
4068
5907
  void refreshThreads();
4069
5908
  }, [refreshThreads, isReady]);
4070
- React20.useEffect(() => {
5909
+ React24.useEffect(() => {
4071
5910
  if (!threadId || !isStreamLoading) return;
4072
5911
  const now = (/* @__PURE__ */ new Date()).toISOString();
4073
5912
  const busyStatus = "busy";
@@ -4088,7 +5927,7 @@ function useThreads(limit = DEFAULT_LIMIT) {
4088
5927
  return changed ? sortThreadRecords(next) : prev;
4089
5928
  });
4090
5929
  }, [threadId, isStreamLoading]);
4091
- React20.useEffect(() => {
5930
+ React24.useEffect(() => {
4092
5931
  if (!isReady || !threadId || isStreamLoading) return;
4093
5932
  let cancelled = false;
4094
5933
  void client.conversations.search({ where: { threadId }, limit: 1 }).then((result) => {
@@ -4102,7 +5941,7 @@ function useThreads(limit = DEFAULT_LIMIT) {
4102
5941
  cancelled = true;
4103
5942
  };
4104
5943
  }, [client, threadId, upsertThreadRecord, isReady, isStreamLoading]);
4105
- const threads = React20.useMemo(
5944
+ const threads = React24.useMemo(
4106
5945
  () => threadRecords.map((threadRecord) => toThreadItem(threadRecord)),
4107
5946
  [threadRecords]
4108
5947
  );
@@ -4119,10 +5958,10 @@ function useThreads(limit = DEFAULT_LIMIT) {
4119
5958
  }
4120
5959
 
4121
5960
  // src/components/thread/context-usage-indicator.tsx
4122
- var React21 = __toESM(require("react"), 1);
5961
+ var React25 = __toESM(require("react"), 1);
4123
5962
 
4124
5963
  // src/components/ui/progress-circle.tsx
4125
- var import_jsx_runtime26 = (
5964
+ var import_jsx_runtime30 = (
4126
5965
  // biome-ignore lint/a11y/useFocusableInteractive: false positive (progress + progressbar are not focusable interactives)
4127
5966
  // biome-ignore lint/nursery/useAriaPropsSupportedByRole: biome rule at odds with mdn docs (presumed nursary bug with rule)
4128
5967
  require("react/jsx-runtime")
@@ -4146,7 +5985,7 @@ var ProgressCircle = ({ value, className, ...restSvgProps }) => {
4146
5985
  fill: "none",
4147
5986
  strokeWidth
4148
5987
  };
4149
- return /* @__PURE__ */ (0, import_jsx_runtime26.jsxs)(
5988
+ return /* @__PURE__ */ (0, import_jsx_runtime30.jsxs)(
4150
5989
  "svg",
4151
5990
  {
4152
5991
  role: "progressbar",
@@ -4157,8 +5996,8 @@ var ProgressCircle = ({ value, className, ...restSvgProps }) => {
4157
5996
  "aria-valuemax": 100,
4158
5997
  ...restSvgProps,
4159
5998
  children: [
4160
- /* @__PURE__ */ (0, import_jsx_runtime26.jsx)("circle", { ...commonParams, className: "stroke-current/25" }),
4161
- /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
5999
+ /* @__PURE__ */ (0, import_jsx_runtime30.jsx)("circle", { ...commonParams, className: "stroke-current/25" }),
6000
+ /* @__PURE__ */ (0, import_jsx_runtime30.jsx)(
4162
6001
  "circle",
4163
6002
  {
4164
6003
  ...commonParams,
@@ -4176,7 +6015,7 @@ var ProgressCircle = ({ value, className, ...restSvgProps }) => {
4176
6015
  };
4177
6016
 
4178
6017
  // src/components/thread/context-usage-indicator.tsx
4179
- var import_jsx_runtime27 = require("react/jsx-runtime");
6018
+ var import_jsx_runtime31 = require("react/jsx-runtime");
4180
6019
  var kNumberFormatter = new Intl.NumberFormat("en-US", {
4181
6020
  minimumFractionDigits: 0,
4182
6021
  maximumFractionDigits: 1
@@ -4209,20 +6048,20 @@ function ContextUsageIndicator({
4209
6048
  }) {
4210
6049
  const { t } = useChatkitTranslation();
4211
6050
  const stream = useStreamContext();
4212
- const [maxContextSize, setMaxContextSize] = React21.useState(null);
4213
- const [usedContextSize, setUsedContextSize] = React21.useState(null);
4214
- const [assistantAgentKey, setAssistantAgentKey] = React21.useState(null);
4215
- const latestRealtimeUsageRef = React21.useRef({
6051
+ const [maxContextSize, setMaxContextSize] = React25.useState(null);
6052
+ const [usedContextSize, setUsedContextSize] = React25.useState(null);
6053
+ const [assistantAgentKey, setAssistantAgentKey] = React25.useState(null);
6054
+ const latestRealtimeUsageRef = React25.useRef({
4216
6055
  threadId: null,
4217
6056
  agentKey: null,
4218
6057
  usedTokens: null
4219
6058
  });
4220
- const realtimeUsage = React21.useMemo(
6059
+ const realtimeUsage = React25.useMemo(
4221
6060
  () => getThreadContextUsage(stream.contextUsageByAgentKey, assistantAgentKey),
4222
6061
  [assistantAgentKey, stream.contextUsageByAgentKey]
4223
6062
  );
4224
6063
  const realtimeUsedContextSize = getThreadContextUsageTotalTokens(realtimeUsage);
4225
- React21.useEffect(() => {
6064
+ React25.useEffect(() => {
4226
6065
  if (!stream.client || !stream.assistantId) {
4227
6066
  setMaxContextSize(null);
4228
6067
  setAssistantAgentKey(null);
@@ -4242,18 +6081,18 @@ function ContextUsageIndicator({
4242
6081
  cancelled = true;
4243
6082
  };
4244
6083
  }, [stream.client, stream.assistantId]);
4245
- React21.useEffect(() => {
6084
+ React25.useEffect(() => {
4246
6085
  latestRealtimeUsageRef.current = {
4247
6086
  threadId: stream.threadId ?? null,
4248
6087
  agentKey: assistantAgentKey,
4249
6088
  usedTokens: realtimeUsedContextSize
4250
6089
  };
4251
6090
  }, [assistantAgentKey, realtimeUsedContextSize, stream.threadId]);
4252
- React21.useEffect(() => {
6091
+ React25.useEffect(() => {
4253
6092
  if (realtimeUsedContextSize == null) return;
4254
6093
  setUsedContextSize(realtimeUsedContextSize);
4255
6094
  }, [realtimeUsedContextSize]);
4256
- React21.useEffect(() => {
6095
+ React25.useEffect(() => {
4257
6096
  if (!stream.client) {
4258
6097
  setUsedContextSize(null);
4259
6098
  return;
@@ -4318,8 +6157,8 @@ function ContextUsageIndicator({
4318
6157
  });
4319
6158
  const usageLabelWithSuffix = usageLabel.endsWith(":") ? usageLabel : `${usageLabel}:`;
4320
6159
  const progressClassName = percent >= 90 ? "text-destructive" : percent >= 75 ? "text-amber-500" : "text-primary dark:text-zinc-300";
4321
- return /* @__PURE__ */ (0, import_jsx_runtime27.jsxs)(Tooltip, { children: [
4322
- /* @__PURE__ */ (0, import_jsx_runtime27.jsx)(TooltipTrigger, { asChild: true, children: /* @__PURE__ */ (0, import_jsx_runtime27.jsx)(
6160
+ return /* @__PURE__ */ (0, import_jsx_runtime31.jsxs)(Tooltip, { children: [
6161
+ /* @__PURE__ */ (0, import_jsx_runtime31.jsx)(TooltipTrigger, { asChild: true, children: /* @__PURE__ */ (0, import_jsx_runtime31.jsx)(
4323
6162
  "button",
4324
6163
  {
4325
6164
  type: "button",
@@ -4328,19 +6167,19 @@ function ContextUsageIndicator({
4328
6167
  className
4329
6168
  ),
4330
6169
  "aria-label": `${usageLabelWithSuffix} ${usageFullLabel}. ${usageTokensLabel}`,
4331
- children: /* @__PURE__ */ (0, import_jsx_runtime27.jsx)(ProgressCircle, { value: percent, className: cn("size-3.5", progressClassName) })
6170
+ children: /* @__PURE__ */ (0, import_jsx_runtime31.jsx)(ProgressCircle, { value: percent, className: cn("size-3.5", progressClassName) })
4332
6171
  }
4333
6172
  ) }),
4334
- /* @__PURE__ */ (0, import_jsx_runtime27.jsxs)(TooltipContent, { side: "top", sideOffset: 6, className: "space-y-0.5 px-3 py-2 text-center", children: [
4335
- /* @__PURE__ */ (0, import_jsx_runtime27.jsx)("div", { className: "text-primary-foreground/70", children: usageLabelWithSuffix }),
4336
- /* @__PURE__ */ (0, import_jsx_runtime27.jsx)("div", { className: "font-medium text-primary-foreground/80", children: usageFullLabel }),
4337
- /* @__PURE__ */ (0, import_jsx_runtime27.jsx)("div", { className: "text-sm font-semibold", children: usageTokensLabel })
6173
+ /* @__PURE__ */ (0, import_jsx_runtime31.jsxs)(TooltipContent, { side: "top", sideOffset: 6, className: "space-y-0.5 px-3 py-2 text-center", children: [
6174
+ /* @__PURE__ */ (0, import_jsx_runtime31.jsx)("div", { className: "text-primary-foreground/70", children: usageLabelWithSuffix }),
6175
+ /* @__PURE__ */ (0, import_jsx_runtime31.jsx)("div", { className: "font-medium text-primary-foreground/80", children: usageFullLabel }),
6176
+ /* @__PURE__ */ (0, import_jsx_runtime31.jsx)("div", { className: "text-sm font-semibold", children: usageTokensLabel })
4338
6177
  ] })
4339
6178
  ] });
4340
6179
  }
4341
6180
 
4342
6181
  // src/components/chat.tsx
4343
- var import_jsx_runtime28 = require("react/jsx-runtime");
6182
+ var import_jsx_runtime32 = require("react/jsx-runtime");
4344
6183
  var import_meta2 = {};
4345
6184
  var defaultApiUrl2 = import_meta2.env.VITE_XPERTAI_API_URL;
4346
6185
  var COMPOSER_INPUT_MAX_HEIGHT = 128;
@@ -4432,8 +6271,8 @@ function ReferenceChip({
4432
6271
  }) {
4433
6272
  const metaLine = getReferenceMetaLine(reference);
4434
6273
  const isComposer = variant === "composer";
4435
- const Icon = reference.type === "quote" ? import_lucide_react11.Quote : reference.type === "image" ? import_lucide_react11.ImageIcon : import_lucide_react11.FileText;
4436
- return /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)(
6274
+ const Icon = reference.type === "quote" ? import_lucide_react15.Quote : reference.type === "image" ? import_lucide_react15.ImageIcon : import_lucide_react15.FileText;
6275
+ return /* @__PURE__ */ (0, import_jsx_runtime32.jsxs)(
4437
6276
  "div",
4438
6277
  {
4439
6278
  className: cn(
@@ -4442,7 +6281,7 @@ function ReferenceChip({
4442
6281
  ),
4443
6282
  title: getReferenceTitle(reference),
4444
6283
  children: [
4445
- /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
6284
+ /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(
4446
6285
  Icon,
4447
6286
  {
4448
6287
  size: isComposer ? 14 : 12,
@@ -4452,8 +6291,8 @@ function ReferenceChip({
4452
6291
  )
4453
6292
  }
4454
6293
  ),
4455
- /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("div", { className: "min-w-0 flex-1", children: [
4456
- /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
6294
+ /* @__PURE__ */ (0, import_jsx_runtime32.jsxs)("div", { className: "min-w-0 flex-1", children: [
6295
+ /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(
4457
6296
  "div",
4458
6297
  {
4459
6298
  className: cn(
@@ -4463,7 +6302,7 @@ function ReferenceChip({
4463
6302
  children: getReferenceLabel(reference)
4464
6303
  }
4465
6304
  ),
4466
- metaLine && /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
6305
+ metaLine && /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(
4467
6306
  "div",
4468
6307
  {
4469
6308
  className: cn(
@@ -4474,7 +6313,7 @@ function ReferenceChip({
4474
6313
  }
4475
6314
  )
4476
6315
  ] }),
4477
- onRemove && removeLabel && /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
6316
+ onRemove && removeLabel && /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(
4478
6317
  "button",
4479
6318
  {
4480
6319
  type: "button",
@@ -4485,7 +6324,7 @@ function ReferenceChip({
4485
6324
  ),
4486
6325
  title: removeLabel,
4487
6326
  "aria-label": removeLabel,
4488
- children: /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(import_lucide_react11.X, { size: 12 })
6327
+ children: /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(import_lucide_react15.X, { size: 12 })
4489
6328
  }
4490
6329
  )
4491
6330
  ]
@@ -4509,20 +6348,20 @@ function Chat({
4509
6348
  const { setStream } = useStreamManager();
4510
6349
  const stream = useStreamContext();
4511
6350
  const { theme } = useTheme();
4512
- const [isHistoryLoading, setIsHistoryLoading] = React22.useState(false);
4513
- const [historyError, setHistoryError] = React22.useState(null);
4514
- const [assistantName, setAssistantName] = React22.useState(null);
4515
- const [assistantAvatar, setAssistantAvatar] = React22.useState(null);
6351
+ const [isHistoryLoading, setIsHistoryLoading] = React26.useState(false);
6352
+ const [historyError, setHistoryError] = React26.useState(null);
6353
+ const [assistantName, setAssistantName] = React26.useState(null);
6354
+ const [assistantAvatar, setAssistantAvatar] = React26.useState(null);
4516
6355
  const LOADING_DOTS_MIN_DURATION = 800;
4517
6356
  const STREAMING_STATUS_REFRESH_MS = 250;
4518
- const [showLoadingDots, setShowLoadingDots] = React22.useState(false);
4519
- const [streamingNow, setStreamingNow] = React22.useState(() => Date.now());
4520
- const loadingStartTimeRef = React22.useRef(null);
4521
- const lastStreamOutputAtRef = React22.useRef(null);
4522
- React22.useEffect(() => {
6357
+ const [showLoadingDots, setShowLoadingDots] = React26.useState(false);
6358
+ const [streamingNow, setStreamingNow] = React26.useState(() => Date.now());
6359
+ const loadingStartTimeRef = React26.useRef(null);
6360
+ const lastStreamOutputAtRef = React26.useRef(null);
6361
+ React26.useEffect(() => {
4523
6362
  setStream(stream);
4524
6363
  }, [setStream, stream]);
4525
- React22.useEffect(() => {
6364
+ React26.useEffect(() => {
4526
6365
  if (stream.isLoading) {
4527
6366
  if (!loadingStartTimeRef.current) {
4528
6367
  loadingStartTimeRef.current = Date.now();
@@ -4545,7 +6384,7 @@ function Chat({
4545
6384
  }
4546
6385
  }
4547
6386
  }, [stream.isLoading]);
4548
- React22.useEffect(() => {
6387
+ React26.useEffect(() => {
4549
6388
  if (!stream.isLoading) {
4550
6389
  lastStreamOutputAtRef.current = null;
4551
6390
  setStreamingNow(Date.now());
@@ -4555,7 +6394,7 @@ function Chat({
4555
6394
  lastStreamOutputAtRef.current = now;
4556
6395
  setStreamingNow(now);
4557
6396
  }, [stream.messages, stream.isLoading]);
4558
- React22.useEffect(() => {
6397
+ React26.useEffect(() => {
4559
6398
  if (!stream.isLoading) {
4560
6399
  return;
4561
6400
  }
@@ -4564,52 +6403,55 @@ function Chat({
4564
6403
  }, STREAMING_STATUS_REFRESH_MS);
4565
6404
  return () => window.clearInterval(timer);
4566
6405
  }, [stream.isLoading]);
4567
- const [draft, setDraft] = React22.useState("");
4568
- const [selectedTool, setSelectedTool] = React22.useState(
6406
+ const [draft, setDraft] = React26.useState("");
6407
+ const [selectedTool, setSelectedTool] = React26.useState(
4569
6408
  null
4570
6409
  );
4571
- const [attachments, setAttachments] = React22.useState([]);
4572
- const [references, setReferences] = React22.useState([]);
4573
- const [isUploadingReferenceImages, setIsUploadingReferenceImages] = React22.useState(false);
4574
- const [quoteSelection, setQuoteSelection] = React22.useState(null);
4575
- const [isAtBottom, setIsAtBottom] = React22.useState(true);
4576
- const [hasUpdatesBelow, setHasUpdatesBelow] = React22.useState(false);
6410
+ const [planModeEnabled, setPlanModeEnabled] = React26.useState(false);
6411
+ const [attachments, setAttachments] = React26.useState([]);
6412
+ const [references, setReferences] = React26.useState([]);
6413
+ const [isUploadingReferenceImages, setIsUploadingReferenceImages] = React26.useState(false);
6414
+ const [quoteSelection, setQuoteSelection] = React26.useState(null);
6415
+ const [isAtBottom, setIsAtBottom] = React26.useState(true);
6416
+ const [hasUpdatesBelow, setHasUpdatesBelow] = React26.useState(false);
4577
6417
  const {
4578
6418
  threads,
4579
6419
  deleteThread,
4580
6420
  refreshThreads,
4581
6421
  isLoading: isThreadsLoading
4582
6422
  } = useThreads();
4583
- const viewportRef = React22.useRef(null);
4584
- const fileInputRef = React22.useRef(null);
4585
- const composerInputRef = React22.useRef(null);
4586
- const shouldAutoScrollRef = React22.useRef(true);
4587
- const forceFollowRef = React22.useRef(false);
4588
- const previousMessageCountRef = React22.useRef(0);
4589
- const previousScrollTopRef = React22.useRef(0);
4590
- const autoScrollFrameRef = React22.useRef(null);
4591
- const isPointerDownRef = React22.useRef(false);
4592
- const lastTouchYRef = React22.useRef(null);
6423
+ const viewportRef = React26.useRef(null);
6424
+ const fileInputRef = React26.useRef(null);
6425
+ const composerInputRef = React26.useRef(null);
6426
+ const shouldAutoScrollRef = React26.useRef(true);
6427
+ const forceFollowRef = React26.useRef(false);
6428
+ const previousMessageCountRef = React26.useRef(0);
6429
+ const previousScrollTopRef = React26.useRef(0);
6430
+ const autoScrollFrameRef = React26.useRef(null);
6431
+ const isPointerDownRef = React26.useRef(false);
6432
+ const lastTouchYRef = React26.useRef(null);
4593
6433
  const resolvedTitle = title ?? t("chat.title");
4594
6434
  const resolvedPlaceholder = placeholder ?? t("chat.placeholder");
4595
6435
  const inputPlaceholder = selectedTool?.placeholderOverride ?? composer?.placeholder ?? resolvedPlaceholder;
4596
- const messages = React22.useMemo(
6436
+ const messages = React26.useMemo(
4597
6437
  () => stream.messages ?? [],
4598
6438
  [stream.messages]
4599
6439
  );
4600
6440
  const trimmedDraft = draft.trim();
4601
6441
  const hasReferences = references.length > 0;
4602
- const pendingFollowUps = React22.useMemo(
6442
+ const pendingFollowUps = React26.useMemo(
4603
6443
  () => [...stream.pendingFollowUps ?? []].sort(
4604
6444
  (a, b) => a.createdAt - b.createdAt
4605
6445
  ),
4606
6446
  [stream.pendingFollowUps]
4607
6447
  );
4608
- const clearQuoteSelection = React22.useCallback(() => {
6448
+ const hasPendingFollowUps = pendingFollowUps.length > 0;
6449
+ const hasPendingRequestUserInput = Boolean(stream.pendingRequestUserInput);
6450
+ const clearQuoteSelection = React26.useCallback(() => {
4609
6451
  setQuoteSelection(null);
4610
6452
  }, []);
4611
6453
  useParentMessenger({
4612
- onSetComposerValue: React22.useCallback(
6454
+ onSetComposerValue: React26.useCallback(
4613
6455
  (payload) => {
4614
6456
  if (!payload) {
4615
6457
  return;
@@ -4632,11 +6474,11 @@ function Chat({
4632
6474
  },
4633
6475
  [composer?.tools]
4634
6476
  ),
4635
- onFocusComposer: React22.useCallback(() => {
6477
+ onFocusComposer: React26.useCallback(() => {
4636
6478
  composerInputRef.current?.focus();
4637
6479
  }, [])
4638
6480
  });
4639
- const syncQuoteSelection = React22.useCallback(() => {
6481
+ const syncQuoteSelection = React26.useCallback(() => {
4640
6482
  if (typeof window === "undefined") {
4641
6483
  clearQuoteSelection();
4642
6484
  return;
@@ -4681,23 +6523,23 @@ function Chat({
4681
6523
  left
4682
6524
  });
4683
6525
  }, [clearQuoteSelection]);
4684
- const cancelPendingAutoScroll = React22.useCallback(() => {
6526
+ const cancelPendingAutoScroll = React26.useCallback(() => {
4685
6527
  if (autoScrollFrameRef.current !== null) {
4686
6528
  cancelAnimationFrame(autoScrollFrameRef.current);
4687
6529
  autoScrollFrameRef.current = null;
4688
6530
  }
4689
6531
  }, []);
4690
- const disableAutoFollow = React22.useCallback(() => {
6532
+ const disableAutoFollow = React26.useCallback(() => {
4691
6533
  forceFollowRef.current = false;
4692
6534
  shouldAutoScrollRef.current = false;
4693
6535
  cancelPendingAutoScroll();
4694
6536
  }, [cancelPendingAutoScroll]);
4695
- const enableAutoFollow = React22.useCallback(() => {
6537
+ const enableAutoFollow = React26.useCallback(() => {
4696
6538
  forceFollowRef.current = true;
4697
6539
  shouldAutoScrollRef.current = true;
4698
6540
  setHasUpdatesBelow(false);
4699
6541
  }, []);
4700
- const scrollToBottom = React22.useCallback(
6542
+ const scrollToBottom = React26.useCallback(
4701
6543
  (smooth = false, force = false) => {
4702
6544
  if (force) {
4703
6545
  enableAutoFollow();
@@ -4719,7 +6561,7 @@ function Chat({
4719
6561
  },
4720
6562
  [cancelPendingAutoScroll, enableAutoFollow]
4721
6563
  );
4722
- React22.useEffect(() => {
6564
+ React26.useEffect(() => {
4723
6565
  const viewport = viewportRef.current;
4724
6566
  if (!viewport) return;
4725
6567
  previousScrollTopRef.current = viewport.scrollTop;
@@ -4800,14 +6642,14 @@ function Chat({
4800
6642
  window.removeEventListener("pointercancel", stopPointerTracking);
4801
6643
  };
4802
6644
  }, [cancelPendingAutoScroll, disableAutoFollow]);
4803
- React22.useEffect(() => {
6645
+ React26.useEffect(() => {
4804
6646
  shouldAutoScrollRef.current = true;
4805
6647
  forceFollowRef.current = false;
4806
6648
  previousScrollTopRef.current = 0;
4807
6649
  setIsAtBottom(true);
4808
6650
  setHasUpdatesBelow(false);
4809
6651
  }, [stream.threadId]);
4810
- React22.useEffect(() => {
6652
+ React26.useEffect(() => {
4811
6653
  const messageCountChanged = messages.length !== previousMessageCountRef.current;
4812
6654
  previousMessageCountRef.current = messages.length;
4813
6655
  if (!shouldAutoScrollRef.current) {
@@ -4826,7 +6668,7 @@ function Chat({
4826
6668
  clientSecret: effectiveClientSecret
4827
6669
  });
4828
6670
  const missingConfig = Boolean(missingConfigKind);
4829
- const missingConfigShortMessage = React22.useMemo(() => {
6671
+ const missingConfigShortMessage = React26.useMemo(() => {
4830
6672
  switch (missingConfigKind) {
4831
6673
  case "apiUrl":
4832
6674
  return t("chat.missingApiUrlShort");
@@ -4838,7 +6680,7 @@ function Chat({
4838
6680
  return t("chat.missingConfigShort");
4839
6681
  }
4840
6682
  }, [missingConfigKind, t]);
4841
- const missingConfigDetailMessage = React22.useMemo(() => {
6683
+ const missingConfigDetailMessage = React26.useMemo(() => {
4842
6684
  switch (missingConfigKind) {
4843
6685
  case "apiUrl":
4844
6686
  return t("chat.missingApiUrlDetail");
@@ -4852,8 +6694,8 @@ function Chat({
4852
6694
  }, [missingConfigKind, t]);
4853
6695
  const showMissingConfig = !isClientSecretInitializing && missingConfig;
4854
6696
  const hasUploadingFiles = attachments.some((a) => a.status === "uploading");
4855
- const isSendDisabled = !trimmedDraft && !hasReferences || missingConfig || isHistoryLoading || hasUploadingFiles || isUploadingReferenceImages;
4856
- const resizeComposerInput = React22.useCallback(() => {
6697
+ const isSendDisabled = !trimmedDraft && !hasReferences || hasPendingRequestUserInput || missingConfig || isHistoryLoading || hasUploadingFiles || isUploadingReferenceImages;
6698
+ const resizeComposerInput = React26.useCallback(() => {
4857
6699
  const textarea = composerInputRef.current;
4858
6700
  if (!textarea) {
4859
6701
  return;
@@ -4866,16 +6708,16 @@ function Chat({
4866
6708
  textarea.style.height = `${nextHeight}px`;
4867
6709
  textarea.style.overflowY = textarea.scrollHeight > COMPOSER_INPUT_MAX_HEIGHT ? "auto" : "hidden";
4868
6710
  }, []);
4869
- React22.useEffect(() => {
6711
+ React26.useEffect(() => {
4870
6712
  resizeComposerInput();
4871
6713
  }, [draft, resizeComposerInput]);
4872
- React22.useEffect(() => {
6714
+ React26.useEffect(() => {
4873
6715
  document.addEventListener("selectionchange", syncQuoteSelection);
4874
6716
  return () => {
4875
6717
  document.removeEventListener("selectionchange", syncQuoteSelection);
4876
6718
  };
4877
6719
  }, [syncQuoteSelection]);
4878
- React22.useEffect(() => {
6720
+ React26.useEffect(() => {
4879
6721
  const viewport = viewportRef.current;
4880
6722
  if (!viewport) {
4881
6723
  return;
@@ -4892,14 +6734,14 @@ function Chat({
4892
6734
  window.removeEventListener("resize", handleViewportScroll);
4893
6735
  };
4894
6736
  }, [clearQuoteSelection]);
4895
- React22.useEffect(() => {
6737
+ React26.useEffect(() => {
4896
6738
  clearQuoteSelection();
4897
6739
  }, [messages.length, stream.threadId, clearQuoteSelection]);
4898
- React22.useEffect(() => {
6740
+ React26.useEffect(() => {
4899
6741
  if (missingConfig) return;
4900
6742
  void refreshThreads();
4901
6743
  }, [missingConfig, refreshThreads]);
4902
- React22.useEffect(() => {
6744
+ React26.useEffect(() => {
4903
6745
  if (missingConfig || !stream.client || !stream.assistantId) {
4904
6746
  setAssistantName(null);
4905
6747
  setAssistantAvatar(null);
@@ -4930,7 +6772,7 @@ function Chat({
4930
6772
  mimetype: a.storageFile?.mimetype ?? a.file.type,
4931
6773
  size: a.storageFile?.size ?? a.file.size
4932
6774
  }));
4933
- const submitDraft = React22.useCallback(
6775
+ const submitDraft = React26.useCallback(
4934
6776
  (followUpOverride) => {
4935
6777
  if (isSendDisabled) return;
4936
6778
  const filesToSend = uploadedFiles.length > 0 ? [...uploadedFiles] : void 0;
@@ -4960,6 +6802,9 @@ function Chat({
4960
6802
  if (filesToSend) {
4961
6803
  inputPayload.files = filesToSend;
4962
6804
  }
6805
+ if (planModeEnabled) {
6806
+ inputPayload.planMode = true;
6807
+ }
4963
6808
  const requestOptions = buildInjectedRequestOptions({
4964
6809
  defaults: options?.request,
4965
6810
  humanInput: inputPayload
@@ -4994,6 +6839,7 @@ function Chat({
4994
6839
  references,
4995
6840
  scrollToBottom,
4996
6841
  selectedTool,
6842
+ planModeEnabled,
4997
6843
  stream,
4998
6844
  trimmedDraft,
4999
6845
  uploadedFiles,
@@ -5004,7 +6850,7 @@ function Chat({
5004
6850
  event.preventDefault();
5005
6851
  submitDraft();
5006
6852
  };
5007
- const handleEditPendingFollowUp = React22.useCallback(
6853
+ const handleEditPendingFollowUp = React26.useCallback(
5008
6854
  (id) => {
5009
6855
  const item = pendingFollowUps.find(
5010
6856
  (entry) => entry.id === id && entry.mode === "queue"
@@ -5031,7 +6877,7 @@ function Chat({
5031
6877
  },
5032
6878
  [pendingFollowUps, stream]
5033
6879
  );
5034
- const handleQuoteSelection = React22.useCallback(() => {
6880
+ const handleQuoteSelection = React26.useCallback(() => {
5035
6881
  if (!quoteSelection) {
5036
6882
  return;
5037
6883
  }
@@ -5047,7 +6893,7 @@ function Chat({
5047
6893
  const handleAttachmentClick = () => {
5048
6894
  fileInputRef.current?.click();
5049
6895
  };
5050
- const uploadContextFile = React22.useCallback(
6896
+ const uploadContextFile = React26.useCallback(
5051
6897
  (file) => stream.client.contexts.uploadFile(file),
5052
6898
  [stream.client]
5053
6899
  );
@@ -5073,7 +6919,7 @@ function Chat({
5073
6919
  }
5074
6920
  submitDraft();
5075
6921
  };
5076
- const handleComposerPaste = React22.useCallback(
6922
+ const handleComposerPaste = React26.useCallback(
5077
6923
  (event) => {
5078
6924
  const clipboardData = event.clipboardData;
5079
6925
  if (!clipboardData) {
@@ -5152,18 +6998,18 @@ function Chat({
5152
6998
  uploadContextFile
5153
6999
  ]
5154
7000
  );
5155
- const alternateFollowUpShortcutLabel = React22.useMemo(() => {
7001
+ const alternateFollowUpShortcutLabel = React26.useMemo(() => {
5156
7002
  if (typeof navigator === "undefined") {
5157
7003
  return "\u2318Enter";
5158
7004
  }
5159
7005
  const platform = navigator.platform || navigator.userAgent;
5160
7006
  return /Mac|iPhone|iPad|iPod/i.test(platform) ? "\u2318Enter" : "Ctrl+Enter";
5161
7007
  }, []);
5162
- const followUpShortcutLabels = React22.useMemo(
7008
+ const followUpShortcutLabels = React26.useMemo(
5163
7009
  () => getComposerFollowUpShortcutLabels(alternateFollowUpShortcutLabel),
5164
7010
  [alternateFollowUpShortcutLabel]
5165
7011
  );
5166
- const uploadFile = React22.useCallback(
7012
+ const uploadFile = React26.useCallback(
5167
7013
  async (localId, file) => {
5168
7014
  try {
5169
7015
  const result = await uploadContextFile(file);
@@ -5186,7 +7032,7 @@ function Chat({
5186
7032
  },
5187
7033
  [uploadContextFile]
5188
7034
  );
5189
- const handleRetryUpload = React22.useCallback(
7035
+ const handleRetryUpload = React26.useCallback(
5190
7036
  (localId) => {
5191
7037
  const attachment = attachments.find((a) => a.localId === localId);
5192
7038
  if (!attachment || attachment.status !== "error") return;
@@ -5257,10 +7103,23 @@ function Chat({
5257
7103
  content: prompt
5258
7104
  };
5259
7105
  const nextFollowUpMode = stream.isLoading ? stream.followUpBehavior : void 0;
7106
+ const inputPayload = {
7107
+ input: prompt,
7108
+ ...planModeEnabled ? { planMode: true } : {}
7109
+ };
7110
+ const requestOptions = buildInjectedRequestOptions({
7111
+ defaults: options?.request,
7112
+ humanInput: inputPayload
7113
+ });
5260
7114
  stream.submit(
5261
- { input: { input: prompt } },
7115
+ {
7116
+ input: inputPayload,
7117
+ ...requestOptions.state ? { state: requestOptions.state } : {}
7118
+ },
5262
7119
  {
5263
7120
  ...nextFollowUpMode ? { followUpMode: nextFollowUpMode } : {},
7121
+ ...requestOptions.context ? { context: requestOptions.context } : {},
7122
+ ...requestOptions.config ? { config: requestOptions.config } : {},
5264
7123
  ...!nextFollowUpMode ? {
5265
7124
  optimisticValues: (prev) => {
5266
7125
  const prevMessages = prev?.messages ?? [];
@@ -5271,7 +7130,7 @@ function Chat({
5271
7130
  );
5272
7131
  scrollToBottom(true, true);
5273
7132
  };
5274
- const loadConversationMessages = React22.useCallback(
7133
+ const loadConversationMessages = React26.useCallback(
5275
7134
  async (recordId) => {
5276
7135
  if (missingConfig) {
5277
7136
  setHistoryError(missingConfigShortMessage);
@@ -5357,18 +7216,18 @@ function Chat({
5357
7216
  }
5358
7217
  };
5359
7218
  const acceptMimes = composer?.attachments?.accept ? Object.entries(composer.attachments.accept).map(([mime, exts]) => [mime, ...exts.map((e) => `.${e}`)].join(",")).join(",") : void 0;
5360
- const currentThread = React22.useMemo(
7219
+ const currentThread = React26.useMemo(
5361
7220
  () => threads.find((item) => item.id === stream.threadId),
5362
7221
  [threads, stream.threadId]
5363
7222
  );
5364
7223
  const errorMessage = stream.error instanceof Error ? stream.error.message : void 0;
5365
- const threadErrorMessage = React22.useMemo(() => {
7224
+ const threadErrorMessage = React26.useMemo(() => {
5366
7225
  if (currentThread?.status !== "error") return void 0;
5367
7226
  const message = currentThread.error?.trim();
5368
7227
  return message || t("thread.errorToast");
5369
7228
  }, [currentThread, t]);
5370
7229
  const assistantTitle = assistantName || resolvedTitle;
5371
- return /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)(
7230
+ return /* @__PURE__ */ (0, import_jsx_runtime32.jsxs)(
5372
7231
  "div",
5373
7232
  {
5374
7233
  ref: viewportRef,
@@ -5377,10 +7236,10 @@ function Chat({
5377
7236
  className
5378
7237
  ),
5379
7238
  children: [
5380
- /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("div", { className: "flex items-center justify-between border-b p-2 sticky top-0 z-10 bg-background", children: [
5381
- /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("div", { className: "flex items-center gap-3 overflow-hidden", children: [
5382
- /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("div", { className: "relative shrink-0", children: [
5383
- /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
7239
+ /* @__PURE__ */ (0, import_jsx_runtime32.jsxs)("div", { className: "flex items-center justify-between border-b p-2 sticky top-0 z-10 bg-background", children: [
7240
+ /* @__PURE__ */ (0, import_jsx_runtime32.jsxs)("div", { className: "flex items-center gap-3 overflow-hidden", children: [
7241
+ /* @__PURE__ */ (0, import_jsx_runtime32.jsxs)("div", { className: "relative shrink-0", children: [
7242
+ /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(
5384
7243
  ChatkitAvatar,
5385
7244
  {
5386
7245
  avatar: assistantAvatar,
@@ -5388,10 +7247,10 @@ function Chat({
5388
7247
  label: assistantTitle
5389
7248
  }
5390
7249
  ),
5391
- /* @__PURE__ */ (0, import_jsx_runtime28.jsx)("span", { className: "absolute bottom-0 right-0 h-2.5 w-2.5 rounded-full border-2 border-background bg-green-500" })
7250
+ /* @__PURE__ */ (0, import_jsx_runtime32.jsx)("span", { className: "absolute bottom-0 right-0 h-2.5 w-2.5 rounded-full border-2 border-background bg-green-500" })
5392
7251
  ] }),
5393
- /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("div", { className: "truncate", children: [
5394
- /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
7252
+ /* @__PURE__ */ (0, import_jsx_runtime32.jsxs)("div", { className: "truncate", children: [
7253
+ /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(
5395
7254
  "h2",
5396
7255
  {
5397
7256
  className: "text-lg font-semibold truncate",
@@ -5399,27 +7258,30 @@ function Chat({
5399
7258
  children: assistantTitle
5400
7259
  }
5401
7260
  ),
5402
- /* @__PURE__ */ (0, import_jsx_runtime28.jsx)("p", { className: "text-xs text-muted-foreground", children: t("chat.statusOnline") })
7261
+ /* @__PURE__ */ (0, import_jsx_runtime32.jsx)("p", { className: "text-xs text-muted-foreground", children: t("chat.statusOnline") })
5403
7262
  ] })
5404
7263
  ] }),
5405
- history?.enabled !== false && /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("div", { className: "flex items-center gap-1", children: [
5406
- /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
5407
- "button",
5408
- {
5409
- type: "button",
5410
- onClick: handleNewThread,
5411
- disabled: missingConfig || isHistoryLoading,
5412
- className: cn(
5413
- "flex h-8 w-8 cursor-pointer items-center justify-center rounded-md",
5414
- "text-muted-foreground hover:text-foreground hover:bg-muted",
5415
- "transition-colors duration-150",
5416
- "disabled:opacity-50 disabled:cursor-not-allowed"
5417
- ),
5418
- title: t("history.newThread"),
5419
- children: /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(import_lucide_react11.Pencil, { size: 16 })
5420
- }
5421
- ),
5422
- /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
7264
+ history?.enabled !== false && /* @__PURE__ */ (0, import_jsx_runtime32.jsxs)("div", { className: "flex items-center gap-1", children: [
7265
+ /* @__PURE__ */ (0, import_jsx_runtime32.jsxs)(Tooltip, { children: [
7266
+ /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(TooltipTrigger, { asChild: true, children: /* @__PURE__ */ (0, import_jsx_runtime32.jsx)("span", { className: "inline-flex h-8 w-8", children: /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(
7267
+ "button",
7268
+ {
7269
+ type: "button",
7270
+ onClick: handleNewThread,
7271
+ disabled: missingConfig || isHistoryLoading,
7272
+ className: cn(
7273
+ "flex h-8 w-8 cursor-pointer items-center justify-center rounded-md",
7274
+ "text-muted-foreground hover:text-foreground hover:bg-muted",
7275
+ "transition-colors duration-150",
7276
+ "disabled:pointer-events-none disabled:opacity-50 disabled:cursor-not-allowed"
7277
+ ),
7278
+ "aria-label": t("history.newThread"),
7279
+ children: /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(import_lucide_react15.Pencil, { size: 16 })
7280
+ }
7281
+ ) }) }),
7282
+ /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(TooltipContent, { side: "bottom", children: t("history.newThread") })
7283
+ ] }),
7284
+ /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(
5423
7285
  HistorySidebar,
5424
7286
  {
5425
7287
  threads,
@@ -5433,18 +7295,18 @@ function Chat({
5433
7295
  )
5434
7296
  ] })
5435
7297
  ] }),
5436
- /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("div", { className: "flex-1 p-4", children: [
5437
- errorMessage && /* @__PURE__ */ (0, import_jsx_runtime28.jsx)("div", { className: "mb-4 rounded-lg border border-destructive/30 bg-destructive/10 px-3 py-2 text-sm text-destructive", children: errorMessage }),
5438
- historyError && /* @__PURE__ */ (0, import_jsx_runtime28.jsx)("div", { className: "mb-4 rounded-lg border border-amber-200 bg-amber-50 px-3 py-2 text-sm text-amber-900", children: historyError }),
5439
- showMissingConfig && /* @__PURE__ */ (0, import_jsx_runtime28.jsx)("div", { className: "mb-4 rounded-lg border border-amber-200 bg-amber-50 px-3 py-2 text-sm text-amber-900", children: missingConfigDetailMessage }),
5440
- isHistoryLoading && /* @__PURE__ */ (0, import_jsx_runtime28.jsx)("div", { className: "mb-4 rounded-lg border border-muted px-3 py-2 text-sm text-muted-foreground", children: t("chat.loadingThread") }),
5441
- messages.length === 0 ? /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
7298
+ /* @__PURE__ */ (0, import_jsx_runtime32.jsxs)("div", { className: "flex-1 p-4", children: [
7299
+ errorMessage && /* @__PURE__ */ (0, import_jsx_runtime32.jsx)("div", { className: "mb-4 rounded-lg border border-destructive/30 bg-destructive/10 px-3 py-2 text-sm text-destructive", children: errorMessage }),
7300
+ historyError && /* @__PURE__ */ (0, import_jsx_runtime32.jsx)("div", { className: "mb-4 rounded-lg border border-amber-200 bg-amber-50 px-3 py-2 text-sm text-amber-900", children: historyError }),
7301
+ showMissingConfig && /* @__PURE__ */ (0, import_jsx_runtime32.jsx)("div", { className: "mb-4 rounded-lg border border-amber-200 bg-amber-50 px-3 py-2 text-sm text-amber-900", children: missingConfigDetailMessage }),
7302
+ isHistoryLoading && /* @__PURE__ */ (0, import_jsx_runtime32.jsx)("div", { className: "mb-4 rounded-lg border border-muted px-3 py-2 text-sm text-muted-foreground", children: t("chat.loadingThread") }),
7303
+ messages.length === 0 ? /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(
5442
7304
  StartScreen,
5443
7305
  {
5444
7306
  startScreen,
5445
7307
  onPromptClick: handlePromptClick
5446
7308
  }
5447
- ) : /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("div", { className: "space-y-4", children: [
7309
+ ) : /* @__PURE__ */ (0, import_jsx_runtime32.jsxs)("div", { className: "space-y-4", children: [
5448
7310
  messages.map((message, index) => {
5449
7311
  const messageType = String(message.type);
5450
7312
  const isAssistantMessage = messageType === "assistant" || messageType === "ai";
@@ -5471,7 +7333,7 @@ function Chat({
5471
7333
  if (!isAssistantMessage && !hasPlainRenderableContent && !hasHumanAttachments && humanReferences.length === 0) {
5472
7334
  return null;
5473
7335
  }
5474
- return /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
7336
+ return /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(
5475
7337
  "div",
5476
7338
  {
5477
7339
  className: cn(
@@ -5479,8 +7341,8 @@ function Chat({
5479
7341
  message.type === "human" ? "justify-end" : "justify-start -ml-1"
5480
7342
  // AI messages: slightly closer to left
5481
7343
  ),
5482
- children: /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("div", { className: "flex flex-col px-3 overflow-hidden", children: [
5483
- /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
7344
+ children: /* @__PURE__ */ (0, import_jsx_runtime32.jsxs)("div", { className: "flex flex-col px-3 overflow-hidden", children: [
7345
+ /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(
5484
7346
  "div",
5485
7347
  {
5486
7348
  ...canQuoteMessage ? {
@@ -5492,18 +7354,24 @@ function Chat({
5492
7354
  message.type === "human" ? "bg-primary text-primary-foreground px-4 py-2.5" : message.type === "system" ? "bg-muted text-muted-foreground text-xs px-4 py-2.5" : "py-1 text-chat-foreground"
5493
7355
  // AI messages: use chat-specific foreground color
5494
7356
  ),
5495
- children: isAssistantMessage ? /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
7357
+ children: isAssistantMessage ? /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(
5496
7358
  AssistantMessage,
5497
7359
  {
5498
7360
  message: {
5499
7361
  ...message,
5500
7362
  type: "assistant"
5501
7363
  },
7364
+ messages: messages.slice(0, index + 1).map(
7365
+ (item) => ({
7366
+ ...item,
7367
+ type: String(item.type) === "ai" ? "assistant" : item.type
7368
+ })
7369
+ ),
5502
7370
  isStreaming: isStreamingMessage,
5503
7371
  streamingStatus
5504
7372
  }
5505
- ) : /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)(import_jsx_runtime28.Fragment, { children: [
5506
- message.type === "human" && humanReferences.length > 0 && /* @__PURE__ */ (0, import_jsx_runtime28.jsx)("div", { className: "mb-2 flex flex-wrap gap-1.5", children: humanReferences.map((reference) => /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
7373
+ ) : /* @__PURE__ */ (0, import_jsx_runtime32.jsxs)(import_jsx_runtime32.Fragment, { children: [
7374
+ message.type === "human" && humanReferences.length > 0 && /* @__PURE__ */ (0, import_jsx_runtime32.jsx)("div", { className: "mb-2 flex flex-wrap gap-1.5", children: humanReferences.map((reference) => /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(
5507
7375
  ReferenceChip,
5508
7376
  {
5509
7377
  reference,
@@ -5511,29 +7379,29 @@ function Chat({
5511
7379
  },
5512
7380
  getReferenceKey(reference)
5513
7381
  )) }),
5514
- message.type === "human" && humanAttachments.length > 0 && /* @__PURE__ */ (0, import_jsx_runtime28.jsx)("div", { className: "flex flex-wrap gap-1.5 mb-2", children: humanAttachments.map((file, fileIndex) => /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)(
7382
+ message.type === "human" && humanAttachments.length > 0 && /* @__PURE__ */ (0, import_jsx_runtime32.jsx)("div", { className: "flex flex-wrap gap-1.5 mb-2", children: humanAttachments.map((file, fileIndex) => /* @__PURE__ */ (0, import_jsx_runtime32.jsxs)(
5515
7383
  "div",
5516
7384
  {
5517
7385
  className: "flex items-center gap-1.5 rounded-md bg-primary-foreground/20 px-2 py-1 text-xs",
5518
7386
  children: [
5519
- /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(import_lucide_react11.FileText, { size: 12 }),
5520
- /* @__PURE__ */ (0, import_jsx_runtime28.jsx)("span", { className: "max-w-[100px] truncate", children: file.originalName })
7387
+ /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(import_lucide_react15.FileText, { size: 12 }),
7388
+ /* @__PURE__ */ (0, import_jsx_runtime32.jsx)("span", { className: "max-w-[100px] truncate", children: file.originalName })
5521
7389
  ]
5522
7390
  },
5523
7391
  fileIndex
5524
7392
  )) }),
5525
- Array.isArray(message.content) ? message.content.map((part, partIndex) => /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
7393
+ Array.isArray(message.content) ? message.content.map((part, partIndex) => /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(
5526
7394
  "p",
5527
7395
  {
5528
7396
  className: "wrap-break-word text-sm leading-relaxed",
5529
7397
  children: formatMessageContent(part)
5530
7398
  },
5531
7399
  `${part.type}-${partIndex}`
5532
- )) : /* @__PURE__ */ (0, import_jsx_runtime28.jsx)("span", { className: "wrap-break-word text-sm leading-relaxed", children: formatMessageContent(message.content) })
7400
+ )) : /* @__PURE__ */ (0, import_jsx_runtime32.jsx)("span", { className: "wrap-break-word text-sm leading-relaxed", children: formatMessageContent(message.content) })
5533
7401
  ] })
5534
7402
  }
5535
7403
  ),
5536
- /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
7404
+ /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(
5537
7405
  MessageActions,
5538
7406
  {
5539
7407
  content: messageContent,
@@ -5569,7 +7437,7 @@ function Chat({
5569
7437
  stream.isLoading,
5570
7438
  { now: streamingNow }
5571
7439
  );
5572
- return /* @__PURE__ */ (0, import_jsx_runtime28.jsx)("div", { className: "flex justify-start gap-3 -ml-2", children: /* @__PURE__ */ (0, import_jsx_runtime28.jsx)("div", { className: "max-w-full rounded-2xl py-2.5", children: /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
7440
+ return /* @__PURE__ */ (0, import_jsx_runtime32.jsx)("div", { className: "flex justify-start gap-3 -ml-2", children: /* @__PURE__ */ (0, import_jsx_runtime32.jsx)("div", { className: "max-w-full rounded-2xl py-2.5", children: /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(
5573
7441
  AssistantStreamingIndicator,
5574
7442
  {
5575
7443
  status: fallbackStreamingStatus ?? "loading"
@@ -5578,7 +7446,7 @@ function Chat({
5578
7446
  })()
5579
7447
  ] })
5580
7448
  ] }),
5581
- !isAtBottom && messages.length > 0 && /* @__PURE__ */ (0, import_jsx_runtime28.jsx)("div", { className: "sticky bottom-20 z-20 flex justify-center px-4 pointer-events-none", children: /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
7449
+ !isAtBottom && messages.length > 0 && /* @__PURE__ */ (0, import_jsx_runtime32.jsx)("div", { className: "sticky bottom-20 z-20 flex justify-center px-4 pointer-events-none", children: /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(
5582
7450
  Button,
5583
7451
  {
5584
7452
  type: "button",
@@ -5591,10 +7459,10 @@ function Chat({
5591
7459
  onClick: () => scrollToBottom(true, true),
5592
7460
  "aria-label": t("chat.scrollToBottom"),
5593
7461
  title: t("chat.scrollToBottom"),
5594
- children: /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(import_lucide_react11.ArrowDown, { size: 16 })
7462
+ children: /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(import_lucide_react15.ArrowDown, { size: 16 })
5595
7463
  }
5596
7464
  ) }),
5597
- quoteSelection && /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
7465
+ quoteSelection && /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(
5598
7466
  "div",
5599
7467
  {
5600
7468
  className: "pointer-events-none fixed z-50",
@@ -5603,7 +7471,7 @@ function Chat({
5603
7471
  left: `${quoteSelection.left}px`,
5604
7472
  transform: "translateX(-50%)"
5605
7473
  },
5606
- children: /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)(
7474
+ children: /* @__PURE__ */ (0, import_jsx_runtime32.jsxs)(
5607
7475
  Button,
5608
7476
  {
5609
7477
  type: "button",
@@ -5615,16 +7483,16 @@ function Chat({
5615
7483
  "aria-label": t("composer.quoteSelection"),
5616
7484
  title: t("composer.quoteSelection"),
5617
7485
  children: [
5618
- /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(import_lucide_react11.Quote, { size: 14 }),
7486
+ /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(import_lucide_react15.Quote, { size: 14 }),
5619
7487
  t("composer.quoteSelection")
5620
7488
  ]
5621
7489
  }
5622
7490
  )
5623
7491
  }
5624
7492
  ),
5625
- /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("div", { className: "p-2 sticky bottom-0 z-10 bg-background", children: [
5626
- threadErrorMessage && /* @__PURE__ */ (0, import_jsx_runtime28.jsx)("div", { className: "mb-3 rounded-lg border border-destructive/30 bg-destructive/10 px-3 py-2 text-sm text-destructive overflow-auto", children: threadErrorMessage }),
5627
- /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
7493
+ /* @__PURE__ */ (0, import_jsx_runtime32.jsxs)("div", { className: "p-2 sticky bottom-0 z-10 bg-background", children: [
7494
+ threadErrorMessage && /* @__PURE__ */ (0, import_jsx_runtime32.jsx)("div", { className: "mb-3 rounded-lg border border-destructive/30 bg-destructive/10 px-3 py-2 text-sm text-destructive overflow-auto", children: threadErrorMessage }),
7495
+ /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(
5628
7496
  "input",
5629
7497
  {
5630
7498
  ref: fileInputRef,
@@ -5635,7 +7503,7 @@ function Chat({
5635
7503
  className: "hidden"
5636
7504
  }
5637
7505
  ),
5638
- attachments.length > 0 && /* @__PURE__ */ (0, import_jsx_runtime28.jsx)("div", { className: "mb-3 flex flex-wrap gap-2", children: attachments.map((item) => /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)(
7506
+ attachments.length > 0 && /* @__PURE__ */ (0, import_jsx_runtime32.jsx)("div", { className: "mb-3 flex flex-wrap gap-2", children: attachments.map((item) => /* @__PURE__ */ (0, import_jsx_runtime32.jsxs)(
5639
7507
  "div",
5640
7508
  {
5641
7509
  className: cn(
@@ -5643,16 +7511,16 @@ function Chat({
5643
7511
  item.status === "error" ? "bg-destructive/10 border border-destructive/30" : "bg-muted"
5644
7512
  ),
5645
7513
  children: [
5646
- item.status === "uploading" && /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
5647
- import_lucide_react11.Loader2,
7514
+ item.status === "uploading" && /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(
7515
+ import_lucide_react15.Loader2,
5648
7516
  {
5649
7517
  size: 14,
5650
7518
  className: "animate-spin text-muted-foreground"
5651
7519
  }
5652
7520
  ),
5653
- item.status === "success" && /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(import_lucide_react11.FileText, { size: 14, className: "text-muted-foreground" }),
5654
- item.status === "error" && /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(import_lucide_react11.FileText, { size: 14, className: "text-destructive" }),
5655
- /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
7521
+ item.status === "success" && /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(import_lucide_react15.FileText, { size: 14, className: "text-muted-foreground" }),
7522
+ item.status === "error" && /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(import_lucide_react15.FileText, { size: 14, className: "text-destructive" }),
7523
+ /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(
5656
7524
  "span",
5657
7525
  {
5658
7526
  className: cn(
@@ -5662,17 +7530,17 @@ function Chat({
5662
7530
  children: item.file.name
5663
7531
  }
5664
7532
  ),
5665
- item.status === "error" && /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
7533
+ item.status === "error" && /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(
5666
7534
  "button",
5667
7535
  {
5668
7536
  type: "button",
5669
7537
  onClick: () => handleRetryUpload(item.localId),
5670
7538
  className: "ml-1 rounded-full p-0.5 text-destructive hover:bg-destructive/20",
5671
7539
  title: t("chat.retryUpload"),
5672
- children: /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(import_lucide_react11.RefreshCw, { size: 12 })
7540
+ children: /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(import_lucide_react15.RefreshCw, { size: 12 })
5673
7541
  }
5674
7542
  ),
5675
- /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
7543
+ /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(
5676
7544
  "button",
5677
7545
  {
5678
7546
  type: "button",
@@ -5681,14 +7549,14 @@ function Chat({
5681
7549
  "ml-1 rounded-full p-0.5",
5682
7550
  item.status === "error" ? "text-destructive hover:bg-destructive/20" : "hover:bg-muted-foreground/20"
5683
7551
  ),
5684
- children: /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(import_lucide_react11.X, { size: 12 })
7552
+ children: /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(import_lucide_react15.X, { size: 12 })
5685
7553
  }
5686
7554
  )
5687
7555
  ]
5688
7556
  },
5689
7557
  item.localId
5690
7558
  )) }),
5691
- references.length > 0 && /* @__PURE__ */ (0, import_jsx_runtime28.jsx)("div", { className: "mb-3 flex flex-wrap gap-2", children: references.map((reference) => /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
7559
+ references.length > 0 && /* @__PURE__ */ (0, import_jsx_runtime32.jsx)("div", { className: "mb-3 flex flex-wrap gap-2", children: references.map((reference) => /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(
5692
7560
  ReferenceChip,
5693
7561
  {
5694
7562
  reference,
@@ -5702,19 +7570,27 @@ function Chat({
5702
7570
  },
5703
7571
  getReferenceKey(reference)
5704
7572
  )) }),
5705
- selectedTool && /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("div", { className: "mb-2 flex items-center gap-2", children: [
5706
- /* @__PURE__ */ (0, import_jsx_runtime28.jsx)("span", { className: "rounded-full bg-primary/10 px-2 py-0.5 text-xs font-medium text-primary", children: selectedTool.shortLabel ?? selectedTool.label }),
5707
- /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
7573
+ selectedTool && /* @__PURE__ */ (0, import_jsx_runtime32.jsxs)("div", { className: "mb-2 flex items-center gap-2", children: [
7574
+ /* @__PURE__ */ (0, import_jsx_runtime32.jsx)("span", { className: "rounded-full bg-primary/10 px-2 py-0.5 text-xs font-medium text-primary", children: selectedTool.shortLabel ?? selectedTool.label }),
7575
+ /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(
5708
7576
  "button",
5709
7577
  {
5710
7578
  type: "button",
5711
7579
  onClick: () => setSelectedTool(null),
5712
7580
  className: "rounded-full p-0.5 text-muted-foreground hover:bg-muted",
5713
- children: /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(import_lucide_react11.X, { size: 12 })
7581
+ children: /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(import_lucide_react15.X, { size: 12 })
5714
7582
  }
5715
7583
  )
5716
7584
  ] }),
5717
- /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
7585
+ /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(
7586
+ PendingTodos,
7587
+ {
7588
+ snapshot: stream.todos,
7589
+ attachToComposer: !hasPendingFollowUps,
7590
+ className: hasPendingFollowUps ? "mb-2" : void 0
7591
+ }
7592
+ ),
7593
+ /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(
5718
7594
  PendingFollowUps,
5719
7595
  {
5720
7596
  items: pendingFollowUps,
@@ -5725,10 +7601,20 @@ function Chat({
5725
7601
  canSendNow: stream.canSendPendingFollowUpNow,
5726
7602
  onSendNow: (id) => stream.sendPendingFollowUpNow(id),
5727
7603
  onEdit: handleEditPendingFollowUp,
5728
- onRemove: stream.removePendingFollowUp
7604
+ onRemove: stream.removePendingFollowUp,
7605
+ attachToComposer: true
7606
+ }
7607
+ ),
7608
+ /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(
7609
+ RequestUserInputPanel,
7610
+ {
7611
+ request: stream.pendingRequestUserInput,
7612
+ onSubmit: stream.submitRequestUserInput,
7613
+ onDismiss: stream.stop,
7614
+ attachToComposer: true
5729
7615
  }
5730
7616
  ),
5731
- /* @__PURE__ */ (0, import_jsx_runtime28.jsx)("form", { className: "flex items-end", onSubmit: handleSubmit, children: /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)(
7617
+ /* @__PURE__ */ (0, import_jsx_runtime32.jsx)("form", { className: "flex items-end", onSubmit: handleSubmit, children: /* @__PURE__ */ (0, import_jsx_runtime32.jsxs)(
5732
7618
  "div",
5733
7619
  {
5734
7620
  className: cn(
@@ -5740,17 +7626,19 @@ function Chat({
5740
7626
  getRoundedClass(theme.radius)
5741
7627
  ),
5742
7628
  children: [
5743
- /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
7629
+ /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(
5744
7630
  ComposerMenu,
5745
7631
  {
5746
7632
  composer,
5747
7633
  onAttachmentClick: handleAttachmentClick,
5748
7634
  onToolSelect: handleToolSelect,
5749
7635
  selectedTool,
5750
- disabled: missingConfig || isHistoryLoading
7636
+ planModeEnabled,
7637
+ onPlanModeChange: setPlanModeEnabled,
7638
+ disabled: missingConfig || isHistoryLoading || hasPendingRequestUserInput
5751
7639
  }
5752
7640
  ),
5753
- /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
7641
+ /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(
5754
7642
  "textarea",
5755
7643
  {
5756
7644
  ref: composerInputRef,
@@ -5760,7 +7648,7 @@ function Chat({
5760
7648
  onKeyDown: handleComposerKeyDown,
5761
7649
  rows: 1,
5762
7650
  placeholder: inputPlaceholder,
5763
- disabled: missingConfig || isHistoryLoading,
7651
+ disabled: missingConfig || isHistoryLoading || hasPendingRequestUserInput,
5764
7652
  className: cn(
5765
7653
  "min-h-8 max-h-32 flex-1 resize-none bg-transparent py-1 pr-2 text-sm leading-5 text-foreground outline-none",
5766
7654
  "placeholder:text-muted-foreground",
@@ -5768,12 +7656,12 @@ function Chat({
5768
7656
  )
5769
7657
  }
5770
7658
  ),
5771
- /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
7659
+ /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(
5772
7660
  SendButton,
5773
7661
  {
5774
7662
  disabled: isSendDisabled,
5775
7663
  isLoading: stream.isLoading,
5776
- showStop: stream.isLoading && !trimmedDraft,
7664
+ showStop: stream.isLoading && (!trimmedDraft || hasPendingRequestUserInput),
5777
7665
  onStop: () => stream.stop(),
5778
7666
  stopLabel: t("chat.stop"),
5779
7667
  sendLabel: t("chat.send"),
@@ -5792,7 +7680,7 @@ function Chat({
5792
7680
  ]
5793
7681
  }
5794
7682
  ) }),
5795
- disclaimer?.text && /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(
7683
+ disclaimer?.text && /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(
5796
7684
  "p",
5797
7685
  {
5798
7686
  className: cn(
@@ -5802,9 +7690,9 @@ function Chat({
5802
7690
  children: disclaimer.text
5803
7691
  }
5804
7692
  ),
5805
- /* @__PURE__ */ (0, import_jsx_runtime28.jsxs)("div", { className: "mt-2 flex items-center justify-center gap-2 text-xs text-muted-foreground", children: [
5806
- /* @__PURE__ */ (0, import_jsx_runtime28.jsx)("span", { children: t("chat.poweredBy") }),
5807
- /* @__PURE__ */ (0, import_jsx_runtime28.jsx)(ContextUsageIndicator, { className: "absolute right-4" })
7693
+ /* @__PURE__ */ (0, import_jsx_runtime32.jsxs)("div", { className: "mt-2 flex items-center justify-center gap-2 text-xs text-muted-foreground", children: [
7694
+ /* @__PURE__ */ (0, import_jsx_runtime32.jsx)("span", { children: t("chat.poweredBy") }),
7695
+ /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(ContextUsageIndicator, { className: "absolute right-4" })
5808
7696
  ] })
5809
7697
  ] })
5810
7698
  ]
@@ -5813,11 +7701,11 @@ function Chat({
5813
7701
  }
5814
7702
 
5815
7703
  // src/components/ui/input.tsx
5816
- var React23 = __toESM(require("react"), 1);
5817
- var import_jsx_runtime29 = require("react/jsx-runtime");
5818
- var Input = React23.forwardRef(
7704
+ var React27 = __toESM(require("react"), 1);
7705
+ var import_jsx_runtime33 = require("react/jsx-runtime");
7706
+ var Input = React27.forwardRef(
5819
7707
  ({ className, type, ...props }, ref) => {
5820
- return /* @__PURE__ */ (0, import_jsx_runtime29.jsx)(
7708
+ return /* @__PURE__ */ (0, import_jsx_runtime33.jsx)(
5821
7709
  "input",
5822
7710
  {
5823
7711
  ref,
@@ -5834,10 +7722,10 @@ var Input = React23.forwardRef(
5834
7722
  Input.displayName = "Input";
5835
7723
 
5836
7724
  // src/components/ui/separator.tsx
5837
- var React24 = __toESM(require("react"), 1);
5838
- var import_jsx_runtime30 = require("react/jsx-runtime");
5839
- var Separator = React24.forwardRef(
5840
- ({ className, orientation = "horizontal", ...props }, ref) => /* @__PURE__ */ (0, import_jsx_runtime30.jsx)(
7725
+ var React28 = __toESM(require("react"), 1);
7726
+ var import_jsx_runtime34 = require("react/jsx-runtime");
7727
+ var Separator = React28.forwardRef(
7728
+ ({ className, orientation = "horizontal", ...props }, ref) => /* @__PURE__ */ (0, import_jsx_runtime34.jsx)(
5841
7729
  "div",
5842
7730
  {
5843
7731
  ref,