@webskill/sdk 0.6.0 → 0.8.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (35) hide show
  1. package/dist/agent.d.ts +2 -2
  2. package/dist/agent.js +218 -28
  3. package/dist/browser.d.ts +177 -4
  4. package/dist/browser.js +444 -35
  5. package/dist/{catalogComponents-Dr5dFMAb-Dacibl1e.js → catalogComponents-DfxxfUvn-D55Gbb2l.js} +4016 -1226
  6. package/dist/{dist-8oQRa8Xz.js → dist-59XlqDuv.js} +93 -6
  7. package/dist/{dist-DnYG2-eY.js → dist-CJqQsIm9.js} +498 -118
  8. package/dist/{dist-DusANsrn.js → dist-DmI5SBBF.js} +437 -55
  9. package/dist/eventTypes-g1BXL6x5-CibcOftR.js +37 -0
  10. package/dist/governance.d.ts +91 -11
  11. package/dist/governance.js +194 -52
  12. package/dist/{index-C-KFAZoF.d.ts → index-K-eewlGL.d.ts} +176 -75
  13. package/dist/{index-BMocOEi0.d.ts → index-P9J2LTfU.d.ts} +163 -6
  14. package/dist/{index-BuTpBMzr.d.ts → index-fLskQfAS.d.ts} +156 -5
  15. package/dist/index.d.ts +3 -3
  16. package/dist/index.js +4 -4
  17. package/dist/mcp.d.ts +129 -6
  18. package/dist/mcp.js +235 -28
  19. package/dist/{memoryArtifactStore-52Zn9npI-BMPYwvoy.js → memoryArtifactStore-52Zn9npI-upv5OWYf.js} +1 -1
  20. package/dist/node.d.ts +3 -3
  21. package/dist/node.js +4 -3
  22. package/dist/{openUiLibrary-Bdrji9qK-DzAxRlTY.js → openUiLibrary-DURlAxjk-CU6AzfSW.js} +3 -3
  23. package/dist/{skillVersionStore-BzLbzFOL-CxdAFWO2.d.ts → skillVersionStore-Bl-ElD45-gRfSaAby.d.ts} +8 -2
  24. package/dist/{testing-CYTFqkDm.js → testing-BCUO5gZR.js} +2 -2
  25. package/dist/testing.d.ts +1 -1
  26. package/dist/testing.js +2 -2
  27. package/dist/{types-4pg-qp_I-Gq63X8Oa.d.ts → types-B3n0cMZu-BdcqQ35O.d.ts} +74 -7
  28. package/dist/ui-react.d.ts +16 -7
  29. package/dist/ui-react.js +159 -108
  30. package/dist/ui-vue.d.ts +1 -1
  31. package/dist/ui-vue.js +2 -2
  32. package/dist/ui.d.ts +4 -4
  33. package/dist/ui.js +3 -3
  34. package/dist/{webskillLitCatalog-_mugzRHx-B_54vxum.js → webskillLitCatalog-DwTwSBFt-DiXXpNZA.js} +22 -3
  35. package/package.json +2 -2
package/dist/mcp.js CHANGED
@@ -1,5 +1,5 @@
1
- import { O as messageOf, h as assertRemoteUrlAllowed, m as WebSkillError } from "./dist-8oQRa8Xz.js";
2
- import { at as normalizeToolContent, et as mergeCatalogEntries } from "./dist-DusANsrn.js";
1
+ import { A as messageOf, h as assertRemoteUrlAllowed, m as WebSkillError } from "./dist-59XlqDuv.js";
2
+ import { it as mergeCatalogEntries, lt as normalizeToolContent } from "./dist-DmI5SBBF.js";
3
3
 
4
4
  //#region ../mcp/dist/index.js
5
5
  /**
@@ -182,6 +182,8 @@ const failure$1 = (code, message) => ({
182
182
  message
183
183
  }
184
184
  });
185
+ /** 需要重新授权不是「端点不可用」:压平成后者,模型和界面都会去查网络(0.7.0 FR-22.3) */
186
+ const endpointFailure = (e, message) => failure$1(e instanceof WebSkillError && e.code.startsWith("MCP_OAUTH_") ? e.code : "MCP_ENDPOINT_UNAVAILABLE", message);
185
187
  /**
186
188
  * endpoint:toolName 调用 + 工具清单缓存(TTL 默认 1s + registry 版本号双失效)。
187
189
  */
@@ -204,7 +206,7 @@ var McpToolResolver = class {
204
206
  try {
205
207
  names = await this.#toolNames(endpoint, client);
206
208
  } catch (e) {
207
- return failure$1("MCP_ENDPOINT_UNAVAILABLE", `Failed to list tools: ${messageOf(e)}`);
209
+ return endpointFailure(e, `Failed to list tools: ${messageOf(e)}`);
208
210
  }
209
211
  if (!names.has(toolName)) {
210
212
  this.#cache.delete(endpoint);
@@ -222,7 +224,7 @@ var McpToolResolver = class {
222
224
  });
223
225
  return this.#normalizeCallResult(raw);
224
226
  } catch (e) {
225
- return failure$1("MCP_ENDPOINT_UNAVAILABLE", `Tool "${toolName}" on endpoint "${endpoint}" failed: ${messageOf(e)}`);
227
+ return endpointFailure(e, `Tool "${toolName}" on endpoint "${endpoint}" failed: ${messageOf(e)}`);
226
228
  }
227
229
  }
228
230
  async #toolNames(endpoint, client) {
@@ -443,6 +445,16 @@ var ExperimentalWebMcpAdapter = class {
443
445
  const api = this.#resolveApi();
444
446
  return this.#enabled && typeof api?.executeTool === "function";
445
447
  }
448
+ isEnabled() {
449
+ return this.#enabled;
450
+ }
451
+ /**
452
+ * 宿主把开关交给用户时必须走这里:适配器是工具是否对 LLM 可见的**唯一闸门**。
453
+ * 宿主自己另存一份开关态而不同步到这里,会出现「界面上关了、模型照样能调」。
454
+ */
455
+ setEnabled(on) {
456
+ this.#enabled = on;
457
+ }
446
458
  /** 工具清单(getTools 缺失时返回 undefined;调用失败时告警后返回 undefined) */
447
459
  async listTools() {
448
460
  const api = this.#resolveApi();
@@ -565,22 +577,182 @@ var McpRuntimePlugin = class {
565
577
  };
566
578
  }
567
579
  };
580
+ /**
581
+ * 构造授权相关错误。`message` 只含端点名与阶段,`details` 只有 `{ endpoint, stage }`——
582
+ * 不带 `cause`:SDK 的错误 message 可能回显授权 URL 或 token 端点的响应体(AC-22.6)。
583
+ */
584
+ function oauthError(code, endpoint, stage, reason) {
585
+ return new WebSkillError(code, `Remote MCP endpoint "${endpoint}" ${reason} (stage: ${stage})`, {
586
+ endpoint,
587
+ stage
588
+ });
589
+ }
590
+ /** 显式的内存存储,供 examples 与测试使用。**不是缺省行为**——是宿主主动选的(AC-22.7)。 @experimental */
591
+ function createMemoryOAuthStores() {
592
+ const tokens = /* @__PURE__ */ new Map();
593
+ const handshakes = /* @__PURE__ */ new Map();
594
+ return {
595
+ tokens: {
596
+ load: (endpoint) => Promise.resolve(tokens.get(endpoint)),
597
+ save: (endpoint, value) => {
598
+ tokens.set(endpoint, value);
599
+ return Promise.resolve();
600
+ },
601
+ clear: (endpoint) => {
602
+ tokens.delete(endpoint);
603
+ return Promise.resolve();
604
+ }
605
+ },
606
+ handshake: {
607
+ load: (endpoint) => Promise.resolve(handshakes.get(endpoint)),
608
+ save: (endpoint, value) => {
609
+ handshakes.set(endpoint, value);
610
+ return Promise.resolve();
611
+ },
612
+ clear: (endpoint) => {
613
+ handshakes.delete(endpoint);
614
+ return Promise.resolve();
615
+ }
616
+ }
617
+ };
618
+ }
619
+ const randomState = () => {
620
+ const bytes = /* @__PURE__ */ new Uint8Array(16);
621
+ crypto.getRandomValues(bytes);
622
+ return [...bytes].map((b) => b.toString(16).padStart(2, "0")).join("");
623
+ };
624
+ /**
625
+ * `McpOAuthConfig` → SDK `OAuthClientProvider` 适配器。
626
+ *
627
+ * `state()` 与 `saveCodeVerifier()` 由 SDK 分两次调用(顺序上前者在先),
628
+ * 两者合成一条握手记录:谁先到都把当前已知部分写进去,回程时两项都在。
629
+ * @experimental
630
+ */
631
+ function createOAuthProvider(endpoint, config) {
632
+ const { client, tokens: tokenStore, handshake } = config;
633
+ let pending = {};
634
+ const persist = async (patch) => {
635
+ pending = {
636
+ ...pending,
637
+ ...patch
638
+ };
639
+ await handshake.save(endpoint, {
640
+ codeVerifier: pending.codeVerifier ?? "",
641
+ state: pending.state ?? ""
642
+ });
643
+ };
644
+ return {
645
+ get redirectUrl() {
646
+ return client.redirectUri;
647
+ },
648
+ get clientMetadata() {
649
+ return {
650
+ client_name: "WebSkill SDK",
651
+ redirect_uris: [client.redirectUri],
652
+ grant_types: ["authorization_code", "refresh_token"],
653
+ response_types: ["code"],
654
+ token_endpoint_auth_method: client.clientSecret === void 0 ? "none" : "client_secret_post",
655
+ ...client.scopes && client.scopes.length > 0 ? { scope: client.scopes.join(" ") } : {}
656
+ };
657
+ },
658
+ async state() {
659
+ const value = randomState();
660
+ await persist({ state: value });
661
+ return value;
662
+ },
663
+ clientInformation() {
664
+ return Promise.resolve({
665
+ client_id: client.clientId,
666
+ ...client.clientSecret !== void 0 ? { client_secret: client.clientSecret } : {}
667
+ });
668
+ },
669
+ async tokens() {
670
+ const saved = await tokenStore.load(endpoint);
671
+ if (!saved) return void 0;
672
+ return {
673
+ access_token: saved.accessToken,
674
+ token_type: saved.tokenType ?? "Bearer",
675
+ ...saved.expiresAt !== void 0 ? { expires_in: Math.max(0, Math.round((saved.expiresAt - Date.now()) / 1e3)) } : {},
676
+ ...saved.refreshToken !== void 0 ? { refresh_token: saved.refreshToken } : {},
677
+ ...saved.scope !== void 0 ? { scope: saved.scope } : {}
678
+ };
679
+ },
680
+ async saveTokens(next) {
681
+ await tokenStore.save(endpoint, {
682
+ accessToken: next.access_token,
683
+ ...next.expires_in !== void 0 ? { expiresAt: Date.now() + next.expires_in * 1e3 } : {},
684
+ ...next.refresh_token !== void 0 ? { refreshToken: next.refresh_token } : {},
685
+ ...next.token_type !== void 0 ? { tokenType: next.token_type } : {},
686
+ ...next.scope !== void 0 ? { scope: next.scope } : {}
687
+ });
688
+ },
689
+ async redirectToAuthorization(url) {
690
+ await config.openAuthorization(url);
691
+ },
692
+ async saveCodeVerifier(codeVerifier) {
693
+ await persist({ codeVerifier });
694
+ },
695
+ async codeVerifier() {
696
+ const saved = await handshake.load(endpoint);
697
+ if (!saved?.codeVerifier) throw oauthError("MCP_OAUTH_FAILED", endpoint, "exchange", "has no stored PKCE verifier for this handshake");
698
+ return saved.codeVerifier;
699
+ },
700
+ async invalidateCredentials(scope) {
701
+ if (scope === "all" || scope === "tokens") await tokenStore.clear(endpoint);
702
+ if (scope === "all" || scope === "verifier") await handshake.clear(endpoint);
703
+ }
704
+ };
705
+ }
568
706
  async function loadMcpSdk() {
569
707
  try {
570
- const [client, sse, streamable] = await Promise.all([
708
+ const [client, sse, streamable, auth, errors] = await Promise.all([
571
709
  import("@modelcontextprotocol/sdk/client/index.js"),
572
710
  import("@modelcontextprotocol/sdk/client/sse.js"),
573
- import("@modelcontextprotocol/sdk/client/streamableHttp.js")
711
+ import("@modelcontextprotocol/sdk/client/streamableHttp.js"),
712
+ import("@modelcontextprotocol/sdk/client/auth.js"),
713
+ import("@modelcontextprotocol/sdk/server/auth/errors.js")
574
714
  ]);
575
715
  return {
576
716
  Client: client.Client,
577
717
  SSEClientTransport: sse.SSEClientTransport,
578
- StreamableHTTPClientTransport: streamable.StreamableHTTPClientTransport
718
+ StreamableHTTPClientTransport: streamable.StreamableHTTPClientTransport,
719
+ UnauthorizedError: auth.UnauthorizedError,
720
+ OAuthError: errors.OAuthError
579
721
  };
580
722
  } catch (e) {
581
723
  throw new WebSkillError("MCP_ENDPOINT_UNAVAILABLE", "The \"@modelcontextprotocol/sdk\" package is required for remote MCP endpoints; install it first (npm i @modelcontextprotocol/sdk)", e);
582
724
  }
583
725
  }
726
+ /** 运行期的未授权(含刷新失败)必须在 endpoint 层转成 `WebSkillError`,否则 401 会以工具结果的形式进模型上下文 */
727
+ function wrapOAuthClient(client, endpoint, oauth, isUnauthorized) {
728
+ const guard = async (work) => {
729
+ try {
730
+ return await work();
731
+ } catch (e) {
732
+ if (!isUnauthorized(e)) throw e;
733
+ await oauth.tokens.clear(endpoint);
734
+ throw oauthError("MCP_OAUTH_REQUIRED", endpoint, "refresh", "needs authorization again");
735
+ }
736
+ };
737
+ return {
738
+ listTools: () => guard(() => client.listTools()),
739
+ callTool: (input) => guard(() => client.callTool(input)),
740
+ listPrompts: () => guard(() => client.listPrompts()),
741
+ getPrompt: (input) => guard(() => client.getPrompt(input)),
742
+ listResources: () => guard(() => client.listResources()),
743
+ readResource: (input) => guard(() => client.readResource(input))
744
+ };
745
+ }
746
+ /** 授权注入的完整性校验:缺一项就是宿主的配置错误,不是运行期授权问题(AC-22.7) */
747
+ function assertOAuthConfigured(endpoint, oauth) {
748
+ const missing = [];
749
+ if (!oauth.client?.clientId) missing.push("client.clientId");
750
+ if (!oauth.client?.redirectUri) missing.push("client.redirectUri");
751
+ if (!oauth.tokens) missing.push("tokens");
752
+ if (!oauth.handshake) missing.push("handshake");
753
+ if (typeof oauth.openAuthorization !== "function") missing.push("openAuthorization");
754
+ if (missing.length > 0) throw oauthError("MCP_OAUTH_NOT_CONFIGURED", endpoint, "discover", `is missing OAuth wiring: ${missing.join(", ")}`);
755
+ }
584
756
  /**
585
757
  * 远程 MCP endpoint 装配:SDK 官方 StreamableHTTPClientTransport(默认)/
586
758
  * SSEClientTransport(遗留)连接远端 server,注册进 EndpointRegistry——
@@ -588,7 +760,7 @@ async function loadMcpSdk() {
588
760
  * 返回 close 句柄:断开后 unregister(临时技能随既有生命周期自然消失)。
589
761
  */
590
762
  async function connectRemoteEndpoint(registry, config) {
591
- const { Client, SSEClientTransport, StreamableHTTPClientTransport } = await loadMcpSdk();
763
+ const { Client, SSEClientTransport, StreamableHTTPClientTransport, UnauthorizedError, OAuthError } = await loadMcpSdk();
592
764
  let url;
593
765
  try {
594
766
  url = new URL(config.url);
@@ -599,46 +771,81 @@ async function connectRemoteEndpoint(registry, config) {
599
771
  allowHttp: config.allowHttp ?? false,
600
772
  allowPrivateHosts: config.allowPrivateHosts ?? false
601
773
  });
774
+ const oauth = config.oauth;
775
+ if (oauth) assertOAuthConfigured(config.endpoint, oauth);
776
+ const authProvider = oauth ? createOAuthProvider(config.endpoint, oauth) : void 0;
602
777
  const requestInit = config.headers ? { headers: config.headers } : void 0;
603
- const transport = config.transport === "sse" ? new SSEClientTransport(url, { ...requestInit ? { requestInit } : {} }) : new StreamableHTTPClientTransport(url, { ...requestInit ? { requestInit } : {} });
778
+ const transportOptions = {
779
+ ...requestInit ? { requestInit } : {},
780
+ ...authProvider ? { authProvider } : {}
781
+ };
782
+ const makeTransport = () => config.transport === "sse" ? new SSEClientTransport(url, transportOptions) : new StreamableHTTPClientTransport(url, transportOptions);
604
783
  const client = new Client({
605
784
  name: "webskill-remote-client",
606
785
  version: "0.1.0"
607
786
  });
787
+ const isUnauthorized = (e) => e instanceof UnauthorizedError || e instanceof OAuthError;
608
788
  const unavailable = (e) => new WebSkillError("MCP_ENDPOINT_UNAVAILABLE", `Failed to connect remote MCP endpoint "${config.endpoint}" at ${config.url}: ${messageOf(e)}`, e);
609
- try {
789
+ let closed = false;
790
+ const close = async () => {
791
+ if (closed) return;
792
+ closed = true;
793
+ registry.unregister(config.endpoint);
794
+ try {
795
+ await client.close();
796
+ } catch (e) {
797
+ throw new WebSkillError("MCP_ENDPOINT_UNAVAILABLE", `Failed to close remote MCP endpoint "${config.endpoint}": ${messageOf(e)}`, e);
798
+ }
799
+ };
800
+ const register = () => {
801
+ try {
802
+ const entry = client;
803
+ registry.register(config.endpoint, oauth ? wrapOAuthClient(entry, config.endpoint, oauth, isUnauthorized) : entry);
804
+ } catch (e) {
805
+ client.close().catch(() => void 0);
806
+ throw unavailable(e);
807
+ }
808
+ };
809
+ const openConnection = async (transport) => {
610
810
  let connect = client.connect(transport);
611
811
  if (config.timeoutMs && config.timeoutMs > 0) {
612
812
  const timeoutMs = config.timeoutMs;
613
813
  connect = Promise.race([connect, new Promise((_resolve, reject) => setTimeout(() => reject(/* @__PURE__ */ new Error(`Connection timed out after ${timeoutMs}ms`)), timeoutMs))]);
614
814
  }
615
815
  await connect;
616
- } catch (e) {
816
+ };
817
+ const finishAuthorization = async (code, state) => {
818
+ const saved = await oauth.handshake.load(config.endpoint);
819
+ if (!saved || saved.state === "" || saved.state !== state) throw oauthError("MCP_OAUTH_FAILED", config.endpoint, "authorize", "received a mismatched authorization state");
820
+ const transport = makeTransport();
617
821
  try {
618
- await client.close();
619
- } catch {}
620
- throw unavailable(e);
621
- }
822
+ await transport.finishAuth(code);
823
+ } catch (e) {
824
+ throw oauthError(isUnauthorized(e) ? "MCP_OAUTH_REQUIRED" : "MCP_OAUTH_FAILED", config.endpoint, "exchange", "could not exchange the authorization code");
825
+ }
826
+ await oauth.handshake.clear(config.endpoint);
827
+ await openConnection(transport);
828
+ register();
829
+ };
622
830
  try {
623
- registry.register(config.endpoint, client);
831
+ await openConnection(makeTransport());
624
832
  } catch (e) {
833
+ if (oauth && isUnauthorized(e)) return {
834
+ close,
835
+ finishAuthorization,
836
+ authorizationRequired: true
837
+ };
625
838
  try {
626
839
  await client.close();
627
840
  } catch {}
628
841
  throw unavailable(e);
629
842
  }
630
- let closed = false;
631
- return { close: async () => {
632
- if (closed) return;
633
- closed = true;
634
- registry.unregister(config.endpoint);
635
- try {
636
- await client.close();
637
- } catch (e) {
638
- throw new WebSkillError("MCP_ENDPOINT_UNAVAILABLE", `Failed to close remote MCP endpoint "${config.endpoint}": ${messageOf(e)}`, e);
639
- }
640
- } };
843
+ register();
844
+ return {
845
+ close,
846
+ ...oauth ? { finishAuthorization } : {}
847
+ };
641
848
  }
642
849
 
643
850
  //#endregion
644
- export { EndpointRegistry, ExperimentalWebMcpAdapter, McpRuntimePlugin, McpToolResolver, MessageChannelTransport, TemporarySkillProvider, catalogMerge, connectRemoteEndpoint, endpointToolLlmName, parseEndpointToolLlmName, parseWebMcpToolLlmName, serveSkillAsMcp, validateJsonRpcMessage, webMcpToolLlmName };
851
+ export { EndpointRegistry, ExperimentalWebMcpAdapter, McpRuntimePlugin, McpToolResolver, MessageChannelTransport, TemporarySkillProvider, catalogMerge, connectRemoteEndpoint, createMemoryOAuthStores, createOAuthProvider, endpointToolLlmName, parseEndpointToolLlmName, parseWebMcpToolLlmName, serveSkillAsMcp, validateJsonRpcMessage, webMcpToolLlmName };
@@ -1,4 +1,4 @@
1
- import { m as WebSkillError } from "./dist-8oQRa8Xz.js";
1
+ import { m as WebSkillError } from "./dist-59XlqDuv.js";
2
2
 
3
3
  //#region ../runtime/dist/memoryArtifactStore-52Zn9npI.js
4
4
  /** 纯文本消息内容的构造快捷方式(引擎内部绝大多数消息仍是纯文本) */
package/dist/node.d.ts CHANGED
@@ -1,6 +1,6 @@
1
- import { I as JsonSchema, N as FileStat, O as ArchiveLimits, P as FileSystemProvider, U as SKILLS_LOCKFILE, W as SKILL_MANIFEST_FILE, Y as SignatureAuditSink, _t as VerifyResult, at as SkillManifest, b as UiBridge, c as InteractionResponse, dt as SkillsLockfile, ht as UnsignedPolicy, it as SkillManagerPort, pt as TrustedKeyStore, s as InteractionRequest, tt as SkillInstallSource, y as RenderResultRequest } from "./types-4pg-qp_I-Gq63X8Oa.js";
2
- import { A as FsArtifactStore, Ct as ScriptExecutionContext, J as NetworkPolicy, St as SchemaInferer, Ut as ToolResult, Vt as ToolDefinition, _ as BridgeCapabilities, f as ApprovalScope, fn as createScriptContext, j as FsMemoryStore, on as WebSkillRuntime, sn as WebSkillRuntimeDeps, wt as ScriptExecutor } from "./index-C-KFAZoF.js";
3
- import { a as AuditLog, p as CandidateStore, r as ApprovalPolicy, u as CandidateSkill, v as SkillVersionStore } from "./skillVersionStore-BzLbzFOL-CxdAFWO2.js";
1
+ import { A as ArchiveLimits, F as FileStat, G as SKILLS_LOCKFILE, I as FileSystemProvider, K as SKILL_MANIFEST_FILE, R as JsonSchema, Z as SignatureAuditSink, _t as TrustedKeyStore, at as SkillInstallSource, c as InteractionResponse, ct as SkillManagerPort, ht as SkillsLockfile, lt as SkillManifest, s as InteractionRequest, x as UiBridge, xt as VerifyResult, y as RenderResultRequest, yt as UnsignedPolicy } from "./types-B3n0cMZu-BdcqQ35O.js";
2
+ import { Et as ScriptExecutor, M as FsMemoryStore, Tt as ScriptExecutionContext, Y as NetworkPolicy, Yt as ToolResult, _ as BridgeCapabilities, f as ApprovalScope, j as FsArtifactStore, mn as WebSkillRuntimeDeps, pn as WebSkillRuntime, qt as ToolDefinition, wt as SchemaInferer, yn as createScriptContext } from "./index-K-eewlGL.js";
3
+ import { a as AuditLog, p as CandidateStore, r as ApprovalPolicy, u as CandidateSkill, v as SkillVersionStore } from "./skillVersionStore-Bl-ElD45-gRfSaAby.js";
4
4
  import { n as LlmEnvConfig, s as probeLlmCapabilities, t as LlmCapabilities } from "./env-AK3cSMEA-Dli6QU5E.js";
5
5
  import { Readable, Writable } from "node:stream";
6
6
  //#region ../node/dist/index.d.ts
package/dist/node.js CHANGED
@@ -1,6 +1,7 @@
1
- import { A as parseSkillMarkdown, B as unzipWithLimits, H as verifyManifest, I as resolveArchiveLimits, L as resolveInsideRoot, M as readResponseWithLimit, N as readSkillSignature, O as messageOf, T as isValidSkillName, U as verifySkillSignature, V as validateSkills, _ as atomicWriteText, g as assertSafePathSegment, h as assertRemoteUrlAllowed, j as parseSkillPackManifest, m as WebSkillError, o as SKILLS_LOCKFILE, r as MANIFEST_EXCLUDED_FILES, s as SKILL_MANIFEST_FILE, u as SKILL_PACK_FILE, w as exportSkills, y as buildManifest } from "./dist-8oQRa8Xz.js";
2
- import { I as WebSkillRuntime, V as createScriptContext, at as normalizeToolContent, c as CapabilityApproval, m as FsMemoryStore, nt as networkPolicyLibSource, ot as normalizeToolError, p as FsArtifactStore, st as parseBridgeRequest, z as bridgeError } from "./dist-DusANsrn.js";
1
+ import { A as messageOf, D as isValidSkillName, E as exportSkills, F as readSkillSignature, G as verifyManifest, K as verifySkillSignature, M as parseSkillMarkdown, N as parseSkillPackManifest, P as readResponseWithLimit, R as resolveArchiveLimits, U as unzipWithLimits, W as validateSkills, _ as atomicWriteText, g as assertSafePathSegment, h as assertRemoteUrlAllowed, m as WebSkillError, o as SKILLS_LOCKFILE, r as MANIFEST_EXCLUDED_FILES, s as SKILL_MANIFEST_FILE, u as SKILL_PACK_FILE, y as buildManifest, z as resolveInsideRoot } from "./dist-59XlqDuv.js";
2
+ import { B as bridgeError, H as createScriptContext, L as WebSkillRuntime, c as CapabilityApproval, dt as parseBridgeRequest, h as FsMemoryStore, lt as normalizeToolContent, m as FsArtifactStore, ot as networkPolicyLibSource, ut as normalizeToolError } from "./dist-DmI5SBBF.js";
3
3
  import { i as probeLlmCapabilities } from "./env-8cY40DXB-CGnEVZby.js";
4
+ import { t as AUDIT_EVENT_TYPES } from "./eventTypes-g1BXL6x5-CibcOftR.js";
4
5
  import { createRequire } from "node:module";
5
6
  import { unzipSync, zipSync } from "fflate";
6
7
  import { existsSync, promises, realpathSync } from "node:fs";
@@ -2259,7 +2260,7 @@ var ApprovalWorkflow = class {
2259
2260
  });
2260
2261
  await this.#store.updateStatus(candidateId, "published");
2261
2262
  await this.#audit.append({
2262
- type: "skill.published",
2263
+ type: AUDIT_EVENT_TYPES.skillPublished,
2263
2264
  target: candidate.name,
2264
2265
  actor: input.actor,
2265
2266
  data: {
@@ -1,5 +1,5 @@
1
- import { nt as uiCatalog } from "./dist-DnYG2-eY.js";
2
- import { t as CatalogNode } from "./catalogComponents-Dr5dFMAb-Dacibl1e.js";
1
+ import { ft as uiCatalog } from "./dist-CJqQsIm9.js";
2
+ import { t as CatalogNode } from "./catalogComponents-DfxxfUvn-D55Gbb2l.js";
3
3
  import { z } from "zod";
4
4
  import { Component, Fragment, createContext, useCallback, useContext, useEffect, useInsertionEffect, useMemo, useRef, useState, useSyncExternalStore } from "react";
5
5
  import { jsx, jsxs } from "react/jsx-runtime";
@@ -3761,7 +3761,7 @@ function Renderer({ response, library, isStreaming = false, onAction, onStateUpd
3761
3761
  const FormValidationContext = createContext(null);
3762
3762
 
3763
3763
  //#endregion
3764
- //#region ../ui-react/dist/openUiLibrary-Bdrji9qK.js
3764
+ //#region ../ui-react/dist/openUiLibrary-DURlAxjk.js
3765
3765
  const propsFor = (props, container) => container ? props.extend({ children: z.array(z.any()).optional() }) : props;
3766
3766
  /**
3767
3767
  * catalog 的 OpenUI 投影:`defineComponent` 复用同一份 zod schema 与描述,
@@ -1,5 +1,5 @@
1
- import { B as PageQuery, P as FileSystemProvider, Q as SkillCatalogEntry, at as SkillManifest, z as Page } from "./types-4pg-qp_I-Gq63X8Oa.js";
2
- //#region ../governance/dist/skillVersionStore-BzLbzFOL.d.ts
1
+ import { H as PageQuery, I as FileSystemProvider, V as Page, lt as SkillManifest, nt as SkillCatalogEntry } from "./types-B3n0cMZu-BdcqQ35O.js";
2
+ //#region ../governance/dist/skillVersionStore-Bl-ElD45.d.ts
3
3
  //#region src/types.d.ts
4
4
  type CandidateStatus = 'draft' | 'pending-review' | 'approved' | 'published' | 'rejected';
5
5
  /** `generated` 是 0.5.0 的技能自动生成来源(需求 12 号 AC-9.1) */
@@ -49,6 +49,12 @@ interface AuditQueryFilter {
49
49
  since?: string;
50
50
  /** 含端点(`ts <= until`) */
51
51
  until?: string;
52
+ /**
53
+ * true 时链校验失败不抛错,改为在结果里报告断点(`chainBrokenAt` / `chainReason`)。
54
+ * **仅用于人工查看的降级展示**:程序化消费方(合规导出等)拿到部分结果而不知情
55
+ * 比直接失败更危险。默认 false,保持既有行为。
56
+ */
57
+ tolerateBrokenChain?: boolean;
52
58
  }
53
59
  interface AuditLog {
54
60
  append(event: Omit<AuditEvent, 'id' | 'ts'> & {
@@ -1,5 +1,5 @@
1
- import { m as WebSkillError } from "./dist-8oQRa8Xz.js";
2
- import { a as textParts, n as partsToText } from "./memoryArtifactStore-52Zn9npI-BMPYwvoy.js";
1
+ import { m as WebSkillError } from "./dist-59XlqDuv.js";
2
+ import { a as textParts, n as partsToText } from "./memoryArtifactStore-52Zn9npI-upv5OWYf.js";
3
3
 
4
4
  //#region ../runtime/dist/testing.js
5
5
  /**
package/dist/testing.d.ts CHANGED
@@ -1,4 +1,4 @@
1
- import { _ as MemoryStore, b as UiBridge, c as InteractionResponse, l as LlmClient, m as LlmStreamEvent, n as ArtifactStore, p as LlmResponse, s as InteractionRequest, t as Artifact, u as LlmCompleteInput } from "./types-4pg-qp_I-Gq63X8Oa.js";
1
+ import { _ as MemoryStore, c as InteractionResponse, l as LlmClient, m as LlmStreamEvent, n as ArtifactStore, p as LlmResponse, s as InteractionRequest, t as Artifact, u as LlmCompleteInput, x as UiBridge } from "./types-B3n0cMZu-BdcqQ35O.js";
2
2
  import { a as loadGoogleConfigFromEnv, i as loadAnthropicConfigFromEnv, n as LlmEnvConfig, o as loadLlmConfigFromEnv, r as ProviderEnvConfig } from "./env-AK3cSMEA-Dli6QU5E.js";
3
3
  //#region ../runtime/dist/testing.d.ts
4
4
  //#region src/llm/mockLlmClient.d.ts
package/dist/testing.js CHANGED
@@ -1,5 +1,5 @@
1
- import { t as MemoryArtifactStore } from "./memoryArtifactStore-52Zn9npI-BMPYwvoy.js";
1
+ import { t as MemoryArtifactStore } from "./memoryArtifactStore-52Zn9npI-upv5OWYf.js";
2
2
  import { n as loadGoogleConfigFromEnv, r as loadLlmConfigFromEnv, t as loadAnthropicConfigFromEnv } from "./env-8cY40DXB-CGnEVZby.js";
3
- import { n as MockLlmClient, r as MockUiBridge, t as InMemoryStore } from "./testing-CYTFqkDm.js";
3
+ import { n as MockLlmClient, r as MockUiBridge, t as InMemoryStore } from "./testing-BCUO5gZR.js";
4
4
 
5
5
  export { InMemoryStore, MemoryArtifactStore, MockLlmClient, MockUiBridge, loadAnthropicConfigFromEnv, loadGoogleConfigFromEnv, loadLlmConfigFromEnv };
@@ -1,6 +1,8 @@
1
1
  //#region ../core/dist/index.d.ts
2
2
  //#region src/errors.d.ts
3
- type WebSkillErrorCode = 'FS_NOT_FOUND' | 'FS_PATH_OUTSIDE_ROOT' | 'SKILL_NOT_FOUND' | 'SKILL_INVALID_METADATA' | 'SKILL_INVALID_NAME' | 'SKILL_DUPLICATE_NAME' | 'SKILL_UNSUPPORTED_SCRIPT' | 'VALIDATION_FAILED' | 'TOOL_NOT_FOUND' | 'TOOL_EXECUTION_FAILED' | 'NETWORK_BLOCKED' | 'TOOL_UNSUPPORTED' | 'TOOL_NOT_ALLOWED' | 'TOOL_SCHEMA_UNAVAILABLE' | 'TOOL_RESOLUTION_EXHAUSTED' | 'RUN_TIMEOUT' | 'RUN_MAX_TURNS_EXCEEDED' | 'RUN_FAILED' | 'RUN_CANCELLED' | 'RUN_INTERACTION_TIMEOUT' | 'UI_UNAVAILABLE' | 'LLM_UNAVAILABLE' | 'LLM_REQUEST_FAILED' | 'INSTALL_FAILED' | 'UNINSTALL_FAILED' | 'EXPORT_FAILED' | 'INTEGRITY_FAILED' | 'FS_PERMISSION_DENIED' | 'MCP_ENDPOINT_UNAVAILABLE' | 'MCP_TOOL_NOT_FOUND' | 'CANDIDATE_INVALID' | 'APPROVAL_REQUIRED' | 'SKILL_QUARANTINED' | 'SKILL_DISABLED' | 'SKILL_UNKNOWN_ALLOWED_TOOL' | 'SKILL_UNKNOWN_DEPENDENCY' | 'SKILL_CIRCULAR_DEPENDENCY' | 'GOVERNANCE_FAILED' | 'RUN_SNAPSHOT_NOT_FOUND' | 'RUN_SNAPSHOT_EXPIRED' | 'RUN_SNAPSHOT_INCOMPATIBLE' | 'RUN_SNAPSHOT_SCHEMA_UNSUPPORTED' | 'RUN_TRACE_INCOMPATIBLE' | 'SESSION_INCOMPATIBLE' | 'SIGNATURE_MISSING' | 'SIGNATURE_MALFORMED' | 'SIGNATURE_UNTRUSTED_KEY' | 'SIGNATURE_MISMATCH' | 'SIGNATURE_UNSUPPORTED' | 'MCP_STDIO_SPAWN_FAILED' | 'MCP_STDIO_EXITED' | 'MCP_STDIO_TIMEOUT' | 'TS_RESOURCE_URL_REJECTED' | 'TS_TRANSPILER_UNAVAILABLE' | 'TS_TRANSPILE_FAILED' | 'TODO_LIST_INVALID' | 'TODO_ITEM_NOT_FOUND' | 'SKILL_GENERATION_DISABLED' | 'SKILL_GENERATION_LIMIT_EXCEEDED' | 'SKILL_GENERATION_VALIDATION_FAILED' | 'DELEGATION_UNAVAILABLE' | 'DELEGATION_IN_PROGRESS' | 'DELEGATION_BUDGET_EXCEEDED' | 'PROFILE_IMPORT_INVALID' | 'PROFILE_IMPORT_VERSION_UNSUPPORTED' | 'PROFILE_IMPORT_CREDENTIAL_REJECTED' | 'PROFILE_KEY_UNAVAILABLE' | 'DICTATION_UNAVAILABLE' | 'DICTATION_PERMISSION_DENIED' | 'DICTATION_FAILED' | 'PERCEPTION_NOT_ENABLED' | 'PERCEPTION_FAILED' | 'MODEL_IMAGE_UNSUPPORTED' | 'MODEL_TOOLS_UNSUPPORTED' | 'ATTACHMENT_TOO_LARGE' | 'ATTACHMENT_TYPE_REJECTED';
3
+ type WebSkillErrorCode = 'FS_NOT_FOUND' | 'FS_PATH_OUTSIDE_ROOT' | 'SKILL_NOT_FOUND' | 'SKILL_INVALID_METADATA' | 'SKILL_INVALID_NAME' | 'SKILL_DUPLICATE_NAME' | 'SKILL_UNSUPPORTED_SCRIPT' | 'SKILL_MANIFEST_PROTECTED' | 'VALIDATION_FAILED' | 'TOOL_NOT_FOUND' | 'TOOL_EXECUTION_FAILED' | 'NETWORK_BLOCKED' | 'TOOL_UNSUPPORTED' | 'TOOL_NOT_ALLOWED' | 'TOOL_SCHEMA_UNAVAILABLE' | 'TOOL_RESOLUTION_EXHAUSTED' | 'RUN_TIMEOUT' | 'RUN_MAX_TURNS_EXCEEDED' | 'RUN_FAILED' | 'RUN_CANCELLED' | 'RUN_INTERACTION_TIMEOUT' |
4
+ /** 历史里有未应答的工具调用,但当初为何中断已无从得知(分册 11 读取侧补齐) */
5
+ 'RUN_INTERRUPTED' | 'UI_UNAVAILABLE' | 'LLM_UNAVAILABLE' | 'LLM_REQUEST_FAILED' | 'INSTALL_FAILED' | 'UNINSTALL_FAILED' | 'EXPORT_FAILED' | 'INTEGRITY_FAILED' | 'FS_PERMISSION_DENIED' | 'MCP_ENDPOINT_UNAVAILABLE' | 'MCP_TOOL_NOT_FOUND' | 'CANDIDATE_INVALID' | 'APPROVAL_REQUIRED' | 'SKILL_QUARANTINED' | 'SKILL_DISABLED' | 'SKILL_UNKNOWN_ALLOWED_TOOL' | 'SKILL_UNKNOWN_DEPENDENCY' | 'SKILL_CIRCULAR_DEPENDENCY' | 'GOVERNANCE_FAILED' | 'RUN_SNAPSHOT_NOT_FOUND' | 'RUN_SNAPSHOT_EXPIRED' | 'RUN_SNAPSHOT_INCOMPATIBLE' | 'RUN_SNAPSHOT_SCHEMA_UNSUPPORTED' | 'RUN_TRACE_INCOMPATIBLE' | 'SESSION_INCOMPATIBLE' | 'SIGNATURE_MISSING' | 'SIGNATURE_MALFORMED' | 'SIGNATURE_UNTRUSTED_KEY' | 'SIGNATURE_MISMATCH' | 'SIGNATURE_UNSUPPORTED' | 'MCP_STDIO_SPAWN_FAILED' | 'MCP_STDIO_EXITED' | 'MCP_STDIO_TIMEOUT' | 'MCP_OAUTH_REQUIRED' | 'MCP_OAUTH_FAILED' | 'MCP_OAUTH_NOT_CONFIGURED' | 'PAGE_ACTION_OUT_OF_SCOPE' | 'PAGE_ACTION_STALE_REF' | 'PAGE_ACTION_DECLINED' | 'TS_RESOURCE_URL_REJECTED' | 'TS_TRANSPILER_UNAVAILABLE' | 'TS_TRANSPILE_FAILED' | 'TODO_LIST_INVALID' | 'TODO_ITEM_NOT_FOUND' | 'SKILL_GENERATION_DISABLED' | 'SKILL_GENERATION_LIMIT_EXCEEDED' | 'SKILL_GENERATION_VALIDATION_FAILED' | 'DELEGATION_UNAVAILABLE' | 'DELEGATION_IN_PROGRESS' | 'DELEGATION_BUDGET_EXCEEDED' | 'PROFILE_IMPORT_INVALID' | 'PROFILE_IMPORT_VERSION_UNSUPPORTED' | 'PROFILE_IMPORT_CREDENTIAL_REJECTED' | 'PROFILE_KEY_UNAVAILABLE' | 'DICTATION_UNAVAILABLE' | 'DICTATION_PERMISSION_DENIED' | 'DICTATION_FAILED' | 'PERCEPTION_NOT_ENABLED' | 'PERCEPTION_FAILED' | 'MODEL_IMAGE_UNSUPPORTED' | 'MODEL_TOOLS_UNSUPPORTED' | 'ATTACHMENT_TOO_LARGE' | 'ATTACHMENT_TYPE_REJECTED';
4
6
  /**
5
7
  * 所有公开 API 抛出的结构化错误,code 供上层可编程处理
6
8
  * @stable
@@ -471,6 +473,36 @@ declare function checkDependencyCycles(adjacency: Map<string, string[]>): {
471
473
  involved: Set<string>;
472
474
  };
473
475
  //#endregion
476
+ //#region src/skill/archiveShape.d.ts
477
+ /**
478
+ * 归档的三种合法形态。本轮 bug 的成因是「安装认三种、预览只认扁平」,
479
+ * 抽出后不允许再分叉(设计 19 §2.1)。
480
+ */
481
+ type SkillArchiveShape = 'pack-set' | 'flat' | 'nested-single' | 'invalid';
482
+ interface SkillArchiveDetection {
483
+ shape: SkillArchiveShape;
484
+ /** nested-single 时的顶层目录名(不含尾部斜杠),其余形态为 undefined */
485
+ rootDir?: string;
486
+ /** 无法判定时的原因,面向调用方,英文 */
487
+ reason?: string;
488
+ }
489
+ /**
490
+ * 按归档条目表判定包结构。
491
+ *
492
+ * 入参是条目表而不是文件系统:预览侧只有解压后的 entries,没有落盘的目录。
493
+ * 只看路径,不读内容——内容合法性由 checkSkillRules 负责,两者不重叠。
494
+ */
495
+ declare function detectSkillArchiveShape(entries: Iterable<string>): SkillArchiveDetection;
496
+ /** nested-single 时剥掉顶层目录,其余形态原样返回 */
497
+ declare function stripArchiveRoot<T>(entries: Record<string, T>, detection: SkillArchiveDetection): Record<string, T>;
498
+ /**
499
+ * 文件系统入口:安装管线拿到的是解压后的目录,不是条目表。
500
+ *
501
+ * 只探测判定所需的少量路径(不递归全量列举),再交给上面的纯函数——
502
+ * 判定规则仍然只有一份,这正是 S7 的目的。
503
+ */
504
+ declare function detectSkillArchiveShapeFromFs(fs: FileSystemProvider, contentDir: string): Promise<SkillArchiveDetection>;
505
+ //#endregion
474
506
  //#region src/skill/skillPack.d.ts
475
507
  /**
476
508
  * 技能包集(skill pack)格式与打包逻辑(node/browser 共用单一来源):
@@ -529,7 +561,9 @@ interface DiscoveryResult {
529
561
  }
530
562
  declare class SkillDiscovery {
531
563
  #private;
532
- constructor(fs: FileSystemProvider, roots: string[]);
564
+ constructor(fs: FileSystemProvider, roots: string[], options?: {
565
+ extraKnownSkillNames?: readonly string[];
566
+ });
533
567
  discover(): Promise<DiscoveryResult>;
534
568
  catalog(): Promise<{
535
569
  catalog: SkillCatalog;
@@ -548,8 +582,13 @@ interface ValidationReport {
548
582
  /**
549
583
  * 合规校验。内部直接复用 SkillDiscovery 的扫描逻辑,
550
584
  * 规则判定同样落在 checkSkillRules 单一来源上。
585
+ *
586
+ * `extraKnownSkillNames`:扫描范围之外已存在的技能名。安装时只扫刚解出来的那一个目录,
587
+ * 不告诉它库里还有谁,任何指向包外的 dependencies 都会被判成不存在。
551
588
  */
552
- declare function validateSkills(fs: FileSystemProvider, roots: string[]): Promise<ValidationReport>;
589
+ declare function validateSkills(fs: FileSystemProvider, roots: string[], options?: {
590
+ extraKnownSkillNames?: readonly string[];
591
+ }): Promise<ValidationReport>;
553
592
  //#endregion
554
593
  //#region src/skill/reader.d.ts
555
594
  /** 按技能名读取技能根目录内的文件,全部读取强制经过路径安全检查 */
@@ -582,7 +621,7 @@ declare function escapeXml(text: string): string;
582
621
  declare function renderAvailableSkillsXml(catalog: SkillCatalog): string;
583
622
  declare const xmlRenderer: CatalogRenderer;
584
623
  //#endregion
585
- //#region ../runtime/dist/types-4pg-qp_I.d.ts
624
+ //#region ../runtime/dist/types-B3n0cMZu.d.ts
586
625
  //#region src/llm/streamTypes.d.ts
587
626
  /** 流式 LLM 事件(OpenAI SSE / Vercel fullStream 统一映射) */
588
627
  type LlmStreamEvent = {
@@ -681,6 +720,25 @@ interface ArtifactStore {
681
720
  listArtifacts(runId: string): Promise<Artifact[]>;
682
721
  }
683
722
  //#endregion
723
+ //#region src/skillGeneration/candidateMarker.d.ts
724
+ /**
725
+ * 一个已提交待审批的技能候选。字段固定为 `{ id, name }`——
726
+ * 这条通道只用来把候选交接给界面,扩字段要走 AC-G12 登记。
727
+ * @experimental
728
+ */
729
+ interface SkillCandidateMarker {
730
+ id: string;
731
+ name: string;
732
+ }
733
+ /**
734
+ * `$skillCandidate` 约定的形状校验:JSON content 的 data 含合法 `$skillCandidate` 键 → 候选载荷。
735
+ *
736
+ * 与 `$chart` / `$todo` / `$surface` 同一条既有通道,是第四个。
737
+ * 候选的生成与存储全部在 `@webskill/agent`,runtime 只认这个形状,畸形忽略不炸。
738
+ * @experimental
739
+ */
740
+ declare function extractSkillCandidate(data: unknown): SkillCandidateMarker | undefined;
741
+ //#endregion
684
742
  //#region src/interaction/types.d.ts
685
743
  /**
686
744
  * 交互的发起方标识(FR-11.6)。串行委派下父 agent 与子 agent 都能发起交互,
@@ -743,7 +801,7 @@ type InteractionRequest = {
743
801
  */
744
802
  type: 'authorize';
745
803
  id: string;
746
- capability: 'readReference' | 'writeArtifact' | 'confirm';
804
+ capability: 'readReference' | 'writeArtifact' | 'confirm' | 'pageAction';
747
805
  message: string;
748
806
  details?: unknown;
749
807
  });
@@ -801,6 +859,12 @@ interface RenderResultRequest {
801
859
  summary?: string;
802
860
  blocks: RenderBlock[];
803
861
  artifacts?: Artifact[];
862
+ /**
863
+ * 引擎注入的「最终输出」markdown block 在 `blocks` 中的下标;未注入时缺省。
864
+ * 消费方据此剔除与消息正文重复的那一块,**不得改用正文字符串比较**。
865
+ * 技能作者自己产出的 block 不在此字段的范围内。
866
+ */
867
+ outputBlockIndex?: number;
804
868
  }
805
869
  /** A user action exposed by a generative UI surface. @experimental */
806
870
  interface UiSpecActionCapability {
@@ -894,13 +958,16 @@ interface UiBridge {
894
958
  requestSurfaceAction?(input: UiSurfaceActionRequest): Promise<UiSurfaceActionResponse>;
895
959
  /** Best-effort cleanup when a surface action wait times out or is cancelled. @experimental */
896
960
  cancelSurfaceAction?(nonce: string): void | Promise<void>;
961
+ /** 已提交待审批的技能候选(`$skillCandidate` 载荷);未实现时候选只存在于工具返回值里。 @experimental */
962
+ onSkillCandidate?(runId: string, candidate: SkillCandidateMarker): void | Promise<void>;
897
963
  /** 流式文本增量(流式 LLM 路径下由 AgentLoop 转发) */
898
964
  onTextDelta?(runId: string, delta: string): Promise<void> | void;
899
965
  }
900
966
  interface FormField {
901
967
  name: string;
902
968
  label: string;
903
- type: 'text' | 'number' | 'boolean' | 'select' | 'textarea' | 'file';
969
+ /** `password` 的值不进 paramHistory、不进行为记录、不落会话(FR-23.7) */
970
+ type: 'text' | 'number' | 'boolean' | 'select' | 'textarea' | 'file' | 'password';
904
971
  required?: boolean;
905
972
  description?: string;
906
973
  defaultValue?: unknown;
@@ -942,4 +1009,4 @@ interface MemoryStore {
942
1009
  transaction?<T>(scope: string, fn: (inner: MemoryStore) => Promise<T>): Promise<T>;
943
1010
  }
944
1011
  //#endregion
945
- export { SkillDiscovery as $, CryptoKeyLike as A, isValidSkillName as At, PageQuery as B, renderCatalogJson as Bt, UiSpecEvent as C, buildCatalog as Ct, UiSurfaceActionResponse as D, computeDigest as Dt, UiSurfaceActionRequest as E, checkSkillRules as Et, FsTrustedKeyStore as F, parseSkillMarkdown as Ft, SKILL_NAME_MAX_LENGTH as G, unzipWithLimits as Gt, SIGNATURE_SCHEMA_VERSION as H, resolveInsideRoot as Ht, JsonSchema as I, parseSkillPackManifest as It, SKILL_SIGNATURE_FILE as J, verifySkillSignature as Jt, SKILL_NAME_PATTERN as K, validateSkills as Kt, MANIFEST_EXCLUDED_FILES as L, readResponseWithLimit as Lt, DiscoveryResult as M, keyIdOf as Mt, FileStat as N, messageOf as Nt, ArchiveLimits as O, escapeXml as Ot, FileSystemProvider as P, normalizePath as Pt, SkillCatalogEntry as Q, MemoryFS as R, readSkillSignature as Rt, UiSpecDrafts as S, atomicWriteText as St, UiSpecSnapshot as T, checkDependencyCycles as Tt, SKILLS_LOCKFILE as U, signSkill as Ut, RemoteUrlPolicy as V, resolveArchiveLimits as Vt, SKILL_MANIFEST_FILE as W, signaturePayloadBytes as Wt, SignatureVerdict as X, SignatureAuditSink as Y, xmlRenderer as Yt, SkillCatalog as Z, MemoryStore as _, VerifyResult as _t, InteractionOrigin as a, SkillManifest as at, UiBridge as b, assertRemoteUrlAllowed as bt, InteractionResponse as c, SkillReader as ct, LlmContentPart as d, SkillsLockfile as dt, SkillDocument as et, LlmMessage as f, TrustedKey as ft, LlmToolSpec as g, ValidationReport as gt, LlmToolCall as h, UnsignedPolicy as ht, FormField as i, SkillManagerPort as it, DEFAULT_ARCHIVE_LIMITS as j, jsonRenderer as jt, CatalogRenderer as k, exportSkills as kt, LlmClient as l, SkillSignature as lt, LlmStreamEvent as m, UiSpecNode as mt, ArtifactStore as n, SkillIssue as nt, InteractionPolicy as o, SkillMetadata as ot, LlmResponse as p, TrustedKeyStore as pt, SKILL_PACK_FILE as q, verifyManifest as qt, ChartSpec as r, SkillLocation as rt, InteractionRequest as s, SkillPackManifest as st, Artifact as t, SkillInstallSource as tt, LlmCompleteInput as u, SkillSource as ut, RenderBlock as v, WebSkillError as vt, UiSpecPatch as w, buildManifest as wt, UiSpecActionCapability as x, assertSafePathSegment as xt, RenderResultRequest as y, WebSkillErrorCode as yt, Page as z, renderAvailableSkillsXml as zt };
1012
+ export { SkillArchiveDetection as $, validateSkills as $t, ArchiveLimits as A, checkSkillRules as At, MemoryFS as B, normalizePath as Bt, UiSpecDrafts as C, WebSkillErrorCode as Ct, UiSurfaceActionRequest as D, buildCatalog as Dt, UiSpecSnapshot as E, atomicWriteText as Et, FileStat as F, exportSkills as Ft, SKILLS_LOCKFILE as G, renderAvailableSkillsXml as Gt, PageQuery as H, parseSkillPackManifest as Ht, FileSystemProvider as I, isValidSkillName as It, SKILL_NAME_PATTERN as J, resolveInsideRoot as Jt, SKILL_MANIFEST_FILE as K, renderCatalogJson as Kt, FsTrustedKeyStore as L, jsonRenderer as Lt, CryptoKeyLike as M, detectSkillArchiveShape as Mt, DEFAULT_ARCHIVE_LIMITS as N, detectSkillArchiveShapeFromFs as Nt, UiSurfaceActionResponse as O, buildManifest as Ot, DiscoveryResult as P, escapeXml as Pt, SignatureVerdict as Q, unzipWithLimits as Qt, JsonSchema as R, keyIdOf as Rt, UiSpecActionCapability as S, WebSkillError as St, UiSpecPatch as T, assertSafePathSegment as Tt, RemoteUrlPolicy as U, readResponseWithLimit as Ut, Page as V, parseSkillMarkdown as Vt, SIGNATURE_SCHEMA_VERSION as W, readSkillSignature as Wt, SKILL_SIGNATURE_FILE as X, signaturePayloadBytes as Xt, SKILL_PACK_FILE as Y, signSkill as Yt, SignatureAuditSink as Z, stripArchiveRoot as Zt, MemoryStore as _, TrustedKeyStore as _t, InteractionOrigin as a, SkillInstallSource as at, SkillCandidateMarker as b, ValidationReport as bt, InteractionResponse as c, SkillManagerPort as ct, LlmContentPart as d, SkillPackManifest as dt, verifyManifest as en, SkillArchiveShape as et, LlmMessage as f, SkillReader as ft, LlmToolSpec as g, TrustedKey as gt, LlmToolCall as h, SkillsLockfile as ht, FormField as i, SkillDocument as it, CatalogRenderer as j, computeDigest as jt, extractSkillCandidate as k, checkDependencyCycles as kt, LlmClient as l, SkillManifest as lt, LlmStreamEvent as m, SkillSource as mt, ArtifactStore as n, xmlRenderer as nn, SkillCatalogEntry as nt, InteractionPolicy as o, SkillIssue as ot, LlmResponse as p, SkillSignature as pt, SKILL_NAME_MAX_LENGTH as q, resolveArchiveLimits as qt, ChartSpec as r, SkillDiscovery as rt, InteractionRequest as s, SkillLocation as st, Artifact as t, verifySkillSignature as tn, SkillCatalog as tt, LlmCompleteInput as u, SkillMetadata as ut, RenderBlock as v, UiSpecNode as vt, UiSpecEvent as w, assertRemoteUrlAllowed as wt, UiBridge as x, VerifyResult as xt, RenderResultRequest as y, UnsignedPolicy as yt, MANIFEST_EXCLUDED_FILES as z, messageOf as zt };