agentworkshop 0.7.58 → 0.7.60

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 (545) hide show
  1. package/.AgentWorkShop/prompts/host-tools.json +108 -0
  2. package/.output/.AgentWorkShop/prompts/host-tools.json +108 -0
  3. package/.output/.AgentWorkShop/schema.json +1 -0
  4. package/.output/nitro.json +1 -1
  5. package/.output/public/_nuxt/{CZwDnomB.js → 59a6cSgj.js} +1 -1
  6. package/.output/public/_nuxt/5juo_WO2.js +13 -0
  7. package/.output/public/_nuxt/9j2J4k4w.js +1 -0
  8. package/.output/public/_nuxt/B-WTxXEK2.js +1 -0
  9. package/.output/public/_nuxt/{DTx_DtUo.js → B0w8DZ4C.js} +1 -1
  10. package/.output/public/_nuxt/B1BCga5h2.js +13 -0
  11. package/.output/public/_nuxt/B5lMtA7I2.js +1 -0
  12. package/.output/public/_nuxt/B6_fJd2X.js +1 -0
  13. package/.output/public/_nuxt/B7K5B04W2.js +1 -0
  14. package/.output/public/_nuxt/B7KyS_q2.js +1 -0
  15. package/.output/public/_nuxt/B8q3BGY5.js +37 -0
  16. package/.output/public/_nuxt/B9IK8kDl2.js +1 -0
  17. package/.output/public/_nuxt/BFBysc2M2.js +1 -0
  18. package/.output/public/_nuxt/{BMUEVeOK.js → BGFhOMVM.js} +2 -2
  19. package/.output/public/_nuxt/{cBI0JqsV.js → BMlesJth.js} +1 -1
  20. package/.output/public/_nuxt/BNd2NDxg2.js +1 -0
  21. package/.output/public/_nuxt/BP629NAi.js +1 -0
  22. package/.output/public/_nuxt/BVinTfuN.js +1 -0
  23. package/.output/public/_nuxt/{DJZzthKt2.js → B_BYwIf22.js} +1 -1
  24. package/.output/public/_nuxt/{CW1HGp5X.js → B_JLVF30.js} +1 -1
  25. package/.output/public/_nuxt/BdE41Y_c.js +28 -0
  26. package/.output/public/_nuxt/Bdq2LNSO.js +1 -0
  27. package/.output/public/_nuxt/{BMZ1d25O.js → BeNdseTX.js} +1 -1
  28. package/.output/public/_nuxt/Be_StT8b2.js +1 -0
  29. package/.output/public/_nuxt/BhllzW3K2.js +1 -0
  30. package/.output/public/_nuxt/BjUpWKS6.js +1 -0
  31. package/.output/public/_nuxt/{CCCq9H7D2.js → BlEJRYAn2.js} +1 -1
  32. package/.output/public/_nuxt/{Du0zf-d3.js → BplhglEM.js} +1 -1
  33. package/.output/public/_nuxt/BsYEYxWv.js +24 -0
  34. package/.output/public/_nuxt/BtXwFpv42.js +1 -0
  35. package/.output/public/_nuxt/{BrFF_9742.js → BuNXYpib2.js} +1 -1
  36. package/.output/public/_nuxt/{BzKT-ne_2.js → C0sNwDTK2.js} +1 -1
  37. package/.output/public/_nuxt/{h46i74oE.js → C4AICl3l.js} +4 -4
  38. package/.output/public/_nuxt/{BuVH9MB-.js → C5OSTzBh.js} +1 -1
  39. package/.output/public/_nuxt/{DKhRushG.js → C8XVZGSZ.js} +1 -1
  40. package/.output/public/_nuxt/{zGDAozGA.js → C93LpBMF.js} +4 -4
  41. package/.output/public/_nuxt/CDaZC0_6.js +3 -0
  42. package/.output/public/_nuxt/CE43-V_L.js +2 -0
  43. package/.output/public/_nuxt/{B4R5CHkk.js → CEHT9inW.js} +1 -1
  44. package/.output/public/_nuxt/CGChCy-w2.js +1 -0
  45. package/.output/public/_nuxt/{DvUt9uMt2.js → CMDAjShv2.js} +1 -1
  46. package/.output/public/_nuxt/CUjdqsjC2.js +1 -0
  47. package/.output/public/_nuxt/CWfBtswB.js +70 -0
  48. package/.output/public/_nuxt/CYtH1bv2.js +1 -0
  49. package/.output/public/_nuxt/CZmMgjIK.js +1 -0
  50. package/.output/public/_nuxt/{iZa330UY.js → Cdw4juXw.js} +1 -1
  51. package/.output/public/_nuxt/{DMPpE41S2.js → Ce5SiMQR2.js} +1 -1
  52. package/.output/public/_nuxt/{B03LfmKR.js → Cfp00Rdo.js} +1 -1
  53. package/.output/public/_nuxt/{Dy-V8OEW2.js → CgbP5yJk2.js} +7 -7
  54. package/.output/public/_nuxt/ChPNKPw_.js +1 -0
  55. package/.output/public/_nuxt/{C5wBzGO7.js → CjeMxUv8.js} +1 -1
  56. package/.output/public/_nuxt/CktUrk8z.js +1 -0
  57. package/.output/public/_nuxt/Cst8yEet.js +1 -0
  58. package/.output/public/_nuxt/Cuw2--X2.js +2 -0
  59. package/.output/public/_nuxt/Cyd68Xbv2.js +1 -0
  60. package/.output/public/_nuxt/{pNy4V4kd.js → Cyuxcv5s2.js} +1 -1
  61. package/.output/public/_nuxt/{CIz7SM4H.js → D0vmf1z9.js} +1 -1
  62. package/.output/public/_nuxt/D5-QB_-l.js +1 -0
  63. package/.output/public/_nuxt/D9sgxxsM2.js +1 -0
  64. package/.output/public/_nuxt/DBdwjOGB2.js +1 -0
  65. package/.output/public/_nuxt/DBzdrPzw2.js +1 -0
  66. package/.output/public/_nuxt/DD4J2Otc.js +1 -0
  67. package/.output/public/_nuxt/DMCoWgSb2.js +1 -0
  68. package/.output/public/_nuxt/{CmTqFlYZ.js → DTcsb0fG.js} +1 -1
  69. package/.output/public/_nuxt/Ddc_Pn7D.js +19 -0
  70. package/.output/public/_nuxt/Dg1iMuZ-.js +1 -0
  71. package/.output/public/_nuxt/DhSlJyZD2.js +1 -0
  72. package/.output/public/_nuxt/DmwMkvoQ2.js +1 -0
  73. package/.output/public/_nuxt/EQijmkCh2.js +1 -0
  74. package/.output/public/_nuxt/KXQppTXc.js +1 -0
  75. package/.output/public/_nuxt/{CZ0Gt81h.js → KXvRkBgg.js} +2 -2
  76. package/.output/public/_nuxt/LwITbamf2.js +47 -0
  77. package/.output/public/_nuxt/N9TYd_Mk2.js +1 -0
  78. package/.output/public/_nuxt/VeOVO2sE2.js +1 -0
  79. package/.output/public/_nuxt/_jfzcYrl.js +1 -0
  80. package/.output/public/_nuxt/analysis.D2Pao1rm.css +1 -0
  81. package/.output/public/_nuxt/builds/latest.json +1 -1
  82. package/.output/public/_nuxt/builds/meta/f78a1992-e424-494d-ac4b-aa18971ffc10.json +1 -0
  83. package/.output/public/_nuxt/{default.8ac6QU28.css → default.Bx6RJSbr.css} +1 -1
  84. package/.output/public/_nuxt/{entry.BHNNQA9H.css → entry.BlbU43qz.css} +1 -1
  85. package/.output/public/_nuxt/{MEwEMEMl2.js → iCvdSYYN2.js} +6 -6
  86. package/.output/public/_nuxt/{CYGkUj5M2.js → p2sDc0tO2.js} +1 -1
  87. package/.output/public/_nuxt/{Drhta6gr.js → zVupTo2z2.js} +2 -2
  88. package/.output/server/chunks/_/LeftOutlined.mjs +1 -1
  89. package/.output/server/chunks/_/character-asset.repo.mjs +1 -1
  90. package/.output/server/chunks/_/host-bindings.mjs +1 -1
  91. package/.output/server/chunks/_/nitro.mjs +1629 -1246
  92. package/.output/server/chunks/_/nitro.mjs.map +1 -1
  93. package/.output/server/chunks/_/scene-layout.repo.mjs +1 -1
  94. package/.output/server/chunks/build/{AuthGate-DDPYswkA.mjs → AuthGate-CZYkvPrg.mjs} +5 -5
  95. package/.output/server/chunks/build/{AuthGate-DDPYswkA.mjs.map → AuthGate-CZYkvPrg.mjs.map} +1 -1
  96. package/.output/server/chunks/build/Checkbox-4EdGAAl_.mjs +1 -1
  97. package/.output/server/chunks/build/{FormItemContext-4ORSzhWv.mjs → FormItemContext-DcWIIAaK.mjs} +2 -2
  98. package/.output/server/chunks/build/{FormItemContext-4ORSzhWv.mjs.map → FormItemContext-DcWIIAaK.mjs.map} +1 -1
  99. package/.output/server/chunks/build/{OmpTerminalPanel-DZ2wHMS1.mjs → OmpTerminalPanel-CtFJ6Kc8.mjs} +4 -4
  100. package/.output/server/chunks/build/{OmpTerminalPanel-DZ2wHMS1.mjs.map → OmpTerminalPanel-CtFJ6Kc8.mjs.map} +1 -1
  101. package/.output/server/chunks/build/{PluginSlot-CT4YaNrB.mjs → PluginSlot-BT7kYQgK.mjs} +2 -2
  102. package/.output/server/chunks/build/{PluginSlot-CT4YaNrB.mjs.map → PluginSlot-BT7kYQgK.mjs.map} +1 -1
  103. package/.output/server/chunks/build/{TownView-CZbFn6mO.mjs → TownView-kQZFf4zj.mjs} +3 -3
  104. package/.output/server/chunks/build/{TownView-CZbFn6mO.mjs.map → TownView-kQZFf4zj.mjs.map} +1 -1
  105. package/.output/server/chunks/build/{_id_-Df2pgsAq.mjs → _id_-Bbx1b74O.mjs} +3 -3
  106. package/.output/server/chunks/build/{_id_-Df2pgsAq.mjs.map → _id_-Bbx1b74O.mjs.map} +1 -1
  107. package/.output/server/chunks/build/{_id_-CCVhpJtj.mjs → _id_-IijrRw3f.mjs} +3 -3
  108. package/.output/server/chunks/build/{_id_-CCVhpJtj.mjs.map → _id_-IijrRw3f.mjs.map} +1 -1
  109. package/.output/server/chunks/build/{_wsId_-CJqF-hmP.mjs → _wsId_-DOEw9jgZ.mjs} +22 -21
  110. package/.output/server/chunks/build/{_wsId_-CJqF-hmP.mjs.map → _wsId_-DOEw9jgZ.mjs.map} +1 -1
  111. package/.output/server/chunks/build/{agents-BTsbna5H.mjs → agents-C36wR56A.mjs} +18 -17
  112. package/.output/server/chunks/build/agents-C36wR56A.mjs.map +1 -0
  113. package/.output/server/chunks/build/{aml-BBKfWto1.mjs → aml-CBGndvHT.mjs} +7 -7
  114. package/.output/server/chunks/build/{aml-BBKfWto1.mjs.map → aml-CBGndvHT.mjs.map} +1 -1
  115. package/.output/server/chunks/build/analysis-tgzvOWmD.mjs +332 -0
  116. package/.output/server/chunks/build/analysis-tgzvOWmD.mjs.map +1 -0
  117. package/.output/server/chunks/build/{card-DJOYGuVH.mjs → card-Db7OB49d.mjs} +4 -4
  118. package/.output/server/chunks/build/{card-DJOYGuVH.mjs.map → card-Db7OB49d.mjs.map} +1 -1
  119. package/.output/server/chunks/build/{channel-templates-BPKJ8e4l.mjs → channel-templates-BixUrDmU.mjs} +11 -10
  120. package/.output/server/chunks/build/channel-templates-BixUrDmU.mjs.map +1 -0
  121. package/.output/server/chunks/build/{checkbox-C4AKj81e.mjs → checkbox-CyF96D30.mjs} +3 -3
  122. package/.output/server/chunks/build/{checkbox-C4AKj81e.mjs.map → checkbox-CyF96D30.mjs.map} +1 -1
  123. package/.output/server/chunks/build/{daq-Cz7TaUAM.mjs → daq-DLMLufDq.mjs} +5 -5
  124. package/.output/server/chunks/build/{daq-Cz7TaUAM.mjs.map → daq-DLMLufDq.mjs.map} +1 -1
  125. package/.output/server/chunks/build/dcw-EhjJpVQM.mjs +2 -2
  126. package/.output/server/chunks/build/{default-DweMY872.mjs → default-C7Qmdyz_.mjs} +30 -19
  127. package/.output/server/chunks/build/{default-DweMY872.mjs.map → default-C7Qmdyz_.mjs.map} +1 -1
  128. package/.output/server/chunks/build/{descriptions-CFaUq4y4.mjs → descriptions-1bH81YsZ.mjs} +2 -2
  129. package/.output/server/chunks/build/{descriptions-CFaUq4y4.mjs.map → descriptions-1bH81YsZ.mjs.map} +1 -1
  130. package/.output/server/chunks/build/{drawer-Cfh9_zft.mjs → drawer-C7shdEHy.mjs} +2 -2
  131. package/.output/server/chunks/build/{drawer-Cfh9_zft.mjs.map → drawer-C7shdEHy.mjs.map} +1 -1
  132. package/.output/server/chunks/build/{dropdown-CIsqbX4P.mjs → dropdown-BhLSIp5A.mjs} +2 -2
  133. package/.output/server/chunks/build/{dropdown-CIsqbX4P.mjs.map → dropdown-BhLSIp5A.mjs.map} +1 -1
  134. package/.output/server/chunks/build/{dropdown-CV9GW3z9.mjs → dropdown-BiwcuXDi.mjs} +6 -5
  135. package/.output/server/chunks/build/{dropdown-CV9GW3z9.mjs.map → dropdown-BiwcuXDi.mjs.map} +1 -1
  136. package/.output/server/chunks/build/{form-cs_RcfGx.mjs → form-nE8C0G8B.mjs} +7 -6
  137. package/.output/server/chunks/build/{form-cs_RcfGx.mjs.map → form-nE8C0G8B.mjs.map} +1 -1
  138. package/.output/server/chunks/build/{input-CobQ5LJ5.mjs → input-DwF72eVI.mjs} +93 -3449
  139. package/.output/server/chunks/build/input-DwF72eVI.mjs.map +1 -0
  140. package/.output/server/chunks/build/{input-number-BpPYAWMk.mjs → input-number-TSq6ltkz.mjs} +6 -5
  141. package/.output/server/chunks/build/{input-number-BpPYAWMk.mjs.map → input-number-TSq6ltkz.mjs.map} +1 -1
  142. package/.output/server/chunks/build/{logs-As9fZqU-.mjs → logs-hOEVuxqm.mjs} +3 -3
  143. package/.output/server/chunks/build/{logs-As9fZqU-.mjs.map → logs-hOEVuxqm.mjs.map} +1 -1
  144. package/.output/server/chunks/build/{menu-CVmvHyFT.mjs → menu-Cy5Nrecn.mjs} +4 -3
  145. package/.output/server/chunks/build/{menu-CVmvHyFT.mjs.map → menu-Cy5Nrecn.mjs.map} +1 -1
  146. package/.output/server/chunks/build/{monitor-CdFQ2z4g.mjs → monitor-CfVoiavp.mjs} +20 -19
  147. package/.output/server/chunks/build/{monitor-CdFQ2z4g.mjs.map → monitor-CfVoiavp.mjs.map} +1 -1
  148. package/.output/server/chunks/build/{operations-B2gHCWgZ.mjs → operations-fxI8lEBJ.mjs} +3 -3
  149. package/.output/server/chunks/build/{operations-B2gHCWgZ.mjs.map → operations-fxI8lEBJ.mjs.map} +1 -1
  150. package/.output/server/chunks/build/{pages-BItCt1ar.mjs → pages-6JD9VSbx.mjs} +5 -5
  151. package/.output/server/chunks/build/{pages-BItCt1ar.mjs.map → pages-6JD9VSbx.mjs.map} +1 -1
  152. package/.output/server/chunks/build/{permissions-D6mQw_9j.mjs → permissions-XPtQJSaO.mjs} +14 -13
  153. package/.output/server/chunks/build/permissions-XPtQJSaO.mjs.map +1 -0
  154. package/.output/server/chunks/build/{plugins-NAS9MQ5r.mjs → plugins-DjBSG9pV.mjs} +5 -5
  155. package/.output/server/chunks/build/{plugins-NAS9MQ5r.mjs.map → plugins-DjBSG9pV.mjs.map} +1 -1
  156. package/.output/server/chunks/build/{popconfirm-DFfoFhmt.mjs → popconfirm-DKeEbaGd.mjs} +3 -3
  157. package/.output/server/chunks/build/{popconfirm-DFfoFhmt.mjs.map → popconfirm-DKeEbaGd.mjs.map} +1 -1
  158. package/.output/server/chunks/build/{schedules-BjWNDWL5.mjs → schedules-PcDLCUWN.mjs} +20 -19
  159. package/.output/server/chunks/build/{schedules-BjWNDWL5.mjs.map → schedules-PcDLCUWN.mjs.map} +1 -1
  160. package/.output/server/chunks/build/{segmented-D7FkCgg7.mjs → segmented-BdWCdZUM.mjs} +3 -3
  161. package/.output/server/chunks/build/{segmented-D7FkCgg7.mjs.map → segmented-BdWCdZUM.mjs.map} +1 -1
  162. package/.output/server/chunks/build/{select-FqBNxgxT.mjs → select-C5yighj8.mjs} +5 -4
  163. package/.output/server/chunks/build/{select-FqBNxgxT.mjs.map → select-C5yighj8.mjs.map} +1 -1
  164. package/.output/server/chunks/build/{settings-Cl_KRyEn.mjs → settings-90zT_h9w.mjs} +14 -13
  165. package/.output/server/chunks/build/settings-90zT_h9w.mjs.map +1 -0
  166. package/.output/server/chunks/build/{space-B2uhHJG8.mjs → space-BCffbXIG.mjs} +3 -3
  167. package/.output/server/chunks/build/{space-B2uhHJG8.mjs.map → space-BCffbXIG.mjs.map} +1 -1
  168. package/.output/server/chunks/build/{switch-DZAUIbIN.mjs → switch-OG0SM_Px.mjs} +3 -3
  169. package/.output/server/chunks/build/{switch-DZAUIbIN.mjs.map → switch-OG0SM_Px.mjs.map} +1 -1
  170. package/.output/server/chunks/build/{table-CeOYERqr.mjs → table-UpVzu50c.mjs} +11 -10
  171. package/.output/server/chunks/build/{table-CeOYERqr.mjs.map → table-UpVzu50c.mjs.map} +1 -1
  172. package/.output/server/chunks/build/{tabs-LLNSdLl2.mjs → tabs-CWwoL33v.mjs} +6 -5
  173. package/.output/server/chunks/build/{tabs-LLNSdLl2.mjs.map → tabs-CWwoL33v.mjs.map} +1 -1
  174. package/.output/server/chunks/build/{tag-Dwvkh0Dj.mjs → tag-CS7mwrfG.mjs} +5 -4
  175. package/.output/server/chunks/build/{tag-Dwvkh0Dj.mjs.map → tag-CS7mwrfG.mjs.map} +1 -1
  176. package/.output/server/chunks/build/{teams-CGDZHaQl.mjs → teams-BIAFvRw1.mjs} +19 -18
  177. package/.output/server/chunks/build/teams-BIAFvRw1.mjs.map +1 -0
  178. package/.output/server/chunks/build/{tokens-BOYkZuoB.mjs → tokens-CLpdrzQ7.mjs} +19 -18
  179. package/.output/server/chunks/build/tokens-CLpdrzQ7.mjs.map +1 -0
  180. package/.output/server/chunks/build/tooltip-CJlH_8ZK.mjs +3362 -0
  181. package/.output/server/chunks/build/tooltip-CJlH_8ZK.mjs.map +1 -0
  182. package/.output/server/chunks/build/town-BV-hbwb5.mjs +1 -1
  183. package/.output/server/chunks/build/{town-P1rYoi0v.mjs → town-Bfme7P2I.mjs} +5 -5
  184. package/.output/server/chunks/build/{town-P1rYoi0v.mjs.map → town-Bfme7P2I.mjs.map} +1 -1
  185. package/.output/server/chunks/build/types-D6J7slEa.mjs +1 -1
  186. package/.output/server/chunks/build/types-DWqIeMRP.mjs +75 -0
  187. package/.output/server/chunks/build/types-DWqIeMRP.mjs.map +1 -0
  188. package/.output/server/chunks/build/{useAgentTemplateActions-DsBRUQni.mjs → useAgentTemplateActions-6VyAHgu5.mjs} +1 -1
  189. package/.output/server/chunks/build/{useAgentTemplateActions-DsBRUQni.mjs.map → useAgentTemplateActions-6VyAHgu5.mjs.map} +1 -1
  190. package/.output/server/chunks/build/{useAgentTemplateForm-DzQ_t2Ue.mjs → useAgentTemplateForm-DWa-ezNq.mjs} +1 -1
  191. package/.output/server/chunks/build/{useAgentTemplateForm-DzQ_t2Ue.mjs.map → useAgentTemplateForm-DWa-ezNq.mjs.map} +1 -1
  192. package/.output/server/chunks/build/{useAmlEntities-BMLHU_39.mjs → useAmlEntities-Co2fgjzh.mjs} +1 -1
  193. package/.output/server/chunks/build/{useAmlEntities-BMLHU_39.mjs.map → useAmlEntities-Co2fgjzh.mjs.map} +1 -1
  194. package/.output/server/chunks/build/{useAmlEnv-DdlyVzPu.mjs → useAmlEnv-JTiWPrzH.mjs} +1 -1
  195. package/.output/server/chunks/build/{useAmlEnv-DdlyVzPu.mjs.map → useAmlEnv-JTiWPrzH.mjs.map} +1 -1
  196. package/.output/server/chunks/build/{useAmlJobs-BG_v21hJ.mjs → useAmlJobs-By4pjOzc.mjs} +1 -1
  197. package/.output/server/chunks/build/{useAmlJobs-BG_v21hJ.mjs.map → useAmlJobs-By4pjOzc.mjs.map} +1 -1
  198. package/.output/server/chunks/build/{useAmlModels-D7MuOWOy.mjs → useAmlModels-B1_5vjMA.mjs} +1 -1
  199. package/.output/server/chunks/build/{useAmlModels-D7MuOWOy.mjs.map → useAmlModels-B1_5vjMA.mjs.map} +1 -1
  200. package/.output/server/chunks/build/{useAmlNotes-CTZe-GI0.mjs → useAmlNotes-5uwvCb3h.mjs} +1 -1
  201. package/.output/server/chunks/build/{useAmlNotes-CTZe-GI0.mjs.map → useAmlNotes-5uwvCb3h.mjs.map} +1 -1
  202. package/.output/server/chunks/build/{useAmlPredict-BToRrVRV.mjs → useAmlPredict-lxUv7lAO.mjs} +1 -1
  203. package/.output/server/chunks/build/{useAmlPredict-BToRrVRV.mjs.map → useAmlPredict-lxUv7lAO.mjs.map} +1 -1
  204. package/.output/server/chunks/build/useAnalysisFeed-B4OwUd7p.mjs +128 -0
  205. package/.output/server/chunks/build/useAnalysisFeed-B4OwUd7p.mjs.map +1 -0
  206. package/.output/server/chunks/build/useDaqAddNode-CaOCbe4-.mjs +1 -1
  207. package/.output/server/chunks/build/{useDaqDetailNode-DXgwAu5u.mjs → useDaqDetailNode-DtZ0oDAn.mjs} +3 -3
  208. package/.output/server/chunks/build/{useDaqDetailNode-DXgwAu5u.mjs.map → useDaqDetailNode-DtZ0oDAn.mjs.map} +1 -1
  209. package/.output/server/chunks/build/useDaqDetailParams-CrTMDs-2.mjs +1 -1
  210. package/.output/server/chunks/build/{useDaqFilters-Jx6EERfr.mjs → useDaqFilters-DYHGhECw.mjs} +3 -3
  211. package/.output/server/chunks/build/{useDaqFilters-Jx6EERfr.mjs.map → useDaqFilters-DYHGhECw.mjs.map} +1 -1
  212. package/.output/server/chunks/build/useDaqStream-DhzdoyIR.mjs +1 -1
  213. package/.output/server/chunks/build/useDaqTemplates-C7GzQmdJ.mjs +1 -1
  214. package/.output/server/chunks/build/{useDashboardData-Ce-EU5DJ.mjs → useDashboardData-B3lZjE7x.mjs} +3 -3
  215. package/.output/server/chunks/build/{useDashboardData-Ce-EU5DJ.mjs.map → useDashboardData-B3lZjE7x.mjs.map} +1 -1
  216. package/.output/server/chunks/build/useDcwAddNode-4mTPQ6T8.mjs +1 -1
  217. package/.output/server/chunks/build/{useDcwDetailScope-4j3B03Pi.mjs → useDcwDetailScope-BWH7jnVh.mjs} +2 -2
  218. package/.output/server/chunks/build/{useDcwDetailScope-4j3B03Pi.mjs.map → useDcwDetailScope-BWH7jnVh.mjs.map} +1 -1
  219. package/.output/server/chunks/build/useDcwStream-BXJ2V8HM.mjs +1 -1
  220. package/.output/server/chunks/build/{useLogsManual-CMjD62nt.mjs → useLogsManual-BLfiSU3u.mjs} +1 -1
  221. package/.output/server/chunks/build/{useLogsManual-CMjD62nt.mjs.map → useLogsManual-BLfiSU3u.mjs.map} +1 -1
  222. package/.output/server/chunks/build/{useMonitorData-D2gFSonG.mjs → useMonitorData-BZ6Z-Sy8.mjs} +1 -1
  223. package/.output/server/chunks/build/{useMonitorData-D2gFSonG.mjs.map → useMonitorData-BZ6Z-Sy8.mjs.map} +1 -1
  224. package/.output/server/chunks/build/{useTeamActions-BOLQkYxg.mjs → useTeamActions-ahht5J8Y.mjs} +1 -1
  225. package/.output/server/chunks/build/{useTeamActions-BOLQkYxg.mjs.map → useTeamActions-ahht5J8Y.mjs.map} +1 -1
  226. package/.output/server/chunks/build/{useTeamAddMemberDialog-BCgrLPxI.mjs → useTeamAddMemberDialog-DvXxsVy0.mjs} +1 -1
  227. package/.output/server/chunks/build/{useTeamAddMemberDialog-BCgrLPxI.mjs.map → useTeamAddMemberDialog-DvXxsVy0.mjs.map} +1 -1
  228. package/.output/server/chunks/build/{useTeamCreateDialog-CJk40LqS.mjs → useTeamCreateDialog-A_k-XX5B.mjs} +1 -1
  229. package/.output/server/chunks/build/{useTeamCreateDialog-CJk40LqS.mjs.map → useTeamCreateDialog-A_k-XX5B.mjs.map} +1 -1
  230. package/.output/server/chunks/build/{useTeamDeployDialog-49hdUXQP.mjs → useTeamDeployDialog-CfAFjIr_.mjs} +1 -1
  231. package/.output/server/chunks/build/{useTeamDeployDialog-49hdUXQP.mjs.map → useTeamDeployDialog-CfAFjIr_.mjs.map} +1 -1
  232. package/.output/server/chunks/build/{useTeamPluginDialog-Dh-QOoiU.mjs → useTeamPluginDialog-Djmkk1Nl.mjs} +1 -1
  233. package/.output/server/chunks/build/{useTeamPluginDialog-Dh-QOoiU.mjs.map → useTeamPluginDialog-Djmkk1Nl.mjs.map} +1 -1
  234. package/.output/server/chunks/build/{useTokenCreate-DkYvEQUD.mjs → useTokenCreate-CkWoxSI-.mjs} +1 -1
  235. package/.output/server/chunks/build/{useTokenCreate-DkYvEQUD.mjs.map → useTokenCreate-CkWoxSI-.mjs.map} +1 -1
  236. package/.output/server/chunks/build/{useTokenRename-DOCP4aeI.mjs → useTokenRename-BohjnGT0.mjs} +1 -1
  237. package/.output/server/chunks/build/{useTokenRename-DOCP4aeI.mjs.map → useTokenRename-BohjnGT0.mjs.map} +1 -1
  238. package/.output/server/chunks/build/{useTokenReveal-CybwwflV.mjs → useTokenReveal-BBN5iGz7.mjs} +1 -1
  239. package/.output/server/chunks/build/{useTokenReveal-CybwwflV.mjs.map → useTokenReveal-BBN5iGz7.mjs.map} +1 -1
  240. package/.output/server/chunks/build/{useTokensList-BLiMvrc4.mjs → useTokensList-BQX9WqfT.mjs} +1 -1
  241. package/.output/server/chunks/build/{useTokensList-BLiMvrc4.mjs.map → useTokensList-BQX9WqfT.mjs.map} +1 -1
  242. package/.output/server/chunks/build/{useWorkbenchAuth-DAabQl7X.mjs → useWorkbenchAuth-BTRlS2wZ.mjs} +1 -1
  243. package/.output/server/chunks/build/{useWorkbenchAuth-DAabQl7X.mjs.map → useWorkbenchAuth-BTRlS2wZ.mjs.map} +1 -1
  244. package/.output/server/chunks/build/{useWorkbenchWorkspaces-6-mpCGCR.mjs → useWorkbenchWorkspaces-C6ky7OJH.mjs} +1 -1
  245. package/.output/server/chunks/build/{useWorkbenchWorkspaces-6-mpCGCR.mjs.map → useWorkbenchWorkspaces-C6ky7OJH.mjs.map} +1 -1
  246. package/.output/server/chunks/build/{users-B_pHStEa.mjs → users-BHOEW3Az.mjs} +15 -14
  247. package/.output/server/chunks/build/users-BHOEW3Az.mjs.map +1 -0
  248. package/.output/server/chunks/build/{workshop-C0DefygA.mjs → workshop-DyJ1LXwu.mjs} +11 -10
  249. package/.output/server/chunks/build/workshop-DyJ1LXwu.mjs.map +1 -0
  250. package/.output/server/chunks/routes/api/mcp/workshop.mjs +1 -1
  251. package/.output/server/chunks/routes/api/system/backup/run.post.mjs +2 -2
  252. package/.output/server/chunks/routes/api/workshop/analysis/_id_.delete.mjs +46 -0
  253. package/.output/server/chunks/routes/api/workshop/analysis/_id_.delete.mjs.map +1 -0
  254. package/.output/server/chunks/routes/api/workshop/analysis/_id_.get.mjs +39 -0
  255. package/.output/server/chunks/routes/api/workshop/analysis/_id_.get.mjs.map +1 -0
  256. package/.output/server/chunks/routes/api/workshop/assets/index.post.mjs +1 -1
  257. package/.output/server/chunks/routes/api/workshop/assets/index2.post.mjs +1 -1
  258. package/.output/server/chunks/routes/api/workshop/channel-templates/_id/instantiate.post.mjs +2 -2
  259. package/.output/server/chunks/routes/api/workshop/channels/_id/activate.post.mjs +1 -1
  260. package/.output/server/chunks/routes/api/workshop/channels/_id/chat/index.post.mjs +1 -1
  261. package/.output/server/chunks/routes/api/workshop/channels/_id/index.post.mjs +1 -1
  262. package/.output/server/chunks/routes/api/workshop/channels/_id/index.put.mjs +1 -1
  263. package/.output/server/chunks/routes/api/workshop/channels/_id/index3.post.mjs +1 -1
  264. package/.output/server/chunks/routes/api/workshop/channels/_id/index4.post.mjs +1 -1
  265. package/.output/server/chunks/routes/api/workshop/channels/_id/index5.get.mjs +1 -1
  266. package/.output/server/chunks/routes/api/workshop/channels/_id/line.put.mjs +1 -1
  267. package/.output/server/chunks/routes/api/workshop/channels/_id/terminals.get.mjs +1 -1
  268. package/.output/server/chunks/routes/api/workshop/channels/_id/twin-profile.get.mjs +1 -1
  269. package/.output/server/chunks/routes/api/workshop/channels/_id/twin-profile.patch.mjs +1 -1
  270. package/.output/server/chunks/routes/api/workshop/channels/index.get.mjs +1 -1
  271. package/.output/server/chunks/routes/api/workshop/channels.post.mjs +7 -7
  272. package/.output/server/chunks/routes/api/workshop/daq/_id/samples.get.mjs +1 -1
  273. package/.output/server/chunks/routes/api/workshop/daq/index.post.mjs +1 -1
  274. package/.output/server/chunks/routes/api/workshop/daq/infra/reconnect.post.mjs +1 -1
  275. package/.output/server/chunks/routes/api/workshop/daq/infra.get.mjs +1 -1
  276. package/.output/server/chunks/routes/api/workshop/daq/templates/_key_.delete.mjs +1 -1
  277. package/.output/server/chunks/routes/api/workshop/daq/templates/_key_.patch.mjs +1 -1
  278. package/.output/server/chunks/routes/api/workshop/daq/test-driver.post.mjs +1 -1
  279. package/.output/server/chunks/routes/api/workshop/dcw/_id/bind.post.mjs +1 -1
  280. package/.output/server/chunks/routes/api/workshop/dcw/_id/bindings.put.mjs +1 -1
  281. package/.output/server/chunks/routes/api/workshop/dcw/_id/param-ledger.get.mjs +1 -1
  282. package/.output/server/chunks/routes/api/workshop/dcw/_id/read.post.mjs +1 -1
  283. package/.output/server/chunks/routes/api/workshop/dcw/_id/test.post.mjs +1 -1
  284. package/.output/server/chunks/routes/api/workshop/dcw/_id/write.post.mjs +1 -1
  285. package/.output/server/chunks/routes/api/workshop/dcw/_id_.delete.mjs +1 -1
  286. package/.output/server/chunks/routes/api/workshop/dcw/_id_.patch.mjs +1 -1
  287. package/.output/server/chunks/routes/api/workshop/dcw/controller.post.mjs +1 -1
  288. package/.output/server/chunks/routes/api/workshop/dcw/index.get.mjs +1 -1
  289. package/.output/server/chunks/routes/api/workshop/dcw/index.post.mjs +1 -1
  290. package/.output/server/chunks/routes/api/workshop/dcw/index2.get.mjs +1 -1
  291. package/.output/server/chunks/routes/api/workshop/dcw/index2.post.mjs +1 -1
  292. package/.output/server/chunks/routes/api/workshop/dcw/index3.get.mjs +1 -1
  293. package/.output/server/chunks/routes/api/workshop/dcw/index3.post.mjs +1 -1
  294. package/.output/server/chunks/routes/api/workshop/dcw/index4.get.mjs +1 -1
  295. package/.output/server/chunks/routes/api/workshop/dcw/index4.post.mjs +1 -1
  296. package/.output/server/chunks/routes/api/workshop/dcw/index5.get.mjs +1 -1
  297. package/.output/server/chunks/routes/api/workshop/dcw/index5.post.mjs +1 -1
  298. package/.output/server/chunks/routes/api/workshop/dcw/index6.get.mjs +1 -1
  299. package/.output/server/chunks/routes/api/workshop/dcw/index7.get.mjs +1 -1
  300. package/.output/server/chunks/routes/api/workshop/dcw/journal/node/_nodeId/rollback.post.mjs +1 -1
  301. package/.output/server/chunks/routes/api/workshop/dcw/line/query.get.mjs +1 -1
  302. package/.output/server/chunks/routes/api/workshop/dcw/lines/_id/start.post.mjs +1 -1
  303. package/.output/server/chunks/routes/api/workshop/dcw/lines/_id/stop.post.mjs +1 -1
  304. package/.output/server/chunks/routes/api/workshop/dcw/lines/_id_.delete.mjs +1 -1
  305. package/.output/server/chunks/routes/api/workshop/dcw/mes-artifacts/file.get.mjs +1 -1
  306. package/.output/server/chunks/routes/api/workshop/dcw/mes-hook-test.post.mjs +1 -1
  307. package/.output/server/chunks/routes/api/workshop/dcw/mes-test-read.post.mjs +1 -1
  308. package/.output/server/chunks/routes/api/workshop/dcw/optimizations/_id/judge.post.mjs +1 -1
  309. package/.output/server/chunks/routes/api/workshop/dcw/optimizations/_id/rollback.post.mjs +1 -1
  310. package/.output/server/chunks/routes/api/workshop/dcw/optimizations/_id/series.get.mjs +1 -1
  311. package/.output/server/chunks/routes/api/workshop/dcw/optimizations/_id_.get.mjs +1 -1
  312. package/.output/server/chunks/routes/api/workshop/dcw/params/_id/read.post.mjs +1 -1
  313. package/.output/server/chunks/routes/api/workshop/dcw/params/_id/write.post.mjs +1 -1
  314. package/.output/server/chunks/routes/api/workshop/dcw/params/_id_.delete.mjs +1 -1
  315. package/.output/server/chunks/routes/api/workshop/dcw/params/_id_.patch.mjs +1 -1
  316. package/.output/server/chunks/routes/api/workshop/dcw/products/_id_.delete.mjs +1 -1
  317. package/.output/server/chunks/routes/api/workshop/dcw/products/_id_.patch.mjs +1 -1
  318. package/.output/server/chunks/routes/api/workshop/dcw/recipes/_id/apply.post.mjs +1 -1
  319. package/.output/server/chunks/routes/api/workshop/dcw/recipes/_id/mark-good.post.mjs +1 -1
  320. package/.output/server/chunks/routes/api/workshop/dcw/recipes/_id/rollback-good.post.mjs +1 -1
  321. package/.output/server/chunks/routes/api/workshop/dcw/recipes/_id_.delete.mjs +1 -1
  322. package/.output/server/chunks/routes/api/workshop/dcw/runs/_id/close.post.mjs +1 -1
  323. package/.output/server/chunks/routes/api/workshop/dcw/runs/_id/data.get.mjs +1 -1
  324. package/.output/server/chunks/routes/api/workshop/dcw/runs/_id/rollback.post.mjs +1 -1
  325. package/.output/server/chunks/routes/api/workshop/dcw/templates/_key_.delete.mjs +1 -1
  326. package/.output/server/chunks/routes/api/workshop/dcw/templates/_key_.patch.mjs +1 -1
  327. package/.output/server/chunks/routes/api/workshop/dcw/test-driver.post.mjs +1 -1
  328. package/.output/server/chunks/routes/api/workshop/device-twins/_id/control.post.mjs +1 -1
  329. package/.output/server/chunks/routes/api/workshop/device-twins/_id/telemetry.post.mjs +1 -1
  330. package/.output/server/chunks/routes/api/workshop/device-twins/_id_.delete.mjs +1 -1
  331. package/.output/server/chunks/routes/api/workshop/device-twins/_id_.patch.mjs +1 -1
  332. package/.output/server/chunks/routes/api/workshop/exp/confirmations/_id/decide.post.mjs +1 -1
  333. package/.output/server/chunks/routes/api/workshop/exp/index.get.mjs +1 -1
  334. package/.output/server/chunks/routes/api/workshop/fs/dirs.get.mjs +1 -1
  335. package/.output/server/chunks/routes/api/workshop/harnesses/_id/providers.get.mjs +1 -1
  336. package/.output/server/chunks/routes/api/workshop/harnesses.get.mjs +1 -1
  337. package/.output/server/chunks/routes/api/workshop/hitl/pending.get.mjs +1 -1
  338. package/.output/server/chunks/routes/api/workshop/hitl/respond.post.mjs +1 -1
  339. package/.output/server/chunks/routes/api/workshop/index.put.mjs +1 -1
  340. package/.output/server/chunks/routes/api/workshop/index10.get.mjs +20 -23
  341. package/.output/server/chunks/routes/api/workshop/index10.get.mjs.map +1 -1
  342. package/.output/server/chunks/routes/api/workshop/index11.get.mjs +25 -11
  343. package/.output/server/chunks/routes/api/workshop/index11.get.mjs.map +1 -1
  344. package/.output/server/chunks/routes/api/workshop/index12.get.mjs +10 -4
  345. package/.output/server/chunks/routes/api/workshop/index12.get.mjs.map +1 -1
  346. package/.output/server/chunks/routes/api/workshop/index13.get.mjs +2 -3
  347. package/.output/server/chunks/routes/api/workshop/index13.get.mjs.map +1 -1
  348. package/.output/server/chunks/routes/api/workshop/index14.get.mjs +3 -2
  349. package/.output/server/chunks/routes/api/workshop/index14.get.mjs.map +1 -1
  350. package/.output/server/chunks/routes/api/workshop/index15.get.mjs +30 -0
  351. package/.output/server/chunks/routes/api/workshop/index15.get.mjs.map +1 -0
  352. package/.output/server/chunks/routes/api/workshop/index3.get.mjs +20 -9
  353. package/.output/server/chunks/routes/api/workshop/index3.get.mjs.map +1 -1
  354. package/.output/server/chunks/routes/api/workshop/index3.post.mjs +1 -1
  355. package/.output/server/chunks/routes/api/workshop/index4.get.mjs +10 -4
  356. package/.output/server/chunks/routes/api/workshop/index4.get.mjs.map +1 -1
  357. package/.output/server/chunks/routes/api/workshop/index4.post.mjs +1 -1
  358. package/.output/server/chunks/routes/api/workshop/index5.get.mjs +4 -29
  359. package/.output/server/chunks/routes/api/workshop/index5.get.mjs.map +1 -1
  360. package/.output/server/chunks/routes/api/workshop/index5.post.mjs +1 -1
  361. package/.output/server/chunks/routes/api/workshop/index6.get.mjs +25 -22
  362. package/.output/server/chunks/routes/api/workshop/index6.get.mjs.map +1 -1
  363. package/.output/server/chunks/routes/api/workshop/index7.get.mjs +26 -5
  364. package/.output/server/chunks/routes/api/workshop/index7.get.mjs.map +1 -1
  365. package/.output/server/chunks/routes/api/workshop/index8.get.mjs +4 -39
  366. package/.output/server/chunks/routes/api/workshop/index8.get.mjs.map +1 -1
  367. package/.output/server/chunks/routes/api/workshop/index9.get.mjs +40 -20
  368. package/.output/server/chunks/routes/api/workshop/index9.get.mjs.map +1 -1
  369. package/.output/server/chunks/routes/api/workshop/plugins/_name/disable.post.mjs +1 -1
  370. package/.output/server/chunks/routes/api/workshop/plugins/_name/enable.post.mjs +1 -1
  371. package/.output/server/chunks/routes/api/workshop/scene/layouts/_channelId_.delete.mjs +1 -1
  372. package/.output/server/chunks/routes/api/workshop/scene/layouts/_channelId_.put.mjs +1 -1
  373. package/.output/server/chunks/routes/api/workshop/teams/_id/deploy.post.mjs +1 -1
  374. package/.output/server/chunks/routes/api/workshop/teams/_id/index.put.mjs +1 -1
  375. package/.output/server/chunks/routes/api/workshop/teams/_id/index2.get.mjs +1 -1
  376. package/.output/server/chunks/routes/api/workshop/workspaces/_id/channel-templates/_tplId_.post.mjs +2 -2
  377. package/.output/server/chunks/routes/renderer.mjs +2 -2
  378. package/.output/server/chunks/virtual/entry.mjs +551 -824
  379. package/.output/server/chunks/virtual/entry.mjs.map +1 -1
  380. package/.output/server/chunks/virtual/precomputed.mjs +1 -1
  381. package/.output/server/package.json +1 -1
  382. package/README-zh.md +17 -0
  383. package/README.md +20 -0
  384. package/app/components/AppSidebar.vue +1 -0
  385. package/app/components/analysis/AnalysisFilterCard.vue +160 -0
  386. package/app/components/analysis/AnalysisPageHead.vue +47 -0
  387. package/app/components/analysis/AnalysisTable.vue +306 -0
  388. package/app/composables/useRouteMeta.ts +1 -0
  389. package/app/config/schema.ts +1 -0
  390. package/app/pages/analysis/composables/useAnalysisFeed.ts +85 -0
  391. package/app/pages/analysis/index.vue +92 -0
  392. package/app/pages/analysis/types.ts +44 -0
  393. package/cli/commands/mcp.mjs +160 -154
  394. package/config.yml +1 -1
  395. package/i18n/locales/en.ts +55 -0
  396. package/i18n/locales/zh-CN.ts +55 -0
  397. package/mcp/aw-mcp-server.mjs +799 -796
  398. package/package.json +2 -2
  399. package/scripts/onboarding/onboard.mjs +5 -2
  400. package/scripts/onboarding/sim-twin.mjs +312 -0
  401. package/server/api/workshop/analysis/[id].delete.ts +30 -0
  402. package/server/api/workshop/analysis/[id].get.ts +23 -0
  403. package/server/api/workshop/analysis/index.get.ts +33 -0
  404. package/server/plugins/workshop.ts +4 -0
  405. package/server/repositories/user.repository.ts +2 -2
  406. package/server/services/workshop/agents/host-tool-bridge/catalog.ts +4 -1
  407. package/server/services/workshop/agents/host-tool-bridge/tools/industrial.ts +5 -2
  408. package/server/services/workshop/agents/industrial/analysis-tools.ts +242 -0
  409. package/server/services/workshop/agents/industrial/index.ts +1 -0
  410. package/server/services/workshop/agents/industrial/ops-tools.ts +3 -2
  411. package/server/services/workshop/analysis/analysis.repo.ts +189 -0
  412. package/server/services/workshop/db/database/schema.ts +28 -1
  413. package/server/services/workshop/db/ops.repo.ts +1 -1
  414. package/server/services/workshop/db/retention.ts +2 -0
  415. package/server/services/workshop/db/schema.sql +27 -0
  416. package/server/services/workshop/settings.ts +1 -0
  417. package/shared/config/schema.json +1 -0
  418. package/.output/public/_nuxt/B-Y_rsfn.js +0 -106
  419. package/.output/public/_nuxt/B02cxZz72.js +0 -1
  420. package/.output/public/_nuxt/BAqtRt0q.js +0 -1
  421. package/.output/public/_nuxt/BKHd_sKD2.js +0 -47
  422. package/.output/public/_nuxt/BXKCB3rS.js +0 -1
  423. package/.output/public/_nuxt/BhrnGVGz.js +0 -1
  424. package/.output/public/_nuxt/BikIgp9R.js +0 -1
  425. package/.output/public/_nuxt/BkGqyjWm.js +0 -3
  426. package/.output/public/_nuxt/Bn1N3mJv.js +0 -1
  427. package/.output/public/_nuxt/Br2LgfbH2.js +0 -13
  428. package/.output/public/_nuxt/BtNT93vm2.js +0 -1
  429. package/.output/public/_nuxt/BtYg4aGR2.js +0 -1
  430. package/.output/public/_nuxt/C4X_Z1lA.js +0 -1
  431. package/.output/public/_nuxt/CBATzTUf.js +0 -13
  432. package/.output/public/_nuxt/CEP4UrDv.js +0 -1
  433. package/.output/public/_nuxt/CIPKYgrH2.js +0 -1
  434. package/.output/public/_nuxt/CPSHP_EI.js +0 -1
  435. package/.output/public/_nuxt/CSyIwYcJ2.js +0 -1
  436. package/.output/public/_nuxt/CZkTlW93.js +0 -2
  437. package/.output/public/_nuxt/CZyYdpqZ2.js +0 -1
  438. package/.output/public/_nuxt/CeDkXWCz.js +0 -1
  439. package/.output/public/_nuxt/Cl19UD7U.js +0 -1
  440. package/.output/public/_nuxt/ClrkV0C4.js +0 -1
  441. package/.output/public/_nuxt/CoGETbe-2.js +0 -1
  442. package/.output/public/_nuxt/CuRtzvsa2.js +0 -1
  443. package/.output/public/_nuxt/Cv_H1gOM2.js +0 -1
  444. package/.output/public/_nuxt/D5i2ofVw2.js +0 -1
  445. package/.output/public/_nuxt/D6XGn5vM.js +0 -2
  446. package/.output/public/_nuxt/D6c5ppqB.js +0 -1
  447. package/.output/public/_nuxt/D8VQGThE.js +0 -28
  448. package/.output/public/_nuxt/DBwuADr82.js +0 -1
  449. package/.output/public/_nuxt/DTZO6WMs2.js +0 -1
  450. package/.output/public/_nuxt/DfqRQSFn.js +0 -19
  451. package/.output/public/_nuxt/DraEWn4N2.js +0 -1
  452. package/.output/public/_nuxt/DyMgrV29.js +0 -1
  453. package/.output/public/_nuxt/H7Rbu32y2.js +0 -1
  454. package/.output/public/_nuxt/TjGWqrHo.js +0 -1
  455. package/.output/public/_nuxt/VVomhVqu2.js +0 -1
  456. package/.output/public/_nuxt/YDs3mbQu2.js +0 -1
  457. package/.output/public/_nuxt/Z3MSTcdu2.js +0 -1
  458. package/.output/public/_nuxt/_vR_sc7t.js +0 -24
  459. package/.output/public/_nuxt/builds/meta/082ac92a-d8d0-4e78-8d5a-b4a610080231.json +0 -1
  460. package/.output/public/_nuxt/gbaq2UOO.js +0 -1
  461. package/.output/public/_nuxt/o-G6YtmK2.js +0 -1
  462. package/.output/public/_nuxt/ylowSquM2.js +0 -1
  463. package/.output/server/chunks/build/agents-BTsbna5H.mjs.map +0 -1
  464. package/.output/server/chunks/build/channel-templates-BPKJ8e4l.mjs.map +0 -1
  465. package/.output/server/chunks/build/input-CobQ5LJ5.mjs.map +0 -1
  466. package/.output/server/chunks/build/permissions-D6mQw_9j.mjs.map +0 -1
  467. package/.output/server/chunks/build/settings-Cl_KRyEn.mjs.map +0 -1
  468. package/.output/server/chunks/build/teams-CGDZHaQl.mjs.map +0 -1
  469. package/.output/server/chunks/build/tokens-BOYkZuoB.mjs.map +0 -1
  470. package/.output/server/chunks/build/users-B_pHStEa.mjs.map +0 -1
  471. package/.output/server/chunks/build/workshop-C0DefygA.mjs.map +0 -1
  472. package/scripts/_audit/.tmp/audit-data/dcw-params.json +0 -15
  473. package/scripts/_audit/.tmp/audit-data/dcws.json +0 -30
  474. package/scripts/_audit/aml-layout-diag.mjs +0 -83
  475. package/scripts/_audit/channel-inspect.mjs +0 -49
  476. package/scripts/_audit/cleanup-apply.mjs +0 -89
  477. package/scripts/_audit/cleanup-plan.mjs +0 -82
  478. package/scripts/_audit/contrast-check.mjs +0 -43
  479. package/scripts/_audit/dcw-controller-e2e.ts +0 -106
  480. package/scripts/_audit/dcw-flush-cost.ts +0 -43
  481. package/scripts/_audit/dcw-rollback-ledger.ts +0 -156
  482. package/scripts/_audit/dcw-unrecorded-write.ts +0 -171
  483. package/scripts/_audit/dcw-write-mutex.ts +0 -157
  484. package/scripts/_audit/design-shots.mjs +0 -145
  485. package/scripts/_audit/docs-font-probe.mjs +0 -68
  486. package/scripts/_audit/docs-probe.mjs +0 -107
  487. package/scripts/_audit/docs-shots.mjs +0 -171
  488. package/scripts/_audit/docs-v3-verify.mjs +0 -255
  489. package/scripts/_audit/docs-vue-lint.mjs +0 -81
  490. package/scripts/_audit/docs-vue-lint2.mjs +0 -91
  491. package/scripts/_audit/exp-cost-scaling.mjs +0 -57
  492. package/scripts/_audit/exp-envelope-and-png.mjs +0 -78
  493. package/scripts/_audit/exp-png-decode.mjs +0 -67
  494. package/scripts/_audit/exp-retention-plan.mjs +0 -61
  495. package/scripts/_audit/exp-retention-rescan.mjs +0 -42
  496. package/scripts/_audit/exp-sweep-fairness.mjs +0 -50
  497. package/scripts/_audit/feature-audit-e2e.mjs +0 -342
  498. package/scripts/_audit/fix-settings-count.mjs +0 -57
  499. package/scripts/_audit/full-e2e-adopt.mjs +0 -238
  500. package/scripts/_audit/full-e2e-close-loop.mjs +0 -134
  501. package/scripts/_audit/full-e2e-retrain.mjs +0 -320
  502. package/scripts/_audit/full-e2e-supplement.mjs +0 -192
  503. package/scripts/_audit/full-e2e-ui-final.mjs +0 -111
  504. package/scripts/_audit/full-e2e-ui-mount.mjs +0 -111
  505. package/scripts/_audit/full-feature-e2e-20260927.mjs +0 -627
  506. package/scripts/_audit/glass-verify.mjs +0 -155
  507. package/scripts/_audit/hydration-diff.mjs +0 -104
  508. package/scripts/_audit/hydration-head.mjs +0 -36
  509. package/scripts/_audit/hydration-probe.mjs +0 -59
  510. package/scripts/_audit/idd-scenarios-e2e.mjs +0 -239
  511. package/scripts/_audit/kb-diag-complete.mjs +0 -261
  512. package/scripts/_audit/kb-diag-complete2.mjs +0 -271
  513. package/scripts/_audit/kb-diag-loop-e2e.mjs +0 -357
  514. package/scripts/_audit/kb-diag-loop-mock.mjs +0 -416
  515. package/scripts/_audit/kb-diag-loop-v2.mjs +0 -314
  516. package/scripts/_audit/lead-matrix-test.mjs +0 -172
  517. package/scripts/_audit/plc-agent-task.mjs +0 -74
  518. package/scripts/_audit/plc-clean-scenario.mjs +0 -434
  519. package/scripts/_audit/plc-clean-shots.mjs +0 -161
  520. package/scripts/_audit/plc-fc10-probe.mjs +0 -30
  521. package/scripts/_audit/probe-binding.mjs +0 -114
  522. package/scripts/_audit/recipe-save-e2e.mjs +0 -365
  523. package/scripts/_audit/review-fix-verify.mjs +0 -158
  524. package/scripts/_audit/runtime-dir-e2e.mjs +0 -393
  525. package/scripts/_audit/town-focus-shot.mjs +0 -129
  526. package/scripts/_audit/town-reposition.mjs +0 -85
  527. package/scripts/_audit/verify-cleanup.mjs +0 -67
  528. package/scripts/_audit/verify-data-integrity.mjs +0 -112
  529. package/scripts/_audit/watchdog-recovery-test.mjs +0 -149
  530. package/scripts/_dbg-optloop-ui-shots.mjs +0 -52
  531. /package/.output/public/_nuxt/{4RTUlYvj2.js → 4RTUlYvj.js} +0 -0
  532. /package/.output/public/_nuxt/{BBhLVYdM.js → BBhLVYdM2.js} +0 -0
  533. /package/.output/public/_nuxt/{BG7XSX-S2.js → BG7XSX-S.js} +0 -0
  534. /package/.output/public/_nuxt/{BU7WuuKh.js → BU7WuuKh2.js} +0 -0
  535. /package/.output/public/_nuxt/{BrRX-l9B2.js → BrRX-l9B.js} +0 -0
  536. /package/.output/public/_nuxt/{CHyzK5m52.js → CHyzK5m5.js} +0 -0
  537. /package/.output/public/_nuxt/{Ckafrjnw2.js → Ckafrjnw.js} +0 -0
  538. /package/.output/public/_nuxt/{D1Xw30Dj2.js → D1Xw30Dj.js} +0 -0
  539. /package/.output/public/_nuxt/{DEhjFhZ2.js → DEhjFhZ22.js} +0 -0
  540. /package/.output/public/_nuxt/{DdNujZN5.js → DdNujZN52.js} +0 -0
  541. /package/.output/public/_nuxt/{DzwIZ81f.js → DzwIZ81f2.js} +0 -0
  542. /package/.output/public/_nuxt/{M6NcguDO.js → M6NcguDO2.js} +0 -0
  543. /package/.output/public/_nuxt/{MW-V7IIP2.js → MW-V7IIP.js} +0 -0
  544. /package/.output/public/_nuxt/{WmMwIS4y.js → WmMwIS4y2.js} +0 -0
  545. /package/.output/public/_nuxt/{qIQFsHtF.js → qIQFsHtF2.js} +0 -0
@@ -1,393 +0,0 @@
1
- #!/usr/bin/env node
2
- /**
3
- * scripts/_audit/runtime-dir-e2e.mjs —— 运行时目录规约验收(A1-A6)。
4
- *
5
- * 验收规范:
6
- * A1 目录优先级:cwd ./.AgentWorkShop(最高)> ~/.AgentWorkShop 兜底;AW_HOME/AW_AML_DIR 可显式覆盖
7
- * A2 全产物落位配置根:data/、aml/{datasets,jobs,models,.venv,tools,runtime} 全在 <配置根>;检出根零新增
8
- * A3 AML 训练产物入运行时目录:datasets/<id>/jobs/<id>/models/<id> 全在 <配置根>/aml,模型可读
9
- * A4 uv 优先+启动预热:有 uv → 启动后自动后台创建 <配置根>/aml/.venv 并 ready(无 uv 回退 python -m venv)
10
- * A5 清数据冷启动:删 data/aml 后重启全部自动重建;家目录兜底模式成立
11
- * A6 更新链路:aw update --check 可用;配置根在包外 → 更新不触碰数据/模型/venv
12
- *
13
- * 流程:捕获真实 physics_spec → 预清(改名保留 *.pre-clean-20260927)→ repo 模式冷启 3467 →
14
- * A2/A4 断言 → 注册 admin → 等 venv ready → 建线跑 4 批(4017 模拟器)→ A3 数据集+训练 →
15
- * 家目录兜底实例 3468(临时 cwd)→ aw update --check → 清场。
16
- */
17
- import { spawn, spawnSync } from 'node:child_process'
18
- import { closeSync, existsSync, mkdtempSync, openSync, readdirSync, readFileSync, renameSync, rmSync, statSync, writeFileSync } from 'node:fs'
19
- import { tmpdir, homedir } from 'node:os'
20
- import { dirname, join, resolve } from 'node:path'
21
- import { fileURLToPath } from 'node:url'
22
-
23
- const REPO = resolve(dirname(fileURLToPath(import.meta.url)), '..', '..')
24
- const AW_PORT = 3467
25
- const HOME_PORT = 3468
26
- const SIM_PORT = 4017
27
- const SIM_DIR = resolve(REPO, '..', 'plc-node-simulator-bench-4017')
28
- const CONFIG_ROOT = join(REPO, '.AgentWorkShop')
29
- const TODAY = '20260927'
30
- let BASE = `http://127.0.0.1:${AW_PORT}`
31
- const SIM = `http://127.0.0.1:${SIM_PORT}`
32
-
33
- let pass = 0
34
- const fails = []
35
- const ok = (name, cond, detail = '') => {
36
- if (cond) { pass++; console.log(` ✔ ${name}`) }
37
- else { fails.push(name); console.log(` ✖ ${name}${detail ? ` — ${String(detail).slice(0, 240)}` : ''}`) }
38
- }
39
- const sleep = ms => new Promise(r => setTimeout(r, ms))
40
- const getJson = async (url, token) => {
41
- try {
42
- const r = await fetch(url, { signal: AbortSignal.timeout(15000), headers: token ? { authorization: `Bearer ${token}` } : {} })
43
- return await r.json()
44
- }
45
- catch { return null }
46
- }
47
- const killPort = (port) => {
48
- try {
49
- const psi = spawnSync('powershell', ['-NoProfile', '-Command',
50
- `Get-NetTCPConnection -LocalPort ${port} -State Listen -ErrorAction SilentlyContinue | Select-Object -First 1 -ExpandProperty OwningProcess`], { encoding: 'utf8' })
51
- const pid = Number(psi.stdout.trim())
52
- if (Number.isInteger(pid) && pid > 0) spawnSync('taskkill', ['/PID', String(pid), '/T', '/F'], { stdio: 'ignore' })
53
- }
54
- catch { /* 尽力而为 */ }
55
- }
56
-
57
- /** 捕获既有真实 physics_spec(训练器 fail-closed 要求真实骨架;S0 重命名前取样,训练时空 nodeIds 重映射)。
58
- * 候选:aml/jobs 与各 aml.pre-clean-NNN/jobs;优先含 artifacts 目录(已完成)的最新作业。 */
59
- function captureRealSpec() {
60
- const candidates = [join(REPO, 'aml', 'jobs'), ...readdirSync(REPO).filter(d => d.startsWith('aml.pre-clean-')).map(d => join(REPO, d, 'jobs'))]
61
- for (const jobsDir of candidates) {
62
- try {
63
- if (!existsSync(jobsDir)) continue
64
- const done = readdirSync(jobsDir, { withFileTypes: true })
65
- .filter(d => d.isDirectory() && existsSync(join(jobsDir, d.name, 'artifacts')) && existsSync(join(jobsDir, d.name, 'physics_spec.json')))
66
- .map(d => ({ name: d.name, m: statSync(join(jobsDir, d.name)).mtimeMs }))
67
- .sort((a, b) => b.m - a.m)
68
- if (done.length) return JSON.parse(readFileSync(join(jobsDir, done[0].name, 'physics_spec.json'), 'utf8'))
69
- }
70
- catch { /* 试下一个候选 */ }
71
- }
72
- return null
73
- }
74
-
75
- /* ── S0 · 捕获 spec + 预清数据(改名保留,遵循 *.pre-clean-* 惯例)── */
76
- console.log('[S0] 捕获真实 physics_spec + 预清运行时数据(改名保留)')
77
- const realSpec = captureRealSpec()
78
- ok('捕获真实 physics_spec(训练骨架样本)', Boolean(realSpec), realSpec ? `variables=${realSpec.variables?.length}` : 'aml/jobs 无历史作业')
79
- for (const port of [AW_PORT, HOME_PORT, SIM_PORT]) killPort(port)
80
- if (existsSync(join(REPO, 'aml'))) {
81
- renameSync(join(REPO, 'aml'), join(REPO, `aml.pre-clean-${TODAY}`))
82
- console.log(` · repo/aml → aml.pre-clean-${TODAY}`)
83
- }
84
- // 备份已存在 → 当前目录必是上一轮验收后的全新重建,直接清(真实数据早在首个备份里)
85
- const moveAside = (src, label) => {
86
- if (!existsSync(src)) return
87
- const dst = join(dirname(src), `${label}.pre-clean-${TODAY}`)
88
- if (existsSync(dst)) {
89
- rmSync(src, { recursive: true, force: true })
90
- console.log(` · ${label} → 已有备份 ${label}.pre-clean-${TODAY},当前(上次重建)直接清除`)
91
- }
92
- else {
93
- renameSync(src, dst)
94
- console.log(` · ${label} → ${label}.pre-clean-${TODAY}`)
95
- }
96
- }
97
- moveAside(join(REPO, 'aml'), 'aml')
98
- moveAside(join(CONFIG_ROOT, 'data'), 'data')
99
- moveAside(join(CONFIG_ROOT, 'aml'), 'aml')
100
- // 预置运行时设置:MCP 开关 + 门禁校准(placement 验收用松门禁;数据/模型落位与门禁强弱无关)
101
- writeFileSync(join(CONFIG_ROOT, 'runtime-settings.json'), JSON.stringify({ version: 1, overrides: { 'mcp.enabled': true, 'aml.gates.nrmse': 0.9, 'aml.gates.rolloutNrmse': Number(process.env.RTD_GATE_ROLLOUT ?? 0.99), 'aml.gates.valTestGap': 2, 'aml.gates.minRows': 100 } }))
102
- ok('A0 预清完成(检出根/aml 与配置根/data·aml 均已移除)', !existsSync(join(REPO, 'aml')) && !existsSync(join(CONFIG_ROOT, 'data')) && !existsSync(join(CONFIG_ROOT, 'aml')))
103
-
104
- /* ── S1 · repo 模式冷启动(无 AW_HOME/AW_MODE,配置根=.AgentWorkShop)── */
105
- console.log('[S1] repo 模式冷启动(配置根 = <repo>/.AgentWorkShop)')
106
- {
107
- const out = openSync(join(CONFIG_ROOT, 'boot-audit.log'), 'a')
108
- const p = spawn(process.execPath, [join(REPO, 'bin', 'aw.mjs'), 'start', '--port', String(AW_PORT)], {
109
- cwd: REPO,
110
- env: { ...process.env, NO_PROXY: '127.0.0.1,localhost', HTTP_PROXY: '', HTTPS_PROXY: '', NUXT_SESSION_PASSWORD: 'runtime-dir-e2e-session-password-0123456' },
111
- detached: true, windowsHide: true, stdio: ['ignore', out, out],
112
- })
113
- closeSync(out); p.unref()
114
- }
115
- let actualPort = AW_PORT
116
- for (let i = 0; i < 20; i++) {
117
- await sleep(1500)
118
- try {
119
- const lock = JSON.parse(readFileSync(join(CONFIG_ROOT, '.runtime', 'aw.lock'), 'utf8'))
120
- if (Number.isInteger(lock?.port)) { actualPort = lock.port; break }
121
- }
122
- catch { /* 等锁 */ }
123
- }
124
- BASE = `http://127.0.0.1:${actualPort}`
125
- let up = false
126
- for (let i = 0; i < 40; i++) {
127
- await sleep(2000)
128
- if ((await getJson(`${BASE}/api/health`))?.data?.status === 'ok') { up = true; break }
129
- }
130
- ok('平台健康门', up, `BASE=${BASE} 日志 ${join(CONFIG_ROOT, 'boot-audit.log')}`)
131
- if (!up) { console.log(`═══ ${pass} PASS / ${fails.length + 1} FAIL ═══`); process.exit(1) }
132
-
133
- /* ── S2 · A2 全产物落位 + A4 预热已触发 ── */
134
- console.log('[S2] A2 全产物落位配置根 + A4 启动预热触发')
135
- let TOKEN = ''
136
- {
137
- ok('A2a data/ 重建于配置根', existsSync(join(CONFIG_ROOT, 'data')))
138
- ok('A2b aml 骨架重建于配置根', ['datasets', 'jobs', 'models', 'tools', 'runtime'].every(s => existsSync(join(CONFIG_ROOT, 'aml', s))))
139
- ok('A2c 检出根无 aml/ 运行时目录(零新增)', !existsSync(join(REPO, 'aml')))
140
-
141
- for (let i = 0; i < 15; i++) {
142
- try {
143
- const r = await fetch(`${BASE}/api/users/register`, { method: 'POST', headers: { 'content-type': 'application/json' }, body: JSON.stringify({ name: 'runtime-audit', email: `runtime-${Date.now()}@awshop.local`, password: 'runtime-e2e-passw0rd' }) })
144
- const j = await r.json()
145
- if (j?.data?.token) { TOKEN = j.data.token; break }
146
- }
147
- catch { /* 服务未就绪,重试 */ }
148
- await sleep(2000)
149
- }
150
- ok('admin 注册(全新库首注册即 admin)', Boolean(TOKEN))
151
- const envInfo = await getJson(`${BASE}/api/workshop/aml/env`, TOKEN)
152
- ok('A2d aml/env 报告运行时根', envInfo?.data?.amlRoot === join(CONFIG_ROOT, 'aml'), JSON.stringify({ root: envInfo?.data?.amlRoot, src: envInfo?.data?.amlRootSource }))
153
- ok('A2e 来源标签=项目运行时根', /项目运行时根/.test(envInfo?.data?.amlRootSource ?? ''), envInfo?.data?.amlRootSource)
154
- const bootLog = existsSync(join(CONFIG_ROOT, 'boot-audit.log')) ? readFileSync(join(CONFIG_ROOT, 'boot-audit.log'), 'utf8') : ''
155
- ok('A4a 启动预热已触发(uv 探测+后台建环境)', bootLog.includes('[aml] 启动预热'), bootLog.split('\n').filter(l => l.includes('[aml]')).slice(-2).join(' | ') || '(无 [aml] 行)')
156
- }
157
-
158
- /* ── S3 · A4 等 venv ready(uv 供给)── */
159
- console.log('[S3] A4 等待训练环境就绪(uv 后台供给,最长 10 分钟)')
160
- {
161
- let ready = false
162
- let last = ''
163
- for (let i = 0; i < 60; i++) {
164
- await sleep(10_000)
165
- const st = await getJson(`${BASE}/api/workshop/aml/env`, TOKEN)
166
- last = JSON.stringify({ ready: st?.data?.venv?.ready, task: st?.data?.task?.status, tail: st?.data?.task?.log?.slice(-1) })
167
- if (st?.data?.venv?.ready) { ready = true; break }
168
- }
169
- ok('A4b .venv 在配置根就绪(uv 供给)', ready, last)
170
- ok('A4c venv 落点在配置根内', existsSync(join(CONFIG_ROOT, 'aml', '.venv')), join(CONFIG_ROOT, 'aml', '.venv'))
171
- }
172
-
173
- /* ── S4 · A3 训练产物入配置根(权威建线 → 4 批 → 数据集 → hybrid 训练 → 模型)── */
174
- console.log('[S4] A3 训练产物入运行时目录(建线→4 批次→数据集→训练→模型)')
175
- {
176
- process.env.SIM_BASE = SIM
177
- process.env.SIM_SHADOW_DIR = SIM_DIR
178
- const { ensureSimulator, applyPreset } = await import('../../bench/lib/sim.mjs')
179
- await ensureSimulator({ log: () => {} })
180
- await applyPreset('cast-film-physics')
181
- const simDevices = (await getJson(`${SIM}/api/nodes`))?.data ?? []
182
-
183
- const { provisionTwinLine, startTwinBatch } = await import('../../bench/lib/closedloop.mjs')
184
- const callA = async (method, path, body) => {
185
- const r = await fetch(`${BASE}${path}`, { method, headers: { 'content-type': 'application/json', 'authorization': `Bearer ${TOKEN}` }, body: body === undefined ? undefined : JSON.stringify(body), signal: AbortSignal.timeout(60000) })
186
- const json = await r.json().catch(() => null)
187
- return { status: r.status, json, message: json?.message, data: json?.data }
188
- }
189
- const twin = await provisionTwinLine({ call: async (m, p, b) => { const r = await callA(m, p, b); return { status: r.status, data: r.data, message: r.message } } }, { simDevices, sfx: 'rtdir' })
190
- ok('S4a 权威建线(6 DCW + 5 DAQ)', twin.ok, (twin.ev ?? []).join(' | ').slice(0, 200))
191
- globalThis.__lineId = twin.lineId
192
-
193
- const spReadback = {}
194
- {
195
- // SP 回读 DAQ 节点(two-modes 同款:export 取配置,http/mqtt 的 jsonKey 修成 jsonPath)
196
- for (const dev of simDevices) {
197
- const exp = (await getJson(`${SIM}/api/nodes/${dev.id}/export`))?.data?.items ?? []
198
- for (const id of Object.keys(twin.dcw)) {
199
- if (spReadback[id]) continue
200
- const sig = (dev.signals ?? []).find(s => s.id === id)
201
- if (!sig) continue
202
- const item = exp.find(i => i.signal === sig.name)
203
- if (!item?.driverConfig) continue
204
- const cfg = { ...item.driverConfig }
205
- if (cfg.jsonKey !== undefined && cfg.jsonPath === undefined) { cfg.jsonPath = cfg.jsonKey; delete cfg.jsonKey }
206
- const r = await callA('POST', '/api/workshop/daq', {
207
- name: `${sig.name} 回读 rtdir`, templateRef: 'daq-temp-tc', driver: dev.protocol, driverConfig: cfg,
208
- unit: sig.unit, min: sig.min, max: sig.max, lineId: twin.lineId, intervalMs: 1000, publishIntervalMs: 0,
209
- semantics: `执行器设定点回读(AML control 输入) ${item.signal}`,
210
- })
211
- spReadback[id] = r.json?.data?.node?.id ?? r.json?.data?.id
212
- }
213
- }
214
- }
215
- ok('S4a-2 SP 回读 DAQ ×6', Object.keys(spReadback).length === 6, JSON.stringify(spReadback))
216
- // 膜厚语义补「目标 goal + 厚度」词表(scene 编译 target 识别依据;two-modes 同款 PATCH)
217
- await callA('PATCH', `/api/workshop/daq/${twin.daq['film-thickness']}`, { semantics: '流延膜厚度测量(优化目标 goal,单位 μm;厚度质量输出)' })
218
- await callA('POST', '/api/workshop/daq/controller', { action: 'start' })
219
- const batch = await startTwinBatch({ call: async (m, p, b) => { const r = await callA(m, p, b); return { status: r.status, data: r.data, message: r.message } } }, { lineId: twin.lineId, productId: twin.productId, dcw: twin.dcw, sfx: 'rtdir' })
220
- globalThis.__lineId = twin.lineId
221
- ok('S4b 配方开跑(批次1)', batch.ok && Boolean(batch.recipeId), JSON.stringify(batch).slice(0, 140))
222
- const recipeId = batch.recipeId
223
-
224
- /* ── S4c 训练通道(hybrid_twin)+ 场景发现/编译/冻结 + 骨架 PhysicsSpec ── */
225
- const scene = { sceneId: `runtime-dir-accept`, sceneVersion: '1.0.0', lineId: twin.lineId, productId: twin.productId, recipeId }
226
- const inst = await callA('POST', '/api/workshop/channel-templates/chtpl-hybrid-twin-mpc-default/instantiate', {
227
- name: `运行时目录训练通道 rtdir`, toolProfile: 'hybrid_twin', scene,
228
- objective: { objectiveId: 'thickness-50um', targets: { film_thickness: 50 } },
229
- controlPolicy: 'recommendation_only',
230
- })
231
- const instData = inst.json?.data ?? {}
232
- const channelA = instData.channelId
233
- const workerA = (instData.agents ?? []).find(a => a.role === 'worker')?.id
234
- ok('S4c-1 训练通道实例化(hybrid_twin)+ worker', Boolean(channelA && workerA), JSON.stringify({ channelA, workerA }).slice(0, 120))
235
- for (const nodeId of Object.values(twin.dcw)) await callA('POST', '/api/workshop/agent-tools/bindings', { agentId: workerA, nodeId, kind: 'dcw', mode: 'auto' })
236
- for (const nodeId of Object.values(twin.daq)) await callA('POST', '/api/workshop/agent-tools/bindings', { agentId: workerA, nodeId, kind: 'daq', mode: 'auto' })
237
- const invoke = async (tool, args, agentId) => {
238
- const r = await callA('POST', '/api/workshop/agent-tools/invoke', { agentId, tool, args })
239
- const result = r.json?.data?.result
240
- return { isError: Boolean(result?.isError), text: String(result?.text ?? ''), data: result?.data ?? null }
241
- }
242
- const disco = await invoke('twin_scene_discover', {}, workerA)
243
- ok('S4c-2 场景发现(target=1 语义命中)', !disco.isError && /"target"\s*:\s*1/.test(disco.text), disco.text.slice(0, 140))
244
- const compiled = await invoke('twin_scene_compile', {
245
- scene_id: scene.sceneId, scene_version: '1.0.0', line_id: twin.lineId, product_id: twin.productId, recipe_id: recipeId,
246
- prompt: '流延膜厚度闭环优化:目标膜厚 50μm。控制=6 个执行器设定点,观测=膜厚(目标)/熔温/熔压。约束:熔温 195~225℃,熔压 ≤22MPa。膜厚为目标输出。',
247
- }, workerA)
248
- ok('S4c-3 场景编译', !compiled.isError, compiled.text.slice(0, 140))
249
- const frozen = await invoke('twin_scene_freeze', {
250
- scene_id: scene.sceneId, scene_version: '1.0.0', confirmation: 'USER_CONFIRMED_SCENE_CONTRACT', approved_by: 'runtime-dir-e2e',
251
- }, workerA)
252
- ok('S4c-4 场景冻结(用户确认令牌)', !frozen.isError, frozen.text.slice(0, 140))
253
- const draft = await invoke('twin_physics_spec_draft', { dt_sec: 1 }, workerA)
254
- const draftArtifactPath = (draft.text.match(/artifact:\s*([^\n]+)/) || [])[1]?.trim()
255
- ok('S4c-5 骨架 PhysicsSpec 生成', !draft.isError && Boolean(draftArtifactPath) && existsSync(draftArtifactPath), draft.text.slice(0, 140))
256
- const physicsSpec = JSON.parse(readFileSync(draftArtifactPath, 'utf8'))
257
- const dwToDn = {}
258
- for (const [sig, dn] of Object.entries(spReadback)) dwToDn[twin.dcw[sig]] = dn
259
- console.log(' ↳ 批次1 采样积累 300s(物理滞后:阶跃全响应需要长批)')
260
- await sleep(300_000)
261
-
262
- /* ── S4d 4 个已闭合批次(每批 ~75s;首批已跑)── */
263
- const closeAndRestart = async (i) => {
264
- await callA('POST', `/api/workshop/dcw/lines/${twin.lineId}/stop`, {})
265
- await sleep(3000)
266
- const st = await callA('POST', `/api/workshop/dcw/lines/${twin.lineId}/start`, { recipeId })
267
- if (st.status !== 200) { await sleep(8000); await callA('POST', `/api/workshop/dcw/lines/${twin.lineId}/start`, { recipeId }) }
268
- console.log(` ↳ 批次 ${i} 闭合/重启`)
269
- }
270
- // 批次 2-4:每批 300s + 两次工况阶跃(+65s/+200s)。物理滞后(熔体延迟/热惯性)需要长批
271
- // 才能看到阶跃的全响应;短批数据"输入已变输出未动"会毁掉一致性(实测 NRMSE>1 的根因)。
272
- const BATCHES = [
273
- { n: 2, steps: [{ at: 65_000, node: 'linespeed-sp', v: 97 }, { at: 200_000, node: 'diegap-sp', v: 1.03 }] },
274
- { n: 3, steps: [{ at: 65_000, node: 'linespeed-sp', v: 93 }, { at: 200_000, node: 'diegap-sp', v: 0.97 }] },
275
- { n: 4, steps: [{ at: 65_000, node: 'linespeed-sp', v: 97 }, { at: 200_000, node: 'diegap-sp', v: 1.0 }] },
276
- ]
277
- for (const b of BATCHES) {
278
- await closeAndRestart(b.n) // 闭合上一批 → 新批配方下发(锚定 60s 冷却)
279
- let prev = 0
280
- for (const st of b.steps) {
281
- await sleep(st.at - prev)
282
- prev = st.at
283
- const w = await callA('POST', `/api/workshop/dcw/${twin.dcw[st.node]}/write`, { value: st.v })
284
- console.log(` ↳ 批次 ${b.n} 阶跃 ${st.node} ← ${st.v} ${w.status === 200 ? '√' : '✘ ' + String(w.json?.message ?? '').slice(0, 70)}`)
285
- }
286
- await sleep(300_000 - prev)
287
- }
288
- await callA('POST', `/api/workshop/dcw/lines/${twin.lineId}/stop`, {})
289
- await sleep(3000)
290
-
291
- const runs = (await callA('GET', '/api/workshop/dcw/recipes')).json?.data?.runs ?? []
292
- const closed = runs.filter(x => x.endedAt && x.recipeId === recipeId)
293
- ok('S4d 4 个已闭合批次', closed.length >= 4, `closed=${closed.length}`)
294
-
295
- /* ── S4e 数据集(9 节点)+ spec 变量改绑回读 + 训练 + 模型 ── */
296
- const ds = (await callA('POST', '/api/workshop/aml/datasets', {
297
- lineId: twin.lineId, productId: twin.productId, recipeId,
298
- nodes: [
299
- ...Object.values(spReadback).map(nid => ({ nodeId: nid, role: 'control' })),
300
- { nodeId: twin.daq['film-thickness'], role: 'target' },
301
- { nodeId: twin.daq['melt-pressure'], role: 'feature' },
302
- { nodeId: twin.daq['melt-temp'], role: 'feature' },
303
- ],
304
- beatMs: 1000, window: { historySteps: 8, horizonSteps: 4 },
305
- split: { valRatio: 0.34, testRatio: 0.33, seed: Number(process.env.RTD_SPLIT_SEED ?? 42) },
306
- purpose: 'mpc_surrogate', note: '运行时目录规约验收数据集',
307
- })).json?.data?.dataset
308
- ok('S4e-1 数据集构建(9 变量对齐 spec)', Boolean(ds?.id) && ds.runIds?.length >= 4, JSON.stringify({ id: ds?.id, rows: ds?.rowCount, runs: ds?.runIds?.length }).slice(0, 140))
309
- ok('A3a 数据集实体在配置根', existsSync(join(CONFIG_ROOT, 'aml', 'datasets', ds.id, 'manifest.json')), join(CONFIG_ROOT, 'aml', 'datasets', ds.id))
310
-
311
- // 训练前对齐(two-modes 同款):spec 变量改绑回读节点 + 剔除数据集外变量
312
- const man = JSON.parse(readFileSync(join(CONFIG_ROOT, 'aml', 'datasets', ds.id, 'manifest.json'), 'utf8'))
313
- const datasetNodes = new Set(man.allNodes)
314
- for (const v of physicsSpec.variables) {
315
- if (v.nodeId && !datasetNodes.has(v.nodeId) && dwToDn[v.nodeId]) v.nodeId = dwToDn[v.nodeId]
316
- }
317
- const keptVars = physicsSpec.variables.filter(v => !v.nodeId || datasetNodes.has(v.nodeId))
318
- const keptIds = new Set(keptVars.map(v => v.id))
319
- physicsSpec.variables = keptVars
320
- physicsSpec.states = physicsSpec.states.filter((e) => { const base = e.lhs.endsWith('_next') ? e.lhs.slice(0, -5) : e.lhs; return keptIds.has(base) })
321
- physicsSpec.observations = physicsSpec.observations.filter(e => keptIds.has(e.lhs))
322
- physicsSpec.guards = (physicsSpec.guards ?? []).filter(e => keptIds.has(e.lhs))
323
- physicsSpec.constraints = physicsSpec.constraints.filter(c => keptIds.has(c.id))
324
-
325
- const job = (await callA('POST', '/api/workshop/aml/jobs', {
326
- datasetId: ds.id, purpose: 'mpc_surrogate', changeNote: '运行时目录规约验收训练',
327
- params: { epochs: 600, hidden: 128, lr: 0.0015, residual_scale: 2, ensemble: 3 },
328
- seed: 11, jobKind: 'hybrid_residual', sceneId: scene.sceneId, sceneVersion: '1.0.0', objectiveId: 'thickness-50um',
329
- physicsSpec, providerId: physicsSpec.modelId, providerVersion: '1.0.0', providerHash: `sha256:${JSON.stringify(physicsSpec).length}`,
330
- modelName: `运行时目录验收模型 rtdir`, modelDescription: 'A3 验收:模型工件应落在运行时目录',
331
- })).json?.data?.job
332
- ok('S4e-2 训练作业提交', Boolean(job?.id), JSON.stringify(job ?? {}).slice(0, 160))
333
-
334
- let jobDone = null
335
- for (let i = 0; i < 60; i++) {
336
- await sleep(5000)
337
- const r = await callA('GET', `/api/workshop/aml/jobs/${job.id}`)
338
- jobDone = r.json?.data?.job
339
- if (jobDone?.status === 'done' || jobDone?.status === 'failed') break
340
- }
341
- ok('S4f 训练完成(平台门禁全过)', jobDone?.status === 'done', `status=${jobDone?.status} err=${(jobDone?.error ?? '').slice(0, 160)}`)
342
- const models = (await callA('GET', '/api/workshop/aml/models')).json?.data?.models ?? []
343
- const model = models.find(m => m.datasetId === ds.id)
344
- ok('A3b 模型注册且工件在配置根', Boolean(model?.id) && existsSync(join(CONFIG_ROOT, 'aml', 'models', model.id, 'model.onnx')), join(CONFIG_ROOT, 'aml', 'models', model?.id ?? '?'))
345
- }
346
-
347
- /* ── S5 · A5 家目录兜底(临时 cwd 启动,真 ~/.AgentWorkShop)── */
348
- console.log('[S5] A5 家目录兜底:临时 cwd 启动(无 AW_HOME/AW_MODE)')
349
- {
350
- const tempCwd = mkdtempSync(join(tmpdir(), 'aw-fallback-cwd-'))
351
- const homeRoot = join(homedir(), '.AgentWorkShop')
352
- const out = openSync(join(tempCwd, 'home-instance.log'), 'a')
353
- const p = spawn(process.execPath, [join(REPO, 'bin', 'aw.mjs'), 'start', '--port', String(HOME_PORT)], {
354
- cwd: tempCwd,
355
- env: { ...process.env, NO_PROXY: '127.0.0.1,localhost', HTTP_PROXY: '', HTTPS_PROXY: '', NUXT_SESSION_PASSWORD: 'runtime-dir-e2e-session-password-0123456' },
356
- detached: true, windowsHide: true, stdio: ['ignore', out, out],
357
- })
358
- closeSync(out); p.unref()
359
- let hb = false
360
- for (let i = 0; i < 40; i++) {
361
- await sleep(2000)
362
- if ((await getJson(`http://127.0.0.1:${HOME_PORT}/api/health`))?.data?.status === 'ok') { hb = true; break }
363
- }
364
- ok('A5a 家目录兜底实例健康(检出外 cwd)', hb, `日志 ${join(tempCwd, 'home-instance.log')}`)
365
- await sleep(4000)
366
- const bootLog = existsSync(join(tempCwd, 'home-instance.log')) ? readFileSync(join(tempCwd, 'home-instance.log'), 'utf8') : ''
367
- ok('A5b 兜底实例同样触发 AML 环境预热', bootLog.includes('[aml] 启动预热'), bootLog.split('\n').filter(l => l.includes('[aml]')).slice(-1).join('') || '(无)')
368
- ok('A5c 数据/AML 落 ~/.AgentWorkShop', existsSync(join(homeRoot, 'data')) && existsSync(join(homeRoot, 'aml', 'datasets')))
369
- killPort(HOME_PORT)
370
- try { rmSync(tempCwd, { recursive: true, force: true, maxRetries: 3, retryDelay: 1500 }) } catch { /* 实例句柄延迟释放,允许残留 */ }
371
- }
372
-
373
- /* ── S6 · A6 更新链路 ── */
374
- console.log('[S6] A6 更新链路:aw update --check(npm registry 对比)')
375
- {
376
- const r = spawnSync(process.execPath, [join(REPO, 'bin', 'aw.mjs'), 'update', '--check'], { cwd: REPO, encoding: 'utf8', timeout: 120_000, shell: true })
377
- const out = `${r.stdout ?? ''}${r.stderr ?? ''}`
378
- ok('A6 aw update --check 正常执行(版本对比/网络说明)', r.status === 0 || /latest|version|registry|npm|网络|超时/i.test(out), out.slice(0, 200))
379
- ok('A6b 配置根在包外(更新不触碰数据/模型/venv——设计断言)', !resolve(REPO, '.output').startsWith(join(homedir(), '.AgentWorkShop')) && existsSync(join(CONFIG_ROOT, 'aml', '.venv')))
380
- }
381
-
382
- /* ── 清场 ── */
383
- console.log('[清场]')
384
- killPort(actualPort)
385
- killPort(SIM_PORT)
386
- await sleep(1500)
387
- console.log(` · 保留新初始化的运行时目录(${CONFIG_ROOT})与 aml.pre-clean-${TODAY}/data.pre-clean-${TODAY} 备份`)
388
-
389
- console.log('')
390
- console.log(`═══ 运行时目录规约验收:${pass} PASS / ${fails.length} FAIL ═══`)
391
- for (const f of fails) console.log(` ✖ ${f}`)
392
- console.log('')
393
- process.exit(fails.length ? 1 : 0)
@@ -1,129 +0,0 @@
1
- /**
2
- * town-focus-shot.mjs —— 只拍数字孪生,并尝试把 3D 视角调到能看清设备
3
- * 用 window.__townStats 读真实渲染指标(设备数/实例数/FPS)作为"模型真的在场"的判据,
4
- * 而不是靠肉眼看截图。
5
- */
6
- import { existsSync, mkdirSync } from 'node:fs'
7
- import { dirname, join, resolve } from 'node:path'
8
- import { fileURLToPath } from 'node:url'
9
- import puppeteer from 'puppeteer-core'
10
-
11
- const HERE = dirname(fileURLToPath(import.meta.url))
12
- const REPO = resolve(HERE, '..', '..')
13
- const arg = (k, d) => {
14
- const i = process.argv.indexOf(`--${k}`)
15
- return i > 0 && process.argv[i + 1] ? process.argv[i + 1] : d
16
- }
17
- const BASE = arg('base', 'http://127.0.0.1:3112').replace(/\/$/, '')
18
- const OUT = arg('out', join(REPO, '.e2e-shots', 'plc-clean'))
19
- const EDGE = 'C:\\Program Files (x86)\\Microsoft\\Edge\\Application\\msedge.exe'
20
- const CHROME = 'C:\\Program Files\\Google\\Chrome\\Application\\chrome.exe'
21
- const EXEC = existsSync(EDGE) ? EDGE : CHROME
22
- const sleep = ms => new Promise(r => setTimeout(r, ms))
23
-
24
- mkdirSync(OUT, { recursive: true })
25
- const login = await fetch(`${BASE}/api/users/login`, {
26
- method: 'POST',
27
- headers: { 'content-type': 'application/json' },
28
- body: JSON.stringify({ email: 'plant@awshop.local', password: 'Plant!2026' }),
29
- }).then(r => r.json()).catch(() => null)
30
- const token = login?.data?.token ?? ''
31
- if (!token) { console.error('✖ 登录失败'); process.exit(2) }
32
-
33
- const browser = await puppeteer.launch({
34
- executablePath: EXEC,
35
- headless: 'new',
36
- args: ['--no-sandbox', '--disable-dev-shm-usage', '--force-device-scale-factor=1', '--hide-scrollbars', '--use-gl=angle', '--enable-unsafe-swiftshader'],
37
- defaultViewport: { width: 1920, height: 1200 },
38
- })
39
- try {
40
- const page = await browser.newPage()
41
- await page.goto(`${BASE}/town`, { waitUntil: 'domcontentloaded', timeout: 60_000 })
42
- await page.evaluate((tok) => {
43
- document.cookie = `token=${encodeURIComponent(tok)}; path=/`
44
- document.cookie = 'aw-theme=light; path=/'
45
- localStorage.setItem('app', JSON.stringify({ isDark: false, sidebarCollapsed: true, accent: '', themeTouched: true }))
46
- }, token)
47
- await page.reload({ waitUntil: 'networkidle2', timeout: 60_000 })
48
- // 3D 首帧 + 模型 GLB 异步加载,给足时间
49
- await sleep(12000)
50
-
51
- const stats = await page.evaluate(() => {
52
- const s = globalThis.__townStats
53
- return s ? JSON.parse(JSON.stringify(s)) : null
54
- })
55
- console.log('window.__townStats =', JSON.stringify(stats))
56
-
57
- // 尝试点「复位视角」把相机拉到能看全设备的位置(按钮存在才点)
58
- const resetBtn = await page.evaluateHandle(() => {
59
- const els = [...document.querySelectorAll('button, .ant-btn, [role="button"]')]
60
- return els.find(e => /复位视角|重置视角|复位/.test(e.textContent ?? '')) ?? null
61
- })
62
- const el = resetBtn.asElement()
63
- if (el) {
64
- await el.click().catch(() => {})
65
- console.log('已点击「复位视角」')
66
- await sleep(3500)
67
- }
68
- else {
69
- console.log('未找到「复位视角」按钮,跳过')
70
- }
71
-
72
- // 相机默认拉得很远,设备只有几十像素;点几次放大让设备读得清
73
- const zoomIn = await page.evaluateHandle(() => {
74
- const els = [...document.querySelectorAll('button, .ant-btn, [role="button"], [class*="zoom"]')]
75
- return els.find((e) => {
76
- const txt = (e.textContent ?? '').trim()
77
- const title = `${e.getAttribute('title') ?? ''} ${e.getAttribute('aria-label') ?? ''}`
78
- return txt === '+' || txt === '+' || /放大|zoom in/i.test(title)
79
- }) ?? null
80
- })
81
- const z = zoomIn.asElement()
82
- const ZOOM_CLICKS = Number(arg('zoom', '2'))
83
- if (z) {
84
- for (let i = 0; i < ZOOM_CLICKS; i++) {
85
- await z.click().catch(() => {})
86
- await sleep(700)
87
- }
88
- console.log(`已放大 ${ZOOM_CLICKS} 档`)
89
- }
90
- else {
91
- console.log('未找到放大按钮,保持默认视角')
92
- }
93
- await sleep(1500)
94
-
95
- const file = join(OUT, '数字孪生小镇-1920.png')
96
- await page.screenshot({ path: file, fullPage: false })
97
- console.log(`截图 → ${file}`)
98
-
99
- // 再出一张只含 3D 视口的图:全页截图里场景只占一小块,细节看不出来
100
- const viewport = await page.evaluate(() => {
101
- const canvases = [...document.querySelectorAll('canvas')].map((c) => {
102
- const r = c.getBoundingClientRect()
103
- return { w: r.width, h: r.height, x: r.x, y: r.y }
104
- }).filter(c => c.w > 200 && c.h > 200)
105
- canvases.sort((a, b) => b.w * b.h - a.w * a.h)
106
- const c = canvases[0]
107
- if (!c) return null
108
- // 把 HUD(统计条/趋势/控制面板)也算进去,给出完整场景区
109
- return { x: Math.max(0, c.x - 10), y: Math.max(0, c.y - 60), width: c.w + 20, height: c.h + 80 }
110
- })
111
- if (viewport) {
112
- const sceneFile = join(OUT, '数字孪生小镇-3D视口.png')
113
- await page.screenshot({ path: sceneFile, clip: viewport })
114
- console.log(`3D 视口截图 → ${sceneFile} ${JSON.stringify(viewport)}`)
115
- }
116
-
117
- const canvasInfo = await page.evaluate(() => {
118
- const cs = [...document.querySelectorAll('canvas')].map((c) => {
119
- const r = c.getBoundingClientRect()
120
- return `${c.width}x${c.height} css ${Math.round(r.width)}x${Math.round(r.height)}`
121
- })
122
- return cs
123
- })
124
- console.log('canvases:', JSON.stringify(canvasInfo))
125
- console.log(stats && (stats.devices ?? stats.deviceCount) ? '✅ 场景内确有设备实例' : '⚠ __townStats 未暴露设备计数,以截图为准')
126
- }
127
- finally {
128
- await browser.close()
129
- }
@@ -1,85 +0,0 @@
1
- /**
2
- * town-reposition.mjs —— 把设备孪生收拢到默认相机取景范围内
3
- * 起因:posX/posZ 用的是场景世界坐标,初版按"米"给了 ±14,实际远在默认视锥之外 ——
4
- * __townStats 显示 devices=12(实例确实存在),但画面里几乎看不到。
5
- * 这里按小坐标重新落位,并顺带把频道领地收紧。
6
- */
7
- const BASE = (() => {
8
- const i = process.argv.indexOf('--base')
9
- return (i > 0 ? process.argv[i + 1] : 'http://127.0.0.1:3112').replace(/\/$/, '')
10
- })()
11
-
12
- let TOKEN = null
13
- const api = async (method, path, { body } = {}) => {
14
- const headers = { 'content-type': 'application/json' }
15
- if (TOKEN) headers.authorization = `Bearer ${TOKEN}`
16
- const res = await fetch(`${BASE}${path}`, { method, headers, body: body !== undefined ? JSON.stringify(body) : undefined })
17
- return { status: res.status, ...(await res.json().catch(() => ({}))) }
18
- }
19
- const data = r => r?.data ?? {}
20
-
21
- TOKEN = data(await api('POST', '/api/users/login', { body: { email: 'plant@awshop.local', password: 'Plant!2026' } })).token
22
- if (!TOKEN) { console.error('✖ 登录失败'); process.exit(2) }
23
-
24
- /**
25
- * 三组工艺设备:围绕**世界中心**一字排开。
26
- * ⚠️ 这里是世界坐标,不是"米":shared/town-scene-math.ts 里
27
- * WORLD_W=3200 / WORLD_H=2400,相机看向 (WORLD_CX, WORLD_CZ) = (1600, 1200)。
28
- * 初版按 ±14 给坐标 → 设备落在世界原点那一角,相机根本看不到
29
- * (__townStats 仍报 devices=12,但画面里只有一个位于世界中心的物体)。
30
- */
31
- const CX = 1600
32
- const CZ = 1200
33
- const PLAN = [
34
- { match: /挤出主机/, posX: CX - 120, posZ: CZ - 70 },
35
- { match: /收卷机组/, posX: CX, posZ: CZ - 70 },
36
- { match: /MDO/, posX: CX + 120, posZ: CZ - 70 },
37
- { match: /配电柜/, posX: CX - 120, posZ: CZ + 80 },
38
- { match: /机械臂/, posX: CX, posZ: CZ + 80 },
39
- { match: /测厚仪/, posX: CX + 120, posZ: CZ + 80 },
40
- ]
41
- /** 数采/数控节点也参与场景渲染(伪孪生),它们的 posX/posZ 同样要对齐世界中心 */
42
- const NODE_PLAN = [
43
- { match: /温度采集/, posX: CX - 120, posZ: CZ - 70 },
44
- { match: /速度采集/, posX: CX, posZ: CZ - 70 },
45
- { match: /张力采集/, posX: CX + 120, posZ: CZ - 70 },
46
- { match: /温度设定/, posX: CX - 120, posZ: CZ + 80 },
47
- { match: /速度设定/, posX: CX, posZ: CZ + 80 },
48
- { match: /张力设定/, posX: CX + 120, posZ: CZ + 80 },
49
- ]
50
-
51
- const twins = data(await api('GET', '/api/workshop/device-twins')).twins ?? []
52
- console.log(`孪生实体 ${twins.length} 个`)
53
- let moved = 0
54
- for (const tw of twins) {
55
- const plan = PLAN.find(p => p.match.test(tw.name))
56
- if (!plan) continue
57
- const r = await api('PATCH', `/api/workshop/device-twins/${tw.id}`, { body: { posX: plan.posX, posZ: plan.posZ, rotationY: 0 } })
58
- const okr = r.code === 0 || (r.status >= 200 && r.status < 300)
59
- console.log(` ${okr ? '✔' : '✖'} ${tw.name} → (${plan.posX}, ${plan.posZ})`)
60
- if (okr) moved++
61
- }
62
-
63
- // 数采/数控节点:它们的 posX/posZ 决定场景里的伪孪生落点
64
- let movedNodes = 0
65
- for (const [ep, plan] of [['daq', NODE_PLAN], ['dcw', NODE_PLAN]]) {
66
- const nodes = data(await api('GET', `/api/workshop/${ep}`)).nodes ?? []
67
- for (const n of nodes) {
68
- const p = plan.find(x => x.match.test(n.name))
69
- if (!p) continue
70
- const r = await api('PATCH', `/api/workshop/${ep}/${n.id}`, { body: { posX: p.posX, posZ: p.posZ } })
71
- const okr = r.code === 0 || (r.status >= 200 && r.status < 300)
72
- if (okr) movedNodes++
73
- console.log(` ${okr ? '✔' : '✖'} [${ep}] ${n.name} → (${p.posX}, ${p.posZ})`)
74
- }
75
- }
76
-
77
- // 频道领地铺在世界中心,让地面环与设备尺度匹配
78
- const chans = data(await api('GET', '/api/workshop/channels'))
79
- const ch = (Array.isArray(chans) ? chans : (chans.channels ?? []))[0]
80
- if (ch) {
81
- const r = await api('PUT', `/api/workshop/scene/layouts/${ch.id}`, { body: { x: CX, z: CZ, radiusX: 260, radiusZ: 180, shape: 'ellipse' } })
82
- console.log(` 领地铺在世界中心 (${CX}, ${CZ}) radius 260×180 (code=${r.code})`)
83
- }
84
-
85
- console.log(`\n${moved === PLAN.length && movedNodes === 6 ? '✅' : '⚠'} 孪生 ${moved}/${PLAN.length} · 节点 ${movedNodes}/6 已重排`)