weaver-work-cli 0.1.42 → 0.1.44

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 (318) hide show
  1. package/README.md +17 -0
  2. package/dist/chunks/{archive-J4I6MCKF.js → archive-P6TBQGKL.js} +13 -5
  3. package/dist/chunks/{archive-oa-BRZKKTO4.js → archive-oa-7TQ2NXOH.js} +12 -5
  4. package/dist/chunks/{asset-L7D4FAOZ.js → asset-3ELRG37G.js} +11 -4
  5. package/dist/chunks/{asset-idle-DADLLV75.js → asset-idle-WIGMUFMD.js} +7 -3
  6. package/dist/chunks/{attachment-content-K4C7VLWQ.js → attachment-content-E3276UOV.js} +5 -4
  7. package/dist/chunks/{blog-BVGQ7NZL.js → blog-C5NMZAAC.js} +11 -4
  8. package/dist/chunks/{caizhilian-SAADNFD6.js → caizhilian-5XSM2DFP.js} +13 -6
  9. package/dist/chunks/{calendar-Q7NQY5Z2.js → calendar-FI2WNSBO.js} +12 -5
  10. package/dist/chunks/{chunk-YRSZQUD2.js → chunk-3YBDYOC4.js} +3 -3
  11. package/dist/chunks/{chunk-OOUTBLZ4.js → chunk-56EZERK4.js} +1 -1
  12. package/dist/chunks/chunk-6N4JPNFL.js +76 -0
  13. package/dist/chunks/{chunk-ZUX3P6BQ.js → chunk-727FH2NI.js} +1 -1
  14. package/dist/chunks/chunk-7BDPM5ST.js +11 -0
  15. package/dist/chunks/{chunk-EKWAQSLU.js → chunk-BCVYBYYT.js} +432 -2248
  16. package/dist/chunks/{chunk-W7BEHOSR.js → chunk-CWYGFU5B.js} +2 -2
  17. package/dist/chunks/{chunk-NOODWMCL.js → chunk-D4ADSZ7H.js} +1 -1
  18. package/dist/chunks/{chunk-SA6VBIHY.js → chunk-ETNJSKMM.js} +214 -16
  19. package/dist/chunks/{chunk-BBKDXQEC.js → chunk-F4E4EM35.js} +3 -3
  20. package/dist/chunks/{chunk-IZ7S7QUS.js → chunk-FAZTGX7S.js} +6 -6
  21. package/dist/chunks/{chunk-NKZRQXST.js → chunk-FRZKBMSW.js} +52 -36
  22. package/dist/chunks/{chunk-BYBSCN4X.js → chunk-G7PQWD4L.js} +6 -3
  23. package/dist/chunks/{chunk-GEWYMQME.js → chunk-GAMZLAG2.js} +1 -1
  24. package/dist/chunks/{chunk-R4CHUSKC.js → chunk-GM6J7Q4B.js} +4 -4
  25. package/dist/chunks/{chunk-APVFJUQH.js → chunk-GRDRG6HP.js} +3 -3
  26. package/dist/chunks/{chunk-LDZQPUIA.js → chunk-HIT4Y6OI.js} +1 -1
  27. package/dist/chunks/{chunk-EZALDOQH.js → chunk-HP7JIYMT.js} +5 -2
  28. package/dist/chunks/{chunk-LADPYOWC.js → chunk-IAZ3UPY6.js} +3 -3
  29. package/dist/chunks/{chunk-ZEDWSH32.js → chunk-IC62NFM5.js} +1 -1
  30. package/dist/chunks/{chunk-P26ZWSKU.js → chunk-KIHNAS25.js} +5 -2
  31. package/dist/chunks/{chunk-BIPYLLVS.js → chunk-N4M2DDFE.js} +15 -15
  32. package/dist/chunks/{chunk-QKNKR4RH.js → chunk-OF4S23UB.js} +4 -4
  33. package/dist/chunks/{chunk-JPRO6ER2.js → chunk-PC7VKEB5.js} +57 -60
  34. package/dist/chunks/{chunk-4PD5NWAX.js → chunk-PUQS5MWL.js} +2 -2
  35. package/dist/chunks/{chunk-2LV74IWP.js → chunk-Q4OYAQYH.js} +1 -1
  36. package/dist/chunks/{chunk-72CKAUAG.js → chunk-QVSWRLLU.js} +7 -5
  37. package/dist/chunks/{chunk-4RAE6JXP.js → chunk-TA7FXXJD.js} +6 -3
  38. package/dist/chunks/{chunk-GPMFD4RD.js → chunk-TXUG266F.js} +1 -1
  39. package/dist/chunks/{chunk-FOAA27U5.js → chunk-UFIT2UU3.js} +16 -4
  40. package/dist/chunks/{chunk-LUSPKZKY.js → chunk-UG5G54VL.js} +1 -0
  41. package/dist/chunks/{chunk-NIAJ5ZCG.js → chunk-UL5XUQ25.js} +5 -2
  42. package/dist/chunks/{chunk-FMPJJYYI.js → chunk-WRXSAVKO.js} +1 -1
  43. package/dist/chunks/{chunk-G4UR6NXN.js → chunk-WSF4NNMR.js} +3 -3
  44. package/dist/chunks/chunk-XHK4MDR5.js +2497 -0
  45. package/dist/chunks/{chunk-3KTFS4IA.js → chunk-XNIK66I4.js} +19 -9
  46. package/dist/chunks/{chunk-3SO6QL6U.js → chunk-YWX377BY.js} +5 -2
  47. package/dist/chunks/{chunk-BYATLLEF.js → chunk-Z3GDFVJR.js} +1 -1
  48. package/dist/chunks/{chunk-GHXCDPTM.js → chunk-Z7VYWPZV.js} +1 -1
  49. package/dist/chunks/{conflict-F2OMZRTO.js → conflict-ARLSZJ6V.js} +4 -3
  50. package/dist/chunks/{continuation-2CKSBLA6.js → continuation-3S37AUSH.js} +4 -3
  51. package/dist/chunks/{continuation-RN6PZN2M.js → continuation-3XLYYTKV.js} +4 -3
  52. package/dist/chunks/{continuation-HZIZRZBX.js → continuation-HFW2YT5S.js} +4 -3
  53. package/dist/chunks/{continuation-NLECEJPX.js → continuation-KI7DRRZN.js} +4 -3
  54. package/dist/chunks/{contract-5BETHRSG.js → contract-DNIIW5VJ.js} +13 -5
  55. package/dist/chunks/{cowork-3MN6EQQO.js → cowork-GMLRGVIW.js} +11 -4
  56. package/dist/chunks/{create-flow-5FQNNMVO.js → create-flow-J22BO65E.js} +8 -7
  57. package/dist/chunks/{ebuilder-form-SBHOYBUD.js → ebuilder-form-ANV2FHYV.js} +12 -7
  58. package/dist/chunks/{ehr-KMOJULKG.js → ehr-GSTGAIY3.js} +266 -24
  59. package/dist/chunks/{employee-SAK2QYXX.js → employee-22BGJ3QS.js} +3 -3
  60. package/dist/chunks/{env-LB7NBL2O.js → env-BX3VRFS7.js} +4 -3
  61. package/dist/chunks/{esb-W2PJCFCX.js → esb-ATAIASX2.js} +12 -7
  62. package/dist/chunks/{factory-6ZFQXQ46.js → factory-PETTFME6.js} +3 -2
  63. package/dist/chunks/{fna-ZQPCUV4R.js → fna-YEKBSFSX.js} +14 -8
  64. package/dist/chunks/{group-chat-2HHAJN46.js → group-chat-BFVXAYFX.js} +5 -4
  65. package/dist/chunks/{host-ATKVNZAT.js → host-HRBXEPDQ.js} +5 -5
  66. package/dist/chunks/{host-BQH22NTQ.js → host-LR55CTHP.js} +5 -5
  67. package/dist/chunks/{host-X2CSLFM6.js → host-SUOY6VYQ.js} +5 -5
  68. package/dist/chunks/{host-4CBHGOHT.js → host-SZGV4UNT.js} +5 -5
  69. package/dist/chunks/{host-YTODKMSL.js → host-WIKN2EJ5.js} +5 -5
  70. package/dist/chunks/{hrm-FFM4UJFS.js → hrm-NRDO4W5G.js} +11 -7
  71. package/dist/chunks/{im-VEHKDQPB.js → im-IQ2HN23S.js} +8 -7
  72. package/dist/chunks/{invoice-LVIKSIIF.js → invoice-MNRW76PP.js} +636 -1768
  73. package/dist/chunks/{jiuchuanhui-X6DINO5P.js → jiuchuanhui-DTRBAX4N.js} +14 -6
  74. package/dist/chunks/{lazy-dispatch-KSWTN5L6.js → lazy-dispatch-ZVWAI25B.js} +7 -6
  75. package/dist/chunks/{mail-VDKRGUD3.js → mail-ZVAUXOJA.js} +16 -14
  76. package/dist/chunks/{meeting-CLC6HP3Z.js → meeting-FEVPZ67S.js} +21 -14
  77. package/dist/chunks/{okr-CHG4OO3U.js → okr-SDH3E5RA.js} +12 -5
  78. package/dist/chunks/{operations-5QL3AECO.js → operations-62N6EP3C.js} +4 -3
  79. package/dist/chunks/{plan-XWR75667.js → plan-E35JFDI7.js} +12 -5
  80. package/dist/chunks/{project-5BXOOKMG.js → project-73QXBAB2.js} +11 -4
  81. package/dist/chunks/reception-UWZVACBN.js +1899 -0
  82. package/dist/chunks/{recruit-stage-DGMFNNDE.js → recruit-stage-4MAOCKFY.js} +320 -57
  83. package/dist/chunks/registry-IM5G23LS.js +24 -0
  84. package/dist/chunks/{registry-RHMW6ANW.js → registry-JDUS4E7D.js} +7 -6
  85. package/dist/chunks/{registry-7FFOXIAW.js → registry-KNKSCJNT.js} +7 -6
  86. package/dist/chunks/{registry-Z43434VG.js → registry-PO7SI256.js} +4 -4
  87. package/dist/chunks/{registry-OZSMDVPP.js → registry-PVUZQDDQ.js} +3 -3
  88. package/dist/chunks/{room-recommend-62H7ZQQ6.js → room-recommend-H7KLXA5R.js} +6 -5
  89. package/dist/chunks/{schedule-FNXKH3DQ.js → schedule-ESZIBAUO.js} +6 -5
  90. package/dist/chunks/{workflow-ADHKCAJK.js → workflow-CWJFJLQU.js} +13 -8
  91. package/dist/cmd/action.js +6 -0
  92. package/dist/cmd/identity/index.js +45 -0
  93. package/dist/cmd/index.js +2 -0
  94. package/dist/core/continuation-ttl.js +18 -0
  95. package/dist/core/error-codes.js +85 -0
  96. package/dist/core/logger.js +11 -0
  97. package/dist/index.js +37 -31
  98. package/dist/internal/e10/auth/commands.js +163 -8
  99. package/dist/internal/e10/auth/error-log.js +182 -0
  100. package/dist/internal/e10/auth/session.js +17 -3
  101. package/dist/internal/e10/auth-recovery.js +39 -12
  102. package/dist/internal/e10/context.js +17 -2
  103. package/dist/internal/skills/install.js +9 -1
  104. package/dist/shortcuts/archive/continuation.js +2 -1
  105. package/dist/shortcuts/archive/index.js +3 -0
  106. package/dist/shortcuts/archive/operations/confirm.js +2 -1
  107. package/dist/shortcuts/archive-oa/continuation.js +2 -1
  108. package/dist/shortcuts/archive-oa/index.js +2 -0
  109. package/dist/shortcuts/archive-oa/operations/confirm.js +2 -1
  110. package/dist/shortcuts/asset/continuation.js +2 -1
  111. package/dist/shortcuts/asset/index.js +2 -0
  112. package/dist/shortcuts/asset-idle/index.js +2 -0
  113. package/dist/shortcuts/blog/continuation.js +2 -1
  114. package/dist/shortcuts/blog/index.js +2 -0
  115. package/dist/shortcuts/caizhilian/continuation.js +2 -1
  116. package/dist/shortcuts/caizhilian/index.js +2 -0
  117. package/dist/shortcuts/caizhilian/operations/confirm.js +3 -2
  118. package/dist/shortcuts/calendar/continuation.js +2 -1
  119. package/dist/shortcuts/calendar/index.js +2 -0
  120. package/dist/shortcuts/calendar/operations/write.js +1 -1
  121. package/dist/shortcuts/contract/continuation.js +2 -1
  122. package/dist/shortcuts/contract/index.js +2 -0
  123. package/dist/shortcuts/contract/operations/write.js +2 -1
  124. package/dist/shortcuts/cowork/continuation.js +2 -1
  125. package/dist/shortcuts/cowork/index.js +2 -0
  126. package/dist/shortcuts/ebuilder-form/continuation.js +2 -1
  127. package/dist/shortcuts/ebuilder-form/index.js +2 -0
  128. package/dist/shortcuts/ebuilder-form/operations/write.js +3 -2
  129. package/dist/shortcuts/ehr/continuation.js +2 -1
  130. package/dist/shortcuts/ehr/index.js +2 -0
  131. package/dist/shortcuts/ehr/operations/attend-write.js +1 -1
  132. package/dist/shortcuts/ehr/operations/recruit-candidate-import.js +182 -3
  133. package/dist/shortcuts/ehr/operations/recruit-position.js +134 -2
  134. package/dist/shortcuts/ehr/operations/recruit-write.js +1 -1
  135. package/dist/shortcuts/esb/continuation.js +2 -1
  136. package/dist/shortcuts/esb/index.js +2 -0
  137. package/dist/shortcuts/esb/operations/trigger.js +2 -1
  138. package/dist/shortcuts/fna/continuation.js +2 -1
  139. package/dist/shortcuts/fna/index.js +2 -0
  140. package/dist/shortcuts/fna/operations/invoice-writeoff.js +1 -1
  141. package/dist/shortcuts/fna/operations/loan.js +1 -1
  142. package/dist/shortcuts/hrm/index.js +2 -0
  143. package/dist/shortcuts/im/continuation.js +2 -1
  144. package/dist/shortcuts/index.js +5 -0
  145. package/dist/shortcuts/invoice/continuation.js +2 -1
  146. package/dist/shortcuts/invoice/index.js +14 -15
  147. package/dist/shortcuts/invoice/invoice-record.js +93 -0
  148. package/dist/shortcuts/invoice/manifest.js +190 -393
  149. package/dist/shortcuts/invoice/operations/add.js +2 -1
  150. package/dist/shortcuts/invoice/operations/delete.js +2 -1
  151. package/dist/shortcuts/invoice/operations/import.js +2 -1
  152. package/dist/shortcuts/invoice/operations/issuing-contract-detail.js +86 -0
  153. package/dist/shortcuts/invoice/operations/issuing-contracts.js +210 -0
  154. package/dist/shortcuts/invoice/operations/registry.js +17 -17
  155. package/dist/shortcuts/invoice/operations/reim-auto.js +4 -569
  156. package/dist/shortcuts/invoice/operations/reim.js +52 -341
  157. package/dist/shortcuts/invoice/operations/shared.js +21 -4
  158. package/dist/shortcuts/invoice/operations/update.js +2 -1
  159. package/dist/shortcuts/invoice/projection.js +10 -62
  160. package/dist/shortcuts/jiuchuanhui/continuation.js +2 -1
  161. package/dist/shortcuts/jiuchuanhui/index.js +2 -0
  162. package/dist/shortcuts/jiuchuanhui/operations/datajson.js +2 -1
  163. package/dist/shortcuts/jiuchuanhui/operations/esb.js +2 -1
  164. package/dist/shortcuts/mail/continuation.js +2 -1
  165. package/dist/shortcuts/mail/index.js +2 -0
  166. package/dist/shortcuts/mail/operations/mail-blacklist.js +1 -1
  167. package/dist/shortcuts/mail/operations/mail-contacts.js +1 -1
  168. package/dist/shortcuts/mail/operations/mail-send.js +1 -1
  169. package/dist/shortcuts/mail/operations/mail-sign.js +1 -1
  170. package/dist/shortcuts/mail/operations/mail-template.js +1 -1
  171. package/dist/shortcuts/meeting/continuation.js +2 -1
  172. package/dist/shortcuts/meeting/index.js +2 -0
  173. package/dist/shortcuts/meeting/operations/change.js +1 -1
  174. package/dist/shortcuts/meeting/operations/create.js +1 -1
  175. package/dist/shortcuts/meeting/operations/eb/create-flow.js +16 -7
  176. package/dist/shortcuts/meeting/operations/eb/decision.js +1 -1
  177. package/dist/shortcuts/meeting/operations/eb/factory.js +1 -1
  178. package/dist/shortcuts/meeting/operations/lifecycle.js +1 -1
  179. package/dist/shortcuts/meeting/operations/receipts.js +1 -1
  180. package/dist/shortcuts/meeting/operations/signs.js +1 -1
  181. package/dist/shortcuts/okr/continuation.js +2 -1
  182. package/dist/shortcuts/okr/index.js +2 -0
  183. package/dist/shortcuts/okr/operations/write.js +1 -1
  184. package/dist/shortcuts/plan/continuation.js +2 -1
  185. package/dist/shortcuts/plan/index.js +2 -0
  186. package/dist/shortcuts/plan/operations/write.js +1 -1
  187. package/dist/shortcuts/project/continuation.js +2 -1
  188. package/dist/shortcuts/project/index.js +2 -0
  189. package/dist/shortcuts/reception/constants.js +53 -0
  190. package/dist/shortcuts/reception/errors.js +54 -0
  191. package/dist/shortcuts/reception/host.js +125 -0
  192. package/dist/shortcuts/reception/index.js +198 -0
  193. package/dist/shortcuts/reception/manifest.js +177 -0
  194. package/dist/shortcuts/reception/operations/ask.js +71 -0
  195. package/dist/shortcuts/reception/operations/browsertool.js +58 -0
  196. package/dist/shortcuts/reception/operations/compose.js +129 -0
  197. package/dist/shortcuts/reception/operations/customparams.js +74 -0
  198. package/dist/shortcuts/reception/operations/doc.js +238 -0
  199. package/dist/shortcuts/reception/operations/docrender.js +36 -0
  200. package/dist/shortcuts/reception/operations/panels.js +179 -0
  201. package/dist/shortcuts/reception/operations/registry.js +26 -0
  202. package/dist/shortcuts/reception/operations/render-assets.js +184 -0
  203. package/dist/shortcuts/reception/operations/render.js +123 -0
  204. package/dist/shortcuts/reception/operations/runs.js +38 -0
  205. package/dist/shortcuts/reception/operations/schedule.js +127 -0
  206. package/dist/shortcuts/reception/operations/shared.js +196 -0
  207. package/dist/shortcuts/reception/operations/snapshot.js +68 -0
  208. package/dist/shortcuts/reception/operations/types.js +1 -0
  209. package/dist/shortcuts/reception/operations.js +33 -0
  210. package/dist/shortcuts/reception/upload.js +218 -0
  211. package/dist/shortcuts/recruit-stage/context.js +145 -33
  212. package/dist/shortcuts/recruit-stage/continuation.js +2 -1
  213. package/dist/shortcuts/recruit-stage/operations/jd-create.js +106 -17
  214. package/dist/shortcuts/recruit-stage/operations/resume-import.js +166 -10
  215. package/dist/shortcuts/workflow/continuation.js +2 -1
  216. package/dist/shortcuts/workflow/index.js +2 -0
  217. package/dist/shortcuts/workflow/operations/form.js +32 -8
  218. package/dist/shortcuts/workflow/operations/write.js +1 -1
  219. package/docs/_catalog.md +3 -0
  220. package/docs/agent-invoice.md +1 -1
  221. package/docs/archive-oa.md +1 -1
  222. package/docs/caizhilian.md +1 -1
  223. package/docs/calendar.md +1 -1
  224. package/docs/contract.md +1 -1
  225. package/docs/e10-auth.md +16 -0
  226. package/docs/ehr.md +2 -2
  227. package/docs/esb.md +1 -1
  228. package/docs/im.md +1 -1
  229. package/docs/invoice.md +8 -12
  230. package/docs/okr.md +1 -1
  231. package/docs/reception.md +119 -0
  232. package/package.json +1 -1
  233. package/scripts/clean.mjs +43 -2
  234. package/skill-template/business-info.json +18 -2
  235. package/skill-template/domains/caizhilian.md +1 -1
  236. package/skill-template/domains/reception-flow.md +18 -0
  237. package/skill-template/domains/yepiaotong.md +4 -7
  238. package/skills/weaver-e10-archive-oa/references/source-manifest.json +14 -14
  239. package/skills/weaver-e10-blog/references/blog-publish.md +1 -1
  240. package/skills/weaver-e10-blog/references/source-manifest.json +7 -7
  241. package/skills/weaver-e10-caizhilian/references/source-manifest.json +21 -21
  242. package/skills/weaver-e10-caizhilian/references/write-protocol.md +2 -2
  243. package/skills/weaver-e10-calendar/references/calendar-write.md +1 -1
  244. package/skills/weaver-e10-cowork/SKILL.md +1 -1
  245. package/skills/weaver-e10-ebuilder-form/SKILL.md +1 -1
  246. package/skills/weaver-e10-ebuilder-form/references/custom-api.md +1 -1
  247. package/skills/weaver-e10-ebuilder-form/references/openapi-write.md +1 -1
  248. package/skills/weaver-e10-esb/SKILL.md +2 -2
  249. package/skills/weaver-e10-esb/references/source-manifest.json +22 -22
  250. package/skills/weaver-e10-esb/references/trigger.md +2 -2
  251. package/skills/weaver-e10-jinchengda/references/contract-clause-library-crud.md +1 -1
  252. package/skills/weaver-e10-jinchengda/references/contract-clause-reference-save.md +1 -1
  253. package/skills/weaver-e10-jinchengda/references/contract-request-write.md +1 -1
  254. package/skills/weaver-e10-jinchengda/references/source-manifest.json +29 -29
  255. package/skills/weaver-e10-jucailin/SKILL.md +1 -1
  256. package/skills/weaver-e10-jucailin/references/attend-write.md +2 -2
  257. package/skills/weaver-e10-jucailin/references/recruit-create.md +12 -3
  258. package/skills/weaver-e10-jucailin/references/recruit-write.md +1 -1
  259. package/skills/weaver-e10-meeting/SKILL.md +8 -6
  260. package/skills/weaver-e10-meeting/references/meeting-change.md +1 -1
  261. package/skills/weaver-e10-meeting/references/meeting-create.md +1 -1
  262. package/skills/weaver-e10-meeting/references/meeting-lifecycle.md +1 -1
  263. package/skills/weaver-e10-meeting/references/meeting-verification.md +1 -1
  264. package/skills/weaver-e10-okr/references/okr-align.md +1 -1
  265. package/skills/weaver-e10-okr/references/okr-keyresult.md +1 -1
  266. package/skills/weaver-e10-okr/references/okr-write.md +1 -1
  267. package/skills/weaver-e10-okr/references/source-manifest.json +8 -8
  268. package/skills/weaver-e10-plan/references/plan-report-write.md +1 -1
  269. package/skills/weaver-e10-plan/references/source-manifest.json +20 -20
  270. package/skills/weaver-e10-qiyecheng/references/loan-management.md +1 -1
  271. package/skills/weaver-e10-qiyecheng/references/source-manifest.json +18 -18
  272. package/skills/weaver-e10-reception-flow/SKILL.md +173 -0
  273. package/skills/weaver-e10-reception-flow/assets//350/241/214/347/250/213/345/215/225/346/250/241/346/235/277-/346/263/233/345/276/256.docx +0 -0
  274. package/skills/weaver-e10-reception-flow/data/fields-snapshot.json +213 -0
  275. package/skills/weaver-e10-reception-flow/references/browsertool.md +68 -0
  276. package/skills/weaver-e10-reception-flow/references/env-pitfalls.md +51 -0
  277. package/skills/weaver-e10-reception-flow/references/fields-snapshot.md +227 -0
  278. package/skills/weaver-e10-reception-flow/references/guide.md +179 -0
  279. package/skills/weaver-e10-reception-flow/scripts/locate.sh +14 -0
  280. package/skills/weaver-e10-reception-flow/scripts/render.py +724 -0
  281. package/skills/weaver-e10-recruit-stage/SKILL.md +9 -5
  282. package/skills/weaver-e10-recruit-stage/lib/recruit-xiaoe-file.mjs +1 -1
  283. package/skills/weaver-e10-recruit-stage/lib/xiaoe-session.mjs +66 -0
  284. package/skills/weaver-e10-recruit-stage/references/position-templates.md +202 -0
  285. package/skills/weaver-e10-recruit-stage/references/recruit-jd-create.md +22 -0
  286. package/skills/weaver-e10-recruit-stage/references/recruit-resume-import.md +14 -1
  287. package/skills/weaver-e10-shared/references/e10-auth-and-session.md +6 -0
  288. package/skills/weaver-e10-shijingran/SKILL.md +5 -5
  289. package/skills/weaver-e10-shijingran/references/source-manifest.json +37 -36
  290. package/skills/weaver-e10-skill-maker/references/module-cli-generation.md +2 -0
  291. package/skills/weaver-e10-wenshuding/references/source-manifest.json +3 -3
  292. package/skills/weaver-e10-workflow/references/source-manifest.json +32 -32
  293. package/skills/weaver-e10-yepiaotong/SKILL.md +19 -26
  294. package/skills/weaver-e10-yepiaotong/references/invoice-detail.md +13 -10
  295. package/skills/weaver-e10-yepiaotong/references/invoice-enterprise-list.md +2 -0
  296. package/skills/weaver-e10-yepiaotong/references/invoice-issuing-workflow.md +194 -155
  297. package/skills/weaver-e10-yepiaotong/references/invoice-output-view.md +28 -32
  298. package/skills/weaver-e10-yepiaotong/references/invoice-personal-list.md +5 -1
  299. package/skills/weaver-e10-yepiaotong/references/invoice-reim.md +8 -10
  300. package/skills/weaver-e10-yepiaotong/references/reim-api-reference.md +211 -616
  301. package/skills/weaver-e10-yepiaotong/references/reim-examples.md +149 -117
  302. package/skills/weaver-e10-yepiaotong/references/reim-expense-subject-rules.md +17 -20
  303. package/skills/weaver-e10-yepiaotong/references/reim-form-fill-rules.md +20 -39
  304. package/skills/weaver-e10-yepiaotong/references/reim-matching-rules.md +55 -22
  305. package/skills/weaver-e10-yepiaotong/references/reim-phone-subsidy-rules.md +7 -17
  306. package/skills/weaver-e10-yepiaotong/references/reim-workflow.md +88 -92
  307. package/skills/weaver-e10-yepiaotong/references/source-manifest.json +144 -354
  308. package/skills/weaver-e10-yimiaoban/SKILL.md +1 -1
  309. package/skills/weaver-e10-yimiaoban/references/msg-write.md +1 -1
  310. package/skills/weaver-e10-yimiaoban/references/safety-boundaries.md +1 -1
  311. package/skills/weaver-e10-yimiaoban/references/source-manifest.json +7 -7
  312. package/dist/chunks/chunk-TTPJJJC4.js +0 -465
  313. package/dist/chunks/registry-BKBZPBAJ.js +0 -23
  314. package/dist/shortcuts/invoice/markdown.js +0 -172
  315. package/dist/shortcuts/invoice/operations/issuing-qys.js +0 -424
  316. package/skills/weaver-e10-meeting.zip +0 -0
  317. package/skills/weaver-e10-yepiaotong/references/invoice-issuing-examples.md +0 -131
  318. package/skills/weaver-e10-yepiaotong/references/invoice-issuing-form-fill-rules.md +0 -179
@@ -5,6 +5,7 @@ import { CliError, ExitCode } from '../../../core/errors.js';
5
5
  import { clearInvoiceTokenForSession } from '../../../shortcuts/invoice/host.js';
6
6
  import { buildE10CookieHeader, E10AuthSession, clearProfileAuthFile, extractRawSetCookie, extractSessionTicket, findAuthFile, getActiveProfile, getProfileAuthPath, getProfileDir, listProfiles, profileNameFromUrl, readProfileConfig, readTeamsCheckUserInfo, saveAuthFile, saveProfileConfig, setActiveProfile, switchActiveProfile, } from './session.js';
7
7
  import { getE10AuthRoot } from './paths.js';
8
+ import { appendXiaoEAuthErrorLog, clearXiaoEAuthErrorLog, getXiaoEAuthErrorLogPath, normalizeXiaoEAuthErrorLogLimit, readXiaoEAuthErrorLog, xiaoEAuthLogSecrets, } from './error-log.js';
8
9
  import { XIAOE_AGENT_TYPE, createXiaoEUnifiedLoginUnavailableError, hasXiaoEEnv, inspectXiaoEUnifiedLoginSources, resolveXiaoEPreferredBaseUrl, tryXiaoEUnifiedLogin as tryXiaoEUnifiedSessionLogin, } from './xiaoe.js';
9
10
  export { DEFAULT_E10_BASE_URL, XIAOE_AGENT_TYPE, hasXiaoEEnv, hasXiaoETokenScript, hasXiaoEUnifiedLoginSource, inspectXiaoEUnifiedLoginSources, resolveXiaoEDefaultBaseUrl, resolveXiaoEPreferredBaseUrl, resolveXiaoEUnifiedLoginCredential, } from './xiaoe.js';
10
11
  const DEFAULT_AGENT_TYPE = 'weaver-work-cli';
@@ -385,7 +386,7 @@ async function saveEteamsIdLogin(input) {
385
386
  version: input.version || '',
386
387
  };
387
388
  }
388
- async function tryXiaoEUnifiedLogin(ctx, baseUrl, tenantKeyFallback, profileHint, allowTokenScript = false) {
389
+ async function tryXiaoEUnifiedLogin(ctx, baseUrl, tenantKeyFallback, profileHint, allowTokenScript = false, diagnostics) {
389
390
  const login = await tryXiaoEUnifiedSessionLogin({
390
391
  env: ctx.env,
391
392
  baseUrl,
@@ -394,6 +395,7 @@ async function tryXiaoEUnifiedLogin(ctx, baseUrl, tenantKeyFallback, profileHint
394
395
  profileHint,
395
396
  allowTokenScript,
396
397
  logger: ctx.logger,
398
+ diagnostics,
397
399
  });
398
400
  return login?.result || null;
399
401
  }
@@ -529,6 +531,15 @@ async function runXiaoELogin(ctx, options) {
529
531
  const useXiaoELogin = xiaoESources.any;
530
532
  const baseUrl = preferredXiaoEBaseUrl;
531
533
  const tenantKey = optionString(commandOpts, 'tenantKey');
534
+ const diagnostics = {
535
+ attemptedSteps: [],
536
+ baseUrl,
537
+ clientType: xiaoESources.clientType,
538
+ platformCredentialDetected: xiaoESources.platformCredential,
539
+ };
540
+ if (!useXiaoELogin) {
541
+ diagnostics.attemptedSteps.push('platform_token:missing', 'bundled_env_script:missing', xiaoESources.clientType === 'cloud' ? 'token_script:disabled' : 'token_script:missing', xiaoESources.clientType === 'cloud' ? 'client_session:disabled' : 'client_session:missing', 'environment_map:empty');
542
+ }
532
543
  ctx.logger.info([
533
544
  'XiaoE unified login preflight:',
534
545
  'authMode=xiaoe',
@@ -542,12 +553,34 @@ async function runXiaoELogin(ctx, options) {
542
553
  `baseUrl=${baseUrl || '(unresolved)'}`,
543
554
  ].join(' '));
544
555
  if (useXiaoELogin) {
545
- const xiaoEResult = await tryXiaoEUnifiedLogin(ctx, baseUrl, tenantKey, profileFromGlobal, true);
546
- if (xiaoEResult)
547
- return xiaoEResult;
556
+ try {
557
+ const xiaoEResult = await tryXiaoEUnifiedLogin(ctx, baseUrl, tenantKey, profileFromGlobal, true, diagnostics);
558
+ if (xiaoEResult)
559
+ return xiaoEResult;
560
+ }
561
+ catch (error) {
562
+ await appendXiaoEAuthErrorLog({
563
+ source: 'login',
564
+ profile: profileFromGlobal || getActiveProfile(),
565
+ baseUrl,
566
+ diagnostics,
567
+ error,
568
+ secrets: xiaoEAuthLogSecrets(ctx.env),
569
+ }).catch((logError) => ctx.logger.debug(`Could not persist XiaoE auth error log: ${logError instanceof Error ? logError.message : String(logError)}`));
570
+ throw error;
571
+ }
548
572
  }
549
573
  ctx.logger.warn(xiaoEUnifiedLoginUnavailableMessage(baseUrl, useXiaoELogin));
550
- throw createXiaoEUnifiedLoginUnavailableError(baseUrl);
574
+ const error = createXiaoEUnifiedLoginUnavailableError(baseUrl);
575
+ await appendXiaoEAuthErrorLog({
576
+ source: 'login',
577
+ profile: profileFromGlobal || getActiveProfile(),
578
+ baseUrl,
579
+ diagnostics,
580
+ error,
581
+ secrets: xiaoEAuthLogSecrets(ctx.env),
582
+ }).catch((logError) => ctx.logger.debug(`Could not persist XiaoE auth error log: ${logError instanceof Error ? logError.message : String(logError)}`));
583
+ throw error;
551
584
  }
552
585
  async function runBrowserLogin(ctx, options) {
553
586
  const commandOpts = asOptions(options);
@@ -768,7 +801,78 @@ function formatWhoami(title, data) {
768
801
  'User-Agent: ' + (data.userAgent || ''),
769
802
  ].join('\n');
770
803
  }
771
- function registerBrowserLoginCommand(auth, action, name, description) {
804
+ function formatXiaoEAuthErrorLogEntry(entry) {
805
+ const lines = [
806
+ `[${entry.timestamp}] ${entry.source} id=${entry.id}`,
807
+ ...(entry.profile ? [`profile: ${entry.profile}`] : []),
808
+ ...(entry.baseUrl ? [`baseUrl: ${entry.baseUrl}`] : []),
809
+ ...(entry.clientType ? [`clientType: ${entry.clientType}`] : []),
810
+ ...(entry.attemptedSteps.length ? [`attemptedSteps: ${entry.attemptedSteps.join(', ')}`] : []),
811
+ ...(entry.lastError ? [`lastError: ${entry.lastError}`] : []),
812
+ ...(entry.resultSessionExpired ? ['resultSessionExpired: true'] : []),
813
+ ...(entry.error ? [`error: ${entry.error.type}/${entry.error.subtype}: ${entry.error.message}`] : []),
814
+ ];
815
+ for (const failure of entry.failures || []) {
816
+ lines.push([
817
+ `failure: ${failure.stage}/${failure.kind}`,
818
+ failure.causeCode ? `causeCode=${failure.causeCode}` : '',
819
+ failure.httpStatus === undefined ? '' : `httpStatus=${failure.httpStatus}`,
820
+ failure.message,
821
+ ].filter(Boolean).join(' '));
822
+ }
823
+ return lines.join('\n');
824
+ }
825
+ async function showXiaoEAuthErrorLogs(ctx, options) {
826
+ const commandOpts = asOptions(options);
827
+ let limit;
828
+ try {
829
+ limit = normalizeXiaoEAuthErrorLogLimit(commandOpts.limit);
830
+ }
831
+ catch (error) {
832
+ throw new CliError(error instanceof Error ? error.message : String(error), ExitCode.UsageError);
833
+ }
834
+ const result = await readXiaoEAuthErrorLog(limit);
835
+ const text = result.entries.length
836
+ ? [
837
+ `XiaoE auth error logs (${result.returned}/${result.total}, newest first)`,
838
+ `logFile: ${result.path}`,
839
+ ...(result.invalidLines ? [`invalidLines: ${result.invalidLines}`] : []),
840
+ '',
841
+ result.entries.map(formatXiaoEAuthErrorLogEntry).join('\n\n'),
842
+ ].join('\n')
843
+ : [
844
+ 'No XiaoE auth error logs.',
845
+ `logFile: ${result.path}`,
846
+ ...(result.invalidLines ? [`invalidLines: ${result.invalidLines}`] : []),
847
+ ].join('\n');
848
+ ctx.output.write(result, { text });
849
+ }
850
+ function registerXiaoEAuthLogCommands(auth, action) {
851
+ const logs = auth.command('logs')
852
+ .description('View or clear persisted XiaoE authentication error logs')
853
+ .option('--limit <n>', 'number of recent entries to show (1-500)', '50')
854
+ .action(action(showXiaoEAuthErrorLogs));
855
+ logs.command('show')
856
+ .description('Show persisted XiaoE authentication error logs')
857
+ .option('--limit <n>', 'number of recent entries to show (1-500)', '50')
858
+ .action(action(showXiaoEAuthErrorLogs));
859
+ logs.command('path')
860
+ .description('Print the XiaoE authentication error log path')
861
+ .action(action((ctx) => {
862
+ const path = getXiaoEAuthErrorLogPath();
863
+ ctx.output.write({ path }, { text: path });
864
+ }));
865
+ logs.command('clear')
866
+ .description('Clear persisted XiaoE authentication error logs')
867
+ .action(action(async (ctx) => {
868
+ const result = await clearXiaoEAuthErrorLog();
869
+ const text = result.cleared
870
+ ? `Cleared XiaoE auth error logs.\nlogFile: ${result.path}`
871
+ : `No XiaoE auth error logs to clear.\nlogFile: ${result.path}`;
872
+ ctx.output.write(result, { text });
873
+ }));
874
+ }
875
+ function registerBrowserLoginCommand(auth, action, name, description, machine = false) {
772
876
  const command = auth.command(name)
773
877
  .description(description)
774
878
  .option('--base-url <url>', 'E10 base URL')
@@ -778,8 +882,28 @@ function registerBrowserLoginCommand(auth, action, name, description) {
778
882
  .option('--agent-type <value>', 'Alias of --agent_type')
779
883
  .option('--agent-return-url <url>', 'Desktop application URL linked by the login success page');
780
884
  command.action(action(async (ctx, options) => {
781
- const result = await runBrowserLogin(ctx, options);
782
- ctx.output.write(result, { text: formatLoginResult(result) });
885
+ if (!machine) {
886
+ const result = await runBrowserLogin(ctx, options);
887
+ ctx.output.write(result, { text: formatLoginResult(result) });
888
+ return;
889
+ }
890
+ // 平台型连接器契约:stdout 只出严格 JSON,进度与授权链接走 stderr。
891
+ ctx.logger.machineMode = true;
892
+ try {
893
+ const result = await runBrowserLogin(ctx, options);
894
+ ctx.output.raw(JSON.stringify({
895
+ status: 'authorized',
896
+ employeeId: result.userId || '',
897
+ tenantKey: result.tenantKey || '',
898
+ }));
899
+ }
900
+ catch (error) {
901
+ ctx.output.raw(JSON.stringify({ status: 'unauthorized' }));
902
+ throw error;
903
+ }
904
+ finally {
905
+ ctx.logger.machineMode = false;
906
+ }
783
907
  }));
784
908
  }
785
909
  function registerXiaoELoginCommand(auth, action) {
@@ -847,6 +971,35 @@ export function registerE10AuthCommands(parent, action) {
847
971
  };
848
972
  ctx.output.write(status, { text: formatAuthStatus(status) });
849
973
  }));
974
+ auth.command('show')
975
+ .description('Platform contract: print login status as {"status":"authorized"|"unauthorized"}')
976
+ .option('--status', 'print only the strict JSON status object')
977
+ .option('--no-check', 'skip remote session validity check')
978
+ .action(action(async (ctx, options) => {
979
+ const opts = ctx.getGlobalOptions();
980
+ const commandOpts = asOptions(options);
981
+ const authFile = findAuthFile(ctx.cwd, opts);
982
+ const session = authFile ? E10AuthSession.fromFile(authFile, opts.baseUrl, opts.passportUrl) : null;
983
+ const profile = opts.profile || getActiveProfile();
984
+ const expired = session ? session.isExpired() : false;
985
+ // 三态探活:只有明确失效(401/403)才算未授权,网络异常保持乐观,避免逼用户重复登录。
986
+ const probe = session && !expired && commandOpts.check !== false
987
+ ? await session.probeValid()
988
+ : undefined;
989
+ const authorized = Boolean(session) && !expired && probe !== false;
990
+ if (commandOpts.status === true) {
991
+ ctx.output.raw(JSON.stringify({ status: authorized ? 'authorized' : 'unauthorized' }));
992
+ return;
993
+ }
994
+ ctx.output.write({
995
+ status: authorized ? 'authorized' : 'unauthorized',
996
+ loggedIn: Boolean(session),
997
+ expired,
998
+ reachable: probe,
999
+ profile,
1000
+ baseUrl: session ? session.getBaseUrl() : '',
1001
+ }, { json: true });
1002
+ }));
850
1003
  auth.command('set')
851
1004
  .description('Save E10 auth from an ETEAMSID cookie')
852
1005
  .requiredOption('--eteamsid <id>', 'ETEAMSID cookie value')
@@ -882,7 +1035,9 @@ export function registerE10AuthCommands(parent, action) {
882
1035
  }));
883
1036
  registerBrowserLoginCommand(auth, action, 'login', 'Open browser OAuth2.0 login and save E10 auth');
884
1037
  registerBrowserLoginCommand(auth, action, 'oidc', 'Alias of auth login for OAuth2.0 browser login');
1038
+ registerBrowserLoginCommand(auth, action, 'init', 'Platform contract alias of auth login: stdout is strict JSON {"status":"authorized"}', true);
885
1039
  registerXiaoELoginCommand(auth, action);
1040
+ registerXiaoEAuthLogCommands(auth, action);
886
1041
  auth.command('logout')
887
1042
  .alias('clear')
888
1043
  .description('Clear saved E10 auth for the current or selected profile')
@@ -0,0 +1,182 @@
1
+ import { randomUUID } from 'node:crypto';
2
+ import { appendFile, chmod, mkdir, readFile, unlink } from 'node:fs/promises';
3
+ import { dirname, resolve } from 'node:path';
4
+ import { toErrorEnvelope } from '../../../core/errors.js';
5
+ import { getE10AuthRoot } from './paths.js';
6
+ const XIAOE_AUTH_ERROR_LOG_NAME = 'xiaoe-auth-errors.ndjson';
7
+ const DEFAULT_LOG_LIMIT = 50;
8
+ export const MAX_XIAOE_AUTH_ERROR_LOG_LIMIT = 500;
9
+ /**
10
+ * The log lives beside the CLI-owned E10 profiles, never beside a caller-owned
11
+ * `--auth` file. Keeping the target fixed also makes the clear command safe.
12
+ */
13
+ export function getXiaoEAuthErrorLogPath() {
14
+ return resolve(getE10AuthRoot(), 'logs', XIAOE_AUTH_ERROR_LOG_NAME);
15
+ }
16
+ export function xiaoEAuthLogSecrets(env) {
17
+ return Object.entries(env)
18
+ .filter(([key, value]) => Boolean(value
19
+ && (key.startsWith('XIAOE_') || key.startsWith('WEAVER_XIAOE_'))
20
+ && /(?:TOKEN|AUTH|ETEAMSID|COOKIE|SESSION|SECRET|PASSWORD)/iu.test(key)))
21
+ .map(([, value]) => value);
22
+ }
23
+ function redactSensitiveText(value, secrets = []) {
24
+ let text = value;
25
+ for (const secret of secrets) {
26
+ if (secret && secret.length >= 6)
27
+ text = text.split(secret).join('<redacted>');
28
+ }
29
+ return text
30
+ // Query strings regularly carry temporary tickets. The path is enough for diagnostics.
31
+ .replace(/(https?:\/\/[^\s?#]+)\?[^\s#]*/giu, '$1?<redacted>')
32
+ .replace(/\b(Bearer\s+)[A-Za-z0-9._~+/=-]+/giu, '$1<redacted>')
33
+ .replace(/((?:eteamsid|access[_-]?token|refresh[_-]?token|auth(?:orization)?|cookie|session[_-]?id|secret|password)\s*[:=]\s*)(["']?)[^\s,;}"']+/giu, '$1$2<redacted>')
34
+ .replace(/(["'](?:eteamsid|access[_-]?token|refresh[_-]?token|authorization|cookie|session[_-]?id|secret|password)["']\s*:\s*["'])[^"']*(["'])/giu, '$1<redacted>$2')
35
+ // Opaque credentials that were not labelled by the producer.
36
+ .replace(/\b[A-Za-z0-9_-]{48,}\b/gu, '<redacted>');
37
+ }
38
+ function sanitizeBaseUrl(value, secrets) {
39
+ if (!value)
40
+ return undefined;
41
+ try {
42
+ const url = new URL(value);
43
+ url.username = '';
44
+ url.password = '';
45
+ url.search = '';
46
+ url.hash = '';
47
+ return redactSensitiveText(url.toString().replace(/\/$/u, ''), secrets);
48
+ }
49
+ catch {
50
+ return redactSensitiveText(value, secrets);
51
+ }
52
+ }
53
+ function sanitizeFailure(failure, secrets) {
54
+ return {
55
+ stage: failure.stage,
56
+ kind: failure.kind,
57
+ message: redactSensitiveText(failure.message, secrets),
58
+ ...(failure.causeCode ? { causeCode: redactSensitiveText(failure.causeCode, secrets) } : {}),
59
+ ...(failure.httpStatus === undefined ? {} : { httpStatus: failure.httpStatus }),
60
+ };
61
+ }
62
+ function sanitizeError(error, secrets) {
63
+ if (error === undefined)
64
+ return undefined;
65
+ const envelope = toErrorEnvelope(error);
66
+ return {
67
+ ...envelope,
68
+ message: redactSensitiveText(envelope.message, secrets),
69
+ // Error details can contain arbitrary server payloads. The normalized
70
+ // diagnostics fields above are the only details persisted to disk.
71
+ ...(envelope.details === undefined ? {} : { details: '<omitted from persistent auth log>' }),
72
+ };
73
+ }
74
+ function createEntry(input) {
75
+ const secrets = input.secrets || [];
76
+ const diagnostics = input.diagnostics;
77
+ const baseUrl = sanitizeBaseUrl(input.baseUrl || diagnostics?.baseUrl, secrets);
78
+ const lastError = diagnostics?.lastError
79
+ ? redactSensitiveText(diagnostics.lastError, secrets)
80
+ : undefined;
81
+ const failures = diagnostics?.failures?.map((failure) => sanitizeFailure(failure, secrets));
82
+ const error = sanitizeError(input.error, secrets);
83
+ return {
84
+ schemaVersion: 1,
85
+ id: randomUUID(),
86
+ timestamp: new Date().toISOString(),
87
+ source: input.source,
88
+ ...(input.profile ? { profile: redactSensitiveText(input.profile, secrets) } : {}),
89
+ ...(baseUrl ? { baseUrl } : {}),
90
+ ...(diagnostics?.clientType ? { clientType: diagnostics.clientType } : {}),
91
+ ...(diagnostics?.platformCredentialDetected === undefined
92
+ ? {}
93
+ : { platformCredentialDetected: diagnostics.platformCredentialDetected }),
94
+ attemptedSteps: (diagnostics?.attemptedSteps || []).map((step) => redactSensitiveText(step, secrets)),
95
+ ...(lastError ? { lastError } : {}),
96
+ ...(failures?.length ? { failures } : {}),
97
+ ...(input.resultSessionExpired ? { resultSessionExpired: true } : {}),
98
+ ...(error ? { error } : {}),
99
+ };
100
+ }
101
+ /**
102
+ * Append-only persistence keeps concurrent CLI processes from overwriting one
103
+ * another. A logging failure is returned to the caller and must never replace
104
+ * the original authentication error.
105
+ */
106
+ export async function appendXiaoEAuthErrorLog(input) {
107
+ const path = getXiaoEAuthErrorLogPath();
108
+ await mkdir(dirname(path), { recursive: true, mode: 0o700 });
109
+ await chmod(dirname(path), 0o700).catch(() => undefined);
110
+ const entry = createEntry(input);
111
+ await appendFile(path, `${JSON.stringify(entry)}\n`, { encoding: 'utf8', mode: 0o600 });
112
+ // Existing files may have been created under a permissive umask.
113
+ await chmod(path, 0o600).catch(() => undefined);
114
+ return entry;
115
+ }
116
+ function isLogEntry(value) {
117
+ if (!value || typeof value !== 'object' || Array.isArray(value))
118
+ return false;
119
+ const candidate = value;
120
+ return candidate.schemaVersion === 1
121
+ && typeof candidate.id === 'string'
122
+ && typeof candidate.timestamp === 'string'
123
+ && (candidate.source === 'login' || candidate.source === 'recovery')
124
+ && Array.isArray(candidate.attemptedSteps);
125
+ }
126
+ export function normalizeXiaoEAuthErrorLogLimit(value) {
127
+ if (value === undefined || value === null || value === '')
128
+ return DEFAULT_LOG_LIMIT;
129
+ const limit = Number(value);
130
+ if (!Number.isInteger(limit) || limit < 1 || limit > MAX_XIAOE_AUTH_ERROR_LOG_LIMIT) {
131
+ throw new RangeError(`limit must be an integer between 1 and ${MAX_XIAOE_AUTH_ERROR_LOG_LIMIT}`);
132
+ }
133
+ return limit;
134
+ }
135
+ export async function readXiaoEAuthErrorLog(limit = DEFAULT_LOG_LIMIT) {
136
+ const normalizedLimit = normalizeXiaoEAuthErrorLogLimit(limit);
137
+ const path = getXiaoEAuthErrorLogPath();
138
+ let content = '';
139
+ try {
140
+ content = await readFile(path, 'utf8');
141
+ }
142
+ catch (error) {
143
+ if (error?.code !== 'ENOENT')
144
+ throw error;
145
+ }
146
+ let invalidLines = 0;
147
+ const entries = [];
148
+ for (const line of content.split(/\r?\n/u)) {
149
+ if (!line.trim())
150
+ continue;
151
+ try {
152
+ const value = JSON.parse(line);
153
+ if (isLogEntry(value))
154
+ entries.push(value);
155
+ else
156
+ invalidLines += 1;
157
+ }
158
+ catch {
159
+ invalidLines += 1;
160
+ }
161
+ }
162
+ const recent = entries.slice(-normalizedLimit).reverse();
163
+ return {
164
+ path,
165
+ total: entries.length,
166
+ returned: recent.length,
167
+ invalidLines,
168
+ entries: recent,
169
+ };
170
+ }
171
+ export async function clearXiaoEAuthErrorLog() {
172
+ const path = getXiaoEAuthErrorLogPath();
173
+ try {
174
+ await unlink(path);
175
+ return { path, cleared: true };
176
+ }
177
+ catch (error) {
178
+ if (error?.code === 'ENOENT')
179
+ return { path, cleared: false };
180
+ throw error;
181
+ }
182
+ }
@@ -478,7 +478,14 @@ export class E10AuthSession {
478
478
  clear();
479
479
  }
480
480
  }
481
- async checkValid() {
481
+ /**
482
+ * 三态探活:`true` 明确有效、`false` 明确失效(401/403)、`undefined` 无法判定(网络/5xx)。
483
+ *
484
+ * 为什么要和 `checkValid()` 分开:平台连接器判断"是否已登录"时,
485
+ * 把网络抖动当成"未登录"会逼用户重复登录;而把 401 当成"已登录"会让后续业务全失败。
486
+ * 未认定失效时保持乐观,明确失效才降级。
487
+ */
488
+ async probeValid() {
482
489
  const { signal, clear } = createTimeoutSignal(E10_TEAMS_CHECK_TIMEOUT_MS);
483
490
  try {
484
491
  const resp = await fetch(`${this.getBaseUrl()}/api/ecode/tree/list?parentId=0`, {
@@ -491,15 +498,22 @@ export class E10AuthSession {
491
498
  redirect: 'manual',
492
499
  signal,
493
500
  });
494
- return resp.status === 200;
501
+ if (resp.status === 200)
502
+ return true;
503
+ if (resp.status === 401 || resp.status === 403)
504
+ return false;
505
+ return undefined;
495
506
  }
496
507
  catch {
497
- return false;
508
+ return undefined;
498
509
  }
499
510
  finally {
500
511
  clear();
501
512
  }
502
513
  }
514
+ async checkValid() {
515
+ return (await this.probeValid()) === true;
516
+ }
503
517
  async ensureValid() {
504
518
  if (await this.checkValid())
505
519
  return true;
@@ -1,5 +1,6 @@
1
1
  import { isXiaoERuntimeAgent } from '../../core/runtime-agent.js';
2
2
  import { getActiveProfile, readProfileConfig } from './auth/session.js';
3
+ import { appendXiaoEAuthErrorLog, xiaoEAuthLogSecrets } from './auth/error-log.js';
3
4
  import { hasXiaoEEnv, resolveXiaoEPreferredBaseUrl, tryXiaoEUnifiedLogin, } from './auth/xiaoe.js';
4
5
  const AUTH_REQUIRED_CODES = new Set(['-2', '401']);
5
6
  const AUTH_REQUIRED_MARKERS = [
@@ -242,6 +243,10 @@ function recoveryLogger(ctx) {
242
243
  warn: (message) => adapter.debug(message),
243
244
  };
244
245
  }
246
+ function reportAuthLogWriteFailure(ctx, error) {
247
+ const logger = ctx.logger;
248
+ logger?.debug?.(`Could not persist XiaoE auth error log: ${error instanceof Error ? error.message : String(error)}`);
249
+ }
245
250
  /**
246
251
  * Silently recover a stale or missing XiaoE session. Without a local session,
247
252
  * current runtime evidence is required before obtaining credentials.
@@ -278,18 +283,40 @@ export async function recoverXiaoEAuthSessionWithDiagnostics(ctx, currentSession
278
283
  return existing;
279
284
  const diagnostics = { attemptedSteps: [] };
280
285
  const recovery = (async () => {
281
- const login = await tryXiaoEUnifiedLogin({
282
- env: ctx.env,
283
- baseUrl,
284
- profileBaseUrl: baseUrl,
285
- allowBundledEnvScript: true,
286
- allowTokenScript: true,
287
- tenantKeyFallback: currentSession?.tenantKey || config.tenantKey,
288
- profileHint: profile,
289
- diagnostics,
290
- logger: recoveryLogger(ctx),
291
- });
292
- return { session: login?.session || null, diagnostics };
286
+ try {
287
+ const login = await tryXiaoEUnifiedLogin({
288
+ env: ctx.env,
289
+ baseUrl,
290
+ profileBaseUrl: baseUrl,
291
+ allowBundledEnvScript: true,
292
+ allowTokenScript: true,
293
+ tenantKeyFallback: currentSession?.tenantKey || config.tenantKey,
294
+ profileHint: profile,
295
+ diagnostics,
296
+ logger: recoveryLogger(ctx),
297
+ });
298
+ if (!login) {
299
+ await appendXiaoEAuthErrorLog({
300
+ source: 'recovery',
301
+ profile,
302
+ baseUrl,
303
+ diagnostics,
304
+ secrets: xiaoEAuthLogSecrets(ctx.env),
305
+ }).catch((error) => reportAuthLogWriteFailure(ctx, error));
306
+ }
307
+ return { session: login?.session || null, diagnostics };
308
+ }
309
+ catch (error) {
310
+ await appendXiaoEAuthErrorLog({
311
+ source: 'recovery',
312
+ profile,
313
+ baseUrl,
314
+ diagnostics,
315
+ error,
316
+ secrets: xiaoEAuthLogSecrets(ctx.env),
317
+ }).catch((logError) => reportAuthLogWriteFailure(ctx, logError));
318
+ throw error;
319
+ }
293
320
  })();
294
321
  recoveryInFlight.set(key, recovery);
295
322
  try {
@@ -1,7 +1,8 @@
1
1
  import { CliError, ExitCode } from '../../core/errors.js';
2
2
  import { E10_AUTH_REQUIRED_MESSAGE, E10_XIAOE_HOST_CREDENTIAL_MISSING_MESSAGE, E10_XIAOE_NETWORK_UNAVAILABLE_MESSAGE, E10_XIAOE_RECOVERY_FAILED_MESSAGE, } from './auth/messages.js';
3
3
  import { lastXiaoEFailure, summarizeXiaoEFailureKind, } from './auth/xiaoe.js';
4
- import { E10AuthSession } from './auth/session.js';
4
+ import { appendXiaoEAuthErrorLog, xiaoEAuthLogSecrets } from './auth/error-log.js';
5
+ import { E10AuthSession, getActiveProfile } from './auth/session.js';
5
6
  import { E10ApiClient } from './client.js';
6
7
  import { canAutomaticallyRecoverXiaoE, recoverXiaoEAuthSession, recoverXiaoEAuthSessionWithDiagnostics, } from './auth-recovery.js';
7
8
  /**
@@ -57,12 +58,26 @@ export async function getE10Session(ctx, load = {}) {
57
58
  return E10AuthSession.fromOptions(options, ctx.cwd, load);
58
59
  }
59
60
  export async function requireE10Session(ctx, load = {}) {
61
+ const options = ctx.getGlobalOptions();
60
62
  let session = await getE10Session(ctx, load);
61
63
  if (session?.isExpired() && canAutomaticallyRecoverXiaoE(ctx, session)) {
62
64
  const outcome = await recoverXiaoEAuthSessionWithDiagnostics(ctx, session).catch(() => null);
63
65
  session = outcome?.session || null;
64
66
  if (!session || session.isExpired()) {
65
- throw xiaoERecoveryFailedError(outcome?.diagnostics, session?.isExpired() === true);
67
+ const resultSessionExpired = session?.isExpired() === true;
68
+ const error = xiaoERecoveryFailedError(outcome?.diagnostics, resultSessionExpired);
69
+ if (resultSessionExpired) {
70
+ await appendXiaoEAuthErrorLog({
71
+ source: 'recovery',
72
+ profile: options.profile || getActiveProfile(),
73
+ baseUrl: session?.getBaseUrl(),
74
+ diagnostics: outcome?.diagnostics,
75
+ resultSessionExpired: true,
76
+ error,
77
+ secrets: xiaoEAuthLogSecrets(ctx.env),
78
+ }).catch(() => undefined);
79
+ }
80
+ throw error;
66
81
  }
67
82
  }
68
83
  if (!session && canAutomaticallyRecoverXiaoE(ctx)) {
@@ -272,6 +272,14 @@ function writeProductMetadata(target, productContent) {
272
272
  return;
273
273
  writeFileSync(resolve(target, 'product.json'), productContent, 'utf8');
274
274
  }
275
+ /**
276
+ * 拷贝白名单:整目录复制,只剔除本地依赖与系统垃圾。
277
+ *
278
+ * 历史实现把 `scripts/` 与 `assets/` 一并排除,导致带资产的技能装出来是残缺的——
279
+ * reception 缺 `scripts/render.py` 与 `assets/行程单模板-泛微.docx` 会直接跑不出 docx,
280
+ * builder 缺 `assets/dom-structure/` 也少一半能力。
281
+ * 技能包是受控的内部产物,资产就应当随包分发,因此只保留 node_modules 这一条硬排除。
282
+ */
275
283
  function shouldCopy(entry, sourceRoot, skipSkillProduct) {
276
284
  const relativePath = relative(sourceRoot, entry);
277
285
  const name = basename(entry);
@@ -282,7 +290,7 @@ function shouldCopy(entry, sourceRoot, skipSkillProduct) {
282
290
  if (name === '.DS_Store' || name.startsWith('.'))
283
291
  return false;
284
292
  const parts = relativePath.split(sep);
285
- return !parts.includes('node_modules') && !parts.includes('scripts') && !parts.includes('assets');
293
+ return !parts.includes('node_modules');
286
294
  }
287
295
  function countFiles(root) {
288
296
  let count = 0;
@@ -1,3 +1,4 @@
1
+ import { CONTINUATION_TTL_MS } from '../../core/continuation-ttl.js';
1
2
  import { createHmac, randomBytes, timingSafeEqual } from 'node:crypto';
2
3
  import { existsSync } from 'node:fs';
3
4
  import { chmod, mkdir, readFile, writeFile } from 'node:fs/promises';
@@ -35,7 +36,7 @@ function signature(payload, key) {
35
36
  }
36
37
  export function createArchiveContinuationSigner(ctx) {
37
38
  return {
38
- async issue(payload, ttlMs = 10 * 60_000) {
39
+ async issue(payload, ttlMs = CONTINUATION_TTL_MS) {
39
40
  const issuedAt = Date.now();
40
41
  const body = encode({ ...payload, issuedAt, expiresAt: issuedAt + ttlMs });
41
42
  const sig = signature(body, await loadKey(ctx));
@@ -1,6 +1,7 @@
1
1
  import { readFile, writeFile } from 'node:fs/promises';
2
2
  import { resolve } from 'node:path';
3
3
  import { ExitCode, isCliError, toErrorEnvelope } from '../../core/errors.js';
4
+ import { reportPlatformError } from '../../core/error-codes.js';
4
5
  import { formatSearchCard, formatSearchHtml, formatSearchText } from './render/search-format.js';
5
6
  import { createArchiveContinuationSigner } from './continuation.js';
6
7
  import { createArchiveHost } from './host.js';
@@ -99,6 +100,7 @@ async function executeAndPrint(ctx, operation, input) {
99
100
  ctx.output.write(successEnvelope(result), { json: true });
100
101
  }
101
102
  catch (error) {
103
+ reportPlatformError(error);
102
104
  console.error(JSON.stringify(failureEnvelope(error), null, 2));
103
105
  process.exitCode = isCliError(error) ? error.exitCode : ExitCode.GeneralError;
104
106
  }
@@ -140,6 +142,7 @@ async function executeSearchPrint(ctx, input, format, outputPath) {
140
142
  ctx.output.raw(formatSearchText(rows, meta));
141
143
  }
142
144
  catch (error) {
145
+ reportPlatformError(error);
143
146
  console.error(JSON.stringify(failureEnvelope(error), null, 2));
144
147
  process.exitCode = isCliError(error) ? error.exitCode : ExitCode.GeneralError;
145
148
  }
@@ -1,3 +1,4 @@
1
+ import { CONTINUATION_TTL_MS } from '../../../core/continuation-ttl.js';
1
2
  import { archiveConfirmationError, archiveValidationError } from '../errors.js';
2
3
  /** apply 类写操作必须显式确认。 */
3
4
  export function requireConfirm(args, action) {
@@ -11,7 +12,7 @@ export function requireConfirm(args, action) {
11
12
  * prepare 阶段签发 continuation。
12
13
  * 环境指纹(baseUrl + 登录账号)写进票据,apply 时校验,避免跨环境/跨账号复用。
13
14
  */
14
- export async function issueLease(env, action, payload, ttlMs = 10 * 60_000) {
15
+ export async function issueLease(env, action, payload, ttlMs = CONTINUATION_TTL_MS) {
15
16
  const session = await env.host.getSession();
16
17
  const continuation = await env.continuation.issue({
17
18
  operation: action,
@@ -1,3 +1,4 @@
1
+ import { CONTINUATION_TTL_MS } from '../../core/continuation-ttl.js';
1
2
  import { createHmac, randomBytes, timingSafeEqual } from 'node:crypto';
2
3
  import { existsSync } from 'node:fs';
3
4
  import { chmod, mkdir, readFile, writeFile } from 'node:fs/promises';
@@ -35,7 +36,7 @@ function signature(payload, key) {
35
36
  }
36
37
  export function createArchiveOaContinuationSigner(ctx) {
37
38
  return {
38
- async issue(payload, ttlMs = 10 * 60_000) {
39
+ async issue(payload, ttlMs = CONTINUATION_TTL_MS) {
39
40
  const issuedAt = Date.now();
40
41
  const body = encode({ ...payload, issuedAt, expiresAt: issuedAt + ttlMs });
41
42
  const sig = signature(body, await loadKey(ctx));