skybridge 0.0.0-dev.e31f406 → 0.0.0-dev.e3e0986

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 (132) hide show
  1. package/README.md +122 -0
  2. package/dist/src/server/index.d.ts +2 -0
  3. package/dist/src/server/inferUtilityTypes.d.ts +33 -0
  4. package/dist/src/server/inferUtilityTypes.js +2 -0
  5. package/dist/src/server/inferUtilityTypes.js.map +1 -0
  6. package/dist/src/server/server.d.ts +14 -7
  7. package/dist/src/server/server.js +20 -7
  8. package/dist/src/server/server.js.map +1 -1
  9. package/dist/src/server/templateHelper.d.ts +9 -8
  10. package/dist/src/server/templateHelper.js +0 -8
  11. package/dist/src/server/templateHelper.js.map +1 -1
  12. package/dist/src/server/templates/development.hbs +1 -0
  13. package/dist/src/server/templates/production.hbs +3 -2
  14. package/dist/src/test/utils.js +1 -1
  15. package/dist/src/test/utils.js.map +1 -1
  16. package/dist/src/test/widget.test.js +23 -2
  17. package/dist/src/test/widget.test.js.map +1 -1
  18. package/dist/src/web/hooks/index.d.ts +14 -0
  19. package/dist/src/web/hooks/index.js +15 -0
  20. package/dist/src/web/hooks/index.js.map +1 -0
  21. package/dist/src/web/hooks/use-call-tool.d.ts +62 -0
  22. package/dist/src/web/{use-call-tool.js → hooks/use-call-tool.js} +28 -4
  23. package/dist/src/web/hooks/use-call-tool.js.map +1 -0
  24. package/dist/src/web/hooks/use-call-tool.test.js +163 -0
  25. package/dist/src/web/hooks/use-call-tool.test.js.map +1 -0
  26. package/dist/src/web/hooks/use-display-mode.d.ts +4 -0
  27. package/dist/src/web/hooks/use-display-mode.js +7 -0
  28. package/dist/src/web/hooks/use-display-mode.js.map +1 -0
  29. package/dist/src/web/hooks/use-display-mode.test.js +40 -0
  30. package/dist/src/web/hooks/use-display-mode.test.js.map +1 -0
  31. package/dist/src/web/hooks/use-files.d.ts +10 -0
  32. package/dist/src/web/hooks/use-files.js +7 -0
  33. package/dist/src/web/hooks/use-files.js.map +1 -0
  34. package/dist/src/web/hooks/use-files.test.d.ts +1 -0
  35. package/dist/src/web/hooks/use-files.test.js +29 -0
  36. package/dist/src/web/hooks/use-files.test.js.map +1 -0
  37. package/dist/src/web/hooks/use-locale.d.ts +1 -0
  38. package/dist/src/web/hooks/use-locale.js +5 -0
  39. package/dist/src/web/hooks/use-locale.js.map +1 -0
  40. package/dist/src/web/hooks/use-locale.test.d.ts +1 -0
  41. package/dist/src/web/hooks/use-locale.test.js +21 -0
  42. package/dist/src/web/hooks/use-locale.test.js.map +1 -0
  43. package/dist/src/web/hooks/use-open-external.d.ts +1 -0
  44. package/dist/src/web/hooks/use-open-external.js +6 -0
  45. package/dist/src/web/hooks/use-open-external.js.map +1 -0
  46. package/dist/src/web/hooks/use-open-external.test.d.ts +1 -0
  47. package/dist/src/web/hooks/use-open-external.test.js +24 -0
  48. package/dist/src/web/hooks/use-open-external.test.js.map +1 -0
  49. package/dist/src/web/{use-openai-global.d.ts → hooks/use-openai-global.d.ts} +1 -1
  50. package/dist/src/web/{use-openai-global.js → hooks/use-openai-global.js} +4 -2
  51. package/dist/src/web/hooks/use-openai-global.js.map +1 -0
  52. package/dist/src/web/hooks/use-request-modal.d.ts +6 -0
  53. package/dist/src/web/hooks/use-request-modal.js +9 -0
  54. package/dist/src/web/hooks/use-request-modal.js.map +1 -0
  55. package/dist/src/web/hooks/use-request-modal.test.d.ts +1 -0
  56. package/dist/src/web/hooks/use-request-modal.test.js +24 -0
  57. package/dist/src/web/hooks/use-request-modal.test.js.map +1 -0
  58. package/dist/src/web/hooks/use-send-follow-up-message.d.ts +1 -0
  59. package/dist/src/web/hooks/use-send-follow-up-message.js +11 -0
  60. package/dist/src/web/hooks/use-send-follow-up-message.js.map +1 -0
  61. package/dist/src/web/hooks/use-theme.d.ts +1 -0
  62. package/dist/src/web/hooks/use-theme.js +5 -0
  63. package/dist/src/web/hooks/use-theme.js.map +1 -0
  64. package/dist/src/web/hooks/use-theme.test.d.ts +1 -0
  65. package/dist/src/web/hooks/use-theme.test.js +26 -0
  66. package/dist/src/web/hooks/use-theme.test.js.map +1 -0
  67. package/dist/src/web/hooks/use-tool-info.d.ts +25 -0
  68. package/dist/src/web/hooks/use-tool-info.js +22 -0
  69. package/dist/src/web/hooks/use-tool-info.js.map +1 -0
  70. package/dist/src/web/hooks/use-tool-info.test-d.d.ts +1 -0
  71. package/dist/src/web/hooks/use-tool-info.test-d.js +74 -0
  72. package/dist/src/web/hooks/use-tool-info.test-d.js.map +1 -0
  73. package/dist/src/web/hooks/use-tool-info.test.d.ts +1 -0
  74. package/dist/src/web/hooks/use-tool-info.test.js +59 -0
  75. package/dist/src/web/hooks/use-tool-info.test.js.map +1 -0
  76. package/dist/src/web/hooks/use-tool-output.d.ts +4 -0
  77. package/dist/src/web/hooks/use-tool-output.js +9 -0
  78. package/dist/src/web/hooks/use-tool-output.js.map +1 -0
  79. package/dist/src/web/hooks/use-tool-response-metadata.d.ts +4 -0
  80. package/dist/src/web/hooks/use-tool-response-metadata.js +8 -0
  81. package/dist/src/web/hooks/use-tool-response-metadata.js.map +1 -0
  82. package/dist/src/web/hooks/use-user-agent.d.ts +1 -0
  83. package/dist/src/web/hooks/use-user-agent.js +5 -0
  84. package/dist/src/web/hooks/use-user-agent.js.map +1 -0
  85. package/dist/src/web/hooks/use-user-agent.test.d.ts +1 -0
  86. package/dist/src/web/hooks/use-user-agent.test.js +31 -0
  87. package/dist/src/web/hooks/use-user-agent.test.js.map +1 -0
  88. package/dist/src/web/hooks/use-widget-state.d.ts +4 -0
  89. package/dist/src/web/hooks/use-widget-state.js +30 -0
  90. package/dist/src/web/hooks/use-widget-state.js.map +1 -0
  91. package/dist/src/web/hooks/use-widget-state.test.d.ts +1 -0
  92. package/dist/src/web/hooks/use-widget-state.test.js +60 -0
  93. package/dist/src/web/hooks/use-widget-state.test.js.map +1 -0
  94. package/dist/src/web/index.d.ts +2 -4
  95. package/dist/src/web/index.js +2 -4
  96. package/dist/src/web/index.js.map +1 -1
  97. package/dist/src/web/mount-widget.js +5 -0
  98. package/dist/src/web/mount-widget.js.map +1 -1
  99. package/dist/src/web/plugin.js +2 -4
  100. package/dist/src/web/plugin.js.map +1 -1
  101. package/dist/src/web/proxy.d.ts +1 -0
  102. package/dist/src/web/proxy.js +48 -0
  103. package/dist/src/web/proxy.js.map +1 -0
  104. package/dist/src/web/typed-hooks.d.ts +61 -0
  105. package/dist/src/web/typed-hooks.js +61 -0
  106. package/dist/src/web/typed-hooks.js.map +1 -0
  107. package/dist/src/web/typed-hooks.test-d.d.ts +1 -0
  108. package/dist/src/web/typed-hooks.test-d.js +72 -0
  109. package/dist/src/web/typed-hooks.test-d.js.map +1 -0
  110. package/dist/src/web/typed-hooks.test.d.ts +1 -0
  111. package/dist/src/web/typed-hooks.test.js +10 -0
  112. package/dist/src/web/typed-hooks.test.js.map +1 -0
  113. package/dist/src/web/types.d.ts +30 -14
  114. package/dist/src/web/types.js.map +1 -1
  115. package/dist/vitest.config.js +0 -1
  116. package/dist/vitest.config.js.map +1 -1
  117. package/package.json +4 -2
  118. package/dist/src/test/setup.js +0 -9
  119. package/dist/src/test/setup.js.map +0 -1
  120. package/dist/src/web/use-call-tool.d.ts +0 -54
  121. package/dist/src/web/use-call-tool.js.map +0 -1
  122. package/dist/src/web/use-call-tool.test.js +0 -66
  123. package/dist/src/web/use-call-tool.test.js.map +0 -1
  124. package/dist/src/web/use-openai-global.js.map +0 -1
  125. package/dist/src/web/use-tool-output.d.ts +0 -3
  126. package/dist/src/web/use-tool-output.js +0 -5
  127. package/dist/src/web/use-tool-output.js.map +0 -1
  128. package/dist/src/web/use-tool-response-metadata.d.ts +0 -3
  129. package/dist/src/web/use-tool-response-metadata.js +0 -5
  130. package/dist/src/web/use-tool-response-metadata.js.map +0 -1
  131. /package/dist/src/web/{use-call-tool.test.d.ts → hooks/use-call-tool.test.d.ts} +0 -0
  132. /package/dist/src/{test/setup.d.ts → web/hooks/use-display-mode.test.d.ts} +0 -0
@@ -0,0 +1,74 @@
1
+ import { expectTypeOf, test } from "vitest";
2
+ import { renderHook } from "@testing-library/react";
3
+ import { useToolInfo } from "./use-tool-info.js";
4
+ test("useToolInfo - TypeScript typing", () => {
5
+ test("should have correct types when no generic parameter is provided", () => {
6
+ const result = useToolInfo();
7
+ expectTypeOf(result.status);
8
+ expectTypeOf(result.isPending);
9
+ expectTypeOf(result.isSuccess);
10
+ expectTypeOf(result.input);
11
+ });
12
+ test("should correctly type input, output, and responseMetadata with explicit ToolSignature", () => {
13
+ const result = useToolInfo();
14
+ expectTypeOf(result.input);
15
+ // When pending, output and responseMetadata should be undefined
16
+ if (result.status === "pending") {
17
+ expectTypeOf(result.output);
18
+ expectTypeOf(result.responseMetadata);
19
+ }
20
+ // When success, output and responseMetadata should be defined
21
+ if (result.status === "success") {
22
+ expectTypeOf(result.output);
23
+ expectTypeOf(result.responseMetadata);
24
+ }
25
+ });
26
+ test("should correctly narrow types based on status discriminated union", () => {
27
+ const result = useToolInfo();
28
+ // Test type narrowing
29
+ if (result.isPending) {
30
+ expectTypeOf(result.status);
31
+ expectTypeOf(result.isPending);
32
+ expectTypeOf(result.isSuccess);
33
+ expectTypeOf(result.output);
34
+ expectTypeOf(result.responseMetadata);
35
+ }
36
+ if (result.isSuccess) {
37
+ expectTypeOf(result.status);
38
+ expectTypeOf(result.isPending);
39
+ expectTypeOf(result.isSuccess);
40
+ expectTypeOf(result.output);
41
+ expectTypeOf(result.responseMetadata);
42
+ }
43
+ if (result.status === "pending") {
44
+ expectTypeOf(result.input);
45
+ expectTypeOf(result.isPending);
46
+ expectTypeOf(result.isSuccess);
47
+ expectTypeOf(result.output);
48
+ expectTypeOf(result.responseMetadata);
49
+ }
50
+ if (result.status === "success") {
51
+ expectTypeOf(result.input);
52
+ expectTypeOf(result.isPending);
53
+ expectTypeOf(result.isSuccess);
54
+ expectTypeOf(result.output);
55
+ expectTypeOf(result.responseMetadata);
56
+ }
57
+ });
58
+ test("should handle partial ToolSignature with only input specified", () => {
59
+ const result = useToolInfo();
60
+ expectTypeOf(result.input);
61
+ if (result.status === "success") {
62
+ expectTypeOf(result.output);
63
+ expectTypeOf(result.responseMetadata);
64
+ }
65
+ });
66
+ test("should handle ToolSignature with only output specified", () => {
67
+ const result = useToolInfo();
68
+ expectTypeOf(result.input);
69
+ if (result.status === "success") {
70
+ expectTypeOf(result.output);
71
+ }
72
+ });
73
+ });
74
+ //# sourceMappingURL=use-tool-info.test-d.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"use-tool-info.test-d.js","sourceRoot":"","sources":["../../../../src/web/hooks/use-tool-info.test-d.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1 @@
1
+ export {};
@@ -0,0 +1,59 @@
1
+ import { fireEvent, renderHook, waitFor, act } from "@testing-library/react";
2
+ import { afterEach, beforeEach, describe, expect, it, vi } from "vitest";
3
+ import { useToolInfo } from "./use-tool-info.js";
4
+ import { SET_GLOBALS_EVENT_TYPE, SetGlobalsEvent, } from "../types.js";
5
+ describe("useToolInfo", () => {
6
+ let OpenaiMock;
7
+ beforeEach(() => {
8
+ OpenaiMock = {
9
+ toolInput: { name: "pokemon", args: { name: "pikachu" } },
10
+ toolOutput: null,
11
+ toolResponseMetadata: null,
12
+ };
13
+ vi.stubGlobal("openai", OpenaiMock);
14
+ });
15
+ afterEach(() => {
16
+ vi.unstubAllGlobals();
17
+ vi.resetAllMocks();
18
+ });
19
+ it("should return toolInput on initial mount window.openai", () => {
20
+ const { result } = renderHook(() => useToolInfo());
21
+ expect(result.current).toMatchObject({
22
+ input: { name: "pokemon", args: { name: "pikachu" } },
23
+ status: "pending",
24
+ isPending: true,
25
+ isSuccess: false,
26
+ });
27
+ });
28
+ it("should eventually return tool output and response metadata once tool call completes", async () => {
29
+ const toolOutput = {
30
+ name: "pikachu",
31
+ color: "yellow",
32
+ description: "When several of these POKéMON gather, their\felectricity could build and cause lightning storms.",
33
+ };
34
+ const toolResponseMetadata = { id: 12 };
35
+ const { result } = renderHook(() => useToolInfo());
36
+ act(() => {
37
+ OpenaiMock.toolOutput = toolOutput;
38
+ OpenaiMock.toolResponseMetadata = toolResponseMetadata;
39
+ fireEvent(window, new SetGlobalsEvent(SET_GLOBALS_EVENT_TYPE, {
40
+ detail: {
41
+ globals: {
42
+ toolOutput,
43
+ toolResponseMetadata,
44
+ },
45
+ },
46
+ }));
47
+ });
48
+ await waitFor(() => {
49
+ expect(result.current).toMatchObject({
50
+ status: "success",
51
+ isPending: false,
52
+ isSuccess: true,
53
+ output: toolOutput,
54
+ responseMetadata: toolResponseMetadata,
55
+ });
56
+ });
57
+ });
58
+ });
59
+ //# sourceMappingURL=use-tool-info.test.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"use-tool-info.test.js","sourceRoot":"","sources":["../../../../src/web/hooks/use-tool-info.test.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,SAAS,EAAE,UAAU,EAAE,OAAO,EAAE,GAAG,EAAE,MAAM,wBAAwB,CAAC;AAC7E,OAAO,EAAE,SAAS,EAAE,UAAU,EAAE,QAAQ,EAAE,MAAM,EAAE,EAAE,EAAE,EAAE,EAAE,MAAM,QAAQ,CAAC;AACzE,OAAO,EAAE,WAAW,EAAE,MAAM,oBAAoB,CAAC;AACjD,OAAO,EACL,sBAAsB,EACtB,eAAe,GAEhB,MAAM,aAAa,CAAC;AAErB,QAAQ,CAAC,aAAa,EAAE,GAAG,EAAE;IAC3B,IAAI,UAGH,CAAC;IAEF,UAAU,CAAC,GAAG,EAAE;QACd,UAAU,GAAG;YACX,SAAS,EAAE,EAAE,IAAI,EAAE,SAAS,EAAE,IAAI,EAAE,EAAE,IAAI,EAAE,SAAS,EAAE,EAAE;YACzD,UAAU,EAAE,IAAI;YAChB,oBAAoB,EAAE,IAAI;SAC3B,CAAC;QACF,EAAE,CAAC,UAAU,CAAC,QAAQ,EAAE,UAAU,CAAC,CAAC;IACtC,CAAC,CAAC,CAAC;IAEH,SAAS,CAAC,GAAG,EAAE;QACb,EAAE,CAAC,gBAAgB,EAAE,CAAC;QACtB,EAAE,CAAC,aAAa,EAAE,CAAC;IACrB,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,wDAAwD,EAAE,GAAG,EAAE;QAChE,MAAM,EAAE,MAAM,EAAE,GAAG,UAAU,CAAC,GAAG,EAAE,CAAC,WAAW,EAAE,CAAC,CAAC;QAEnD,MAAM,CAAC,MAAM,CAAC,OAAO,CAAC,CAAC,aAAa,CAAC;YACnC,KAAK,EAAE,EAAE,IAAI,EAAE,SAAS,EAAE,IAAI,EAAE,EAAE,IAAI,EAAE,SAAS,EAAE,EAAE;YACrD,MAAM,EAAE,SAAS;YACjB,SAAS,EAAE,IAAI;YACf,SAAS,EAAE,KAAK;SACjB,CAAC,CAAC;IACL,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,qFAAqF,EAAE,KAAK,IAAI,EAAE;QACnG,MAAM,UAAU,GAAG;YACjB,IAAI,EAAE,SAAS;YACf,KAAK,EAAE,QAAQ;YACf,WAAW,EACT,kGAAkG;SACrG,CAAC;QACF,MAAM,oBAAoB,GAAG,EAAE,EAAE,EAAE,EAAE,EAAE,CAAC;QACxC,MAAM,EAAE,MAAM,EAAE,GAAG,UAAU,CAAC,GAAG,EAAE,CAAC,WAAW,EAAE,CAAC,CAAC;QAEnD,GAAG,CAAC,GAAG,EAAE;YACP,UAAU,CAAC,UAAU,GAAG,UAAU,CAAC;YACnC,UAAU,CAAC,oBAAoB,GAAG,oBAAoB,CAAC;YACvD,SAAS,CACP,MAAM,EACN,IAAI,eAAe,CAAC,sBAAsB,EAAE;gBAC1C,MAAM,EAAE;oBACN,OAAO,EAAE;wBACP,UAAU;wBACV,oBAAoB;qBACrB;iBACF;aACF,CAAC,CACH,CAAC;QACJ,CAAC,CAAC,CAAC;QAEH,MAAM,OAAO,CAAC,GAAG,EAAE;YACjB,MAAM,CAAC,MAAM,CAAC,OAAO,CAAC,CAAC,aAAa,CAAC;gBACnC,MAAM,EAAE,SAAS;gBACjB,SAAS,EAAE,KAAK;gBAChB,SAAS,EAAE,IAAI;gBACf,MAAM,EAAE,UAAU;gBAClB,gBAAgB,EAAE,oBAAoB;aACvC,CAAC,CAAC;QACL,CAAC,CAAC,CAAC;IACL,CAAC,CAAC,CAAC;AACL,CAAC,CAAC,CAAC"}
@@ -0,0 +1,4 @@
1
+ /**
2
+ * @deprecated This hook is deprecated. Use `useToolInfo()` instead and access the `output` property.
3
+ */
4
+ export declare function useToolOutput(): import("../types.js").UnknownObject | undefined;
@@ -0,0 +1,9 @@
1
+ import { useToolInfo } from "./use-tool-info.js";
2
+ /**
3
+ * @deprecated This hook is deprecated. Use `useToolInfo()` instead and access the `output` property.
4
+ */
5
+ export function useToolOutput() {
6
+ const { output } = useToolInfo();
7
+ return output;
8
+ }
9
+ //# sourceMappingURL=use-tool-output.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"use-tool-output.js","sourceRoot":"","sources":["../../../../src/web/hooks/use-tool-output.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,WAAW,EAAE,MAAM,oBAAoB,CAAC;AAEjD;;GAEG;AACH,MAAM,UAAU,aAAa;IAC3B,MAAM,EAAE,MAAM,EAAE,GAAG,WAAW,EAAE,CAAC;IAEjC,OAAO,MAAM,CAAC;AAChB,CAAC"}
@@ -0,0 +1,4 @@
1
+ /**
2
+ * @deprecated This hook is deprecated. Use `useToolInfo()` instead and access the `responseMetadata` property.
3
+ */
4
+ export declare function useToolResponseMetadata(): import("../types.js").UnknownObject | null | undefined;
@@ -0,0 +1,8 @@
1
+ import { useOpenAiGlobal } from "./use-openai-global.js";
2
+ /**
3
+ * @deprecated This hook is deprecated. Use `useToolInfo()` instead and access the `responseMetadata` property.
4
+ */
5
+ export function useToolResponseMetadata() {
6
+ return useOpenAiGlobal("toolResponseMetadata");
7
+ }
8
+ //# sourceMappingURL=use-tool-response-metadata.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"use-tool-response-metadata.js","sourceRoot":"","sources":["../../../../src/web/hooks/use-tool-response-metadata.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,eAAe,EAAE,MAAM,wBAAwB,CAAC;AAEzD;;GAEG;AACH,MAAM,UAAU,uBAAuB;IACrC,OAAO,eAAe,CAAC,sBAAsB,CAAC,CAAC;AACjD,CAAC"}
@@ -0,0 +1 @@
1
+ export declare function useUserAgent(): import("../types.js").UserAgent;
@@ -0,0 +1,5 @@
1
+ import { useOpenAiGlobal } from "./use-openai-global.js";
2
+ export function useUserAgent() {
3
+ return useOpenAiGlobal("userAgent");
4
+ }
5
+ //# sourceMappingURL=use-user-agent.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"use-user-agent.js","sourceRoot":"","sources":["../../../../src/web/hooks/use-user-agent.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,eAAe,EAAE,MAAM,wBAAwB,CAAC;AAEzD,MAAM,UAAU,YAAY;IAC1B,OAAO,eAAe,CAAC,WAAW,CAAE,CAAC;AACvC,CAAC"}
@@ -0,0 +1 @@
1
+ export {};
@@ -0,0 +1,31 @@
1
+ import { useUserAgent } from "./use-user-agent.js";
2
+ import { describe, it, expect, vi, beforeEach, afterEach, } from "vitest";
3
+ import { renderHook } from "@testing-library/react";
4
+ describe("useUserAgent", () => {
5
+ let OpenaiMock;
6
+ beforeEach(() => {
7
+ OpenaiMock = {
8
+ userAgent: {
9
+ device: { type: "mobile" },
10
+ capabilities: { hover: false, touch: true },
11
+ },
12
+ };
13
+ vi.stubGlobal("openai", OpenaiMock);
14
+ });
15
+ afterEach(() => {
16
+ vi.unstubAllGlobals();
17
+ vi.resetAllMocks();
18
+ });
19
+ it("should return the current user agent from window.openai.userAgent", () => {
20
+ OpenaiMock.userAgent = {
21
+ device: { type: "mobile" },
22
+ capabilities: { hover: false, touch: true },
23
+ };
24
+ const { result } = renderHook(() => useUserAgent());
25
+ expect(result.current).toEqual({
26
+ device: { type: "mobile" },
27
+ capabilities: { hover: false, touch: true },
28
+ });
29
+ });
30
+ });
31
+ //# sourceMappingURL=use-user-agent.test.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"use-user-agent.test.js","sourceRoot":"","sources":["../../../../src/web/hooks/use-user-agent.test.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,YAAY,EAAE,MAAM,qBAAqB,CAAC;AACnD,OAAO,EACL,QAAQ,EACR,EAAE,EACF,MAAM,EACN,EAAE,EACF,UAAU,EACV,SAAS,GAEV,MAAM,QAAQ,CAAC;AAChB,OAAO,EAAE,UAAU,EAAE,MAAM,wBAAwB,CAAC;AAGpD,QAAQ,CAAC,cAAc,EAAE,GAAG,EAAE;IAC5B,IAAI,UAEH,CAAC;IAEF,UAAU,CAAC,GAAG,EAAE;QACd,UAAU,GAAG;YACX,SAAS,EAAE;gBACT,MAAM,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE;gBAC1B,YAAY,EAAE,EAAE,KAAK,EAAE,KAAK,EAAE,KAAK,EAAE,IAAI,EAAE;aAC5C;SACF,CAAC;QACF,EAAE,CAAC,UAAU,CAAC,QAAQ,EAAE,UAAU,CAAC,CAAC;IACtC,CAAC,CAAC,CAAC;IAEH,SAAS,CAAC,GAAG,EAAE;QACb,EAAE,CAAC,gBAAgB,EAAE,CAAC;QACtB,EAAE,CAAC,aAAa,EAAE,CAAC;IACrB,CAAC,CAAC,CAAC;IAEH,EAAE,CAAC,mEAAmE,EAAE,GAAG,EAAE;QAC3E,UAAU,CAAC,SAAS,GAAG;YACrB,MAAM,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE;YAC1B,YAAY,EAAE,EAAE,KAAK,EAAE,KAAK,EAAE,KAAK,EAAE,IAAI,EAAE;SAC5C,CAAC;QACF,MAAM,EAAE,MAAM,EAAE,GAAG,UAAU,CAAC,GAAG,EAAE,CAAC,YAAY,EAAE,CAAC,CAAC;QAEpD,MAAM,CAAC,MAAM,CAAC,OAAO,CAAC,CAAC,OAAO,CAAC;YAC7B,MAAM,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE;YAC1B,YAAY,EAAE,EAAE,KAAK,EAAE,KAAK,EAAE,KAAK,EAAE,IAAI,EAAE;SAC5C,CAAC,CAAC;IACL,CAAC,CAAC,CAAC;AACL,CAAC,CAAC,CAAC"}
@@ -0,0 +1,4 @@
1
+ import { type SetStateAction } from "react";
2
+ import type { UnknownObject } from "../types.js";
3
+ export declare function useWidgetState<T extends UnknownObject>(defaultState: T | (() => T)): readonly [T, (state: SetStateAction<T>) => void];
4
+ export declare function useWidgetState<T extends UnknownObject>(defaultState?: T | (() => T | null) | null): readonly [T | null, (state: SetStateAction<T | null>) => void];
@@ -0,0 +1,30 @@
1
+ import { useCallback, useEffect, useState } from "react";
2
+ import { useOpenAiGlobal } from "./use-openai-global.js";
3
+ export function useWidgetState(defaultState) {
4
+ const widgetStateFromWindow = useOpenAiGlobal("widgetState");
5
+ const [widgetState, _setWidgetState] = useState(() => {
6
+ if (widgetStateFromWindow !== null) {
7
+ return widgetStateFromWindow;
8
+ }
9
+ return typeof defaultState === "function"
10
+ ? defaultState()
11
+ : defaultState ?? null;
12
+ });
13
+ useEffect(() => {
14
+ // Fixes openai implementation bug
15
+ if (widgetStateFromWindow !== null) {
16
+ _setWidgetState(widgetStateFromWindow);
17
+ }
18
+ }, [widgetStateFromWindow]);
19
+ const setWidgetState = useCallback((state) => {
20
+ _setWidgetState((prevState) => {
21
+ const newState = typeof state === "function" ? state(prevState) : state;
22
+ if (newState !== null) {
23
+ window.openai.setWidgetState(newState);
24
+ }
25
+ return newState;
26
+ });
27
+ }, [window.openai.setWidgetState]);
28
+ return [widgetState, setWidgetState];
29
+ }
30
+ //# sourceMappingURL=use-widget-state.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"use-widget-state.js","sourceRoot":"","sources":["../../../../src/web/hooks/use-widget-state.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,WAAW,EAAE,SAAS,EAAE,QAAQ,EAAuB,MAAM,OAAO,CAAC;AAE9E,OAAO,EAAE,eAAe,EAAE,MAAM,wBAAwB,CAAC;AAQzD,MAAM,UAAU,cAAc,CAC5B,YAA0C;IAE1C,MAAM,qBAAqB,GAAG,eAAe,CAAC,aAAa,CAAM,CAAC;IAElE,MAAM,CAAC,WAAW,EAAE,eAAe,CAAC,GAAG,QAAQ,CAAW,GAAG,EAAE;QAC7D,IAAI,qBAAqB,KAAK,IAAI,EAAE,CAAC;YACnC,OAAO,qBAAqB,CAAC;QAC/B,CAAC;QAED,OAAO,OAAO,YAAY,KAAK,UAAU;YACvC,CAAC,CAAC,YAAY,EAAE;YAChB,CAAC,CAAC,YAAY,IAAI,IAAI,CAAC;IAC3B,CAAC,CAAC,CAAC;IAEH,SAAS,CAAC,GAAG,EAAE;QACb,kCAAkC;QAClC,IAAI,qBAAqB,KAAK,IAAI,EAAE,CAAC;YACnC,eAAe,CAAC,qBAAqB,CAAC,CAAC;QACzC,CAAC;IACH,CAAC,EAAE,CAAC,qBAAqB,CAAC,CAAC,CAAC;IAE5B,MAAM,cAAc,GAAG,WAAW,CAChC,CAAC,KAA+B,EAAE,EAAE;QAClC,eAAe,CAAC,CAAC,SAAS,EAAE,EAAE;YAC5B,MAAM,QAAQ,GAAG,OAAO,KAAK,KAAK,UAAU,CAAC,CAAC,CAAC,KAAK,CAAC,SAAS,CAAC,CAAC,CAAC,CAAC,KAAK,CAAC;YAExE,IAAI,QAAQ,KAAK,IAAI,EAAE,CAAC;gBACtB,MAAM,CAAC,MAAM,CAAC,cAAc,CAAC,QAAQ,CAAC,CAAC;YACzC,CAAC;YAED,OAAO,QAAQ,CAAC;QAClB,CAAC,CAAC,CAAC;IACL,CAAC,EACD,CAAC,MAAM,CAAC,MAAM,CAAC,cAAc,CAAC,CAC/B,CAAC;IAEF,OAAO,CAAC,WAAW,EAAE,cAAc,CAAU,CAAC;AAChD,CAAC"}
@@ -0,0 +1 @@
1
+ export {};
@@ -0,0 +1,60 @@
1
+ import { useWidgetState } from "./use-widget-state.js";
2
+ import { describe, it, expect, vi, beforeEach, afterEach, } from "vitest";
3
+ import { renderHook, act } from "@testing-library/react";
4
+ describe("useWidgetState", () => {
5
+ let OpenaiMock;
6
+ beforeEach(() => {
7
+ OpenaiMock = {
8
+ widgetState: null,
9
+ setWidgetState: vi.fn().mockResolvedValue(undefined),
10
+ };
11
+ vi.stubGlobal("openai", OpenaiMock);
12
+ });
13
+ afterEach(() => {
14
+ vi.unstubAllGlobals();
15
+ vi.resetAllMocks();
16
+ });
17
+ const defaultState = { count: 0, name: "test" };
18
+ const windowState = { count: 5, name: "window" };
19
+ it("should initialize with default state when window.openai.widgetState is null", () => {
20
+ OpenaiMock.widgetState = null;
21
+ const { result } = renderHook(() => useWidgetState(defaultState));
22
+ expect(result.current[0]).toEqual(defaultState);
23
+ });
24
+ it("should initialize with window.openai.widgetState when available", () => {
25
+ OpenaiMock.widgetState = windowState;
26
+ const { result } = renderHook(() => useWidgetState(defaultState));
27
+ expect(result.current[0]).toEqual(windowState);
28
+ });
29
+ it("should call window.openai.setWidgetState when setWidgetState is called with a new state", async () => {
30
+ const { result } = renderHook(() => useWidgetState(defaultState));
31
+ const newState = { count: 10, name: "updated" };
32
+ act(() => {
33
+ result.current[1](newState);
34
+ });
35
+ expect(OpenaiMock.setWidgetState).toHaveBeenCalledWith(newState);
36
+ expect(result.current[0]).toEqual(newState);
37
+ });
38
+ it("should call window.openai.setWidgetState when setWidgetState is called with a function updater", async () => {
39
+ const { result } = renderHook(() => useWidgetState(defaultState));
40
+ act(() => {
41
+ result.current[1]((prev) => ({ ...prev, count: prev.count + 1 }));
42
+ });
43
+ expect(OpenaiMock.setWidgetState).toHaveBeenCalledWith({
44
+ count: 1,
45
+ name: "test",
46
+ });
47
+ expect(result.current[0]).toEqual({ count: 1, name: "test" });
48
+ });
49
+ it("should update state when window.openai.widgetState changes", () => {
50
+ OpenaiMock.widgetState = defaultState;
51
+ const { result, rerender } = renderHook(() => useWidgetState(defaultState));
52
+ expect(result.current[0]).toEqual(defaultState);
53
+ // Simulate window.openai.widgetState changing
54
+ OpenaiMock.widgetState = windowState;
55
+ // Trigger re-render to simulate the useEffect running
56
+ rerender();
57
+ expect(result.current[0]).toEqual(windowState);
58
+ });
59
+ });
60
+ //# sourceMappingURL=use-widget-state.test.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"use-widget-state.test.js","sourceRoot":"","sources":["../../../../src/web/hooks/use-widget-state.test.ts"],"names":[],"mappings":"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"}
@@ -1,7 +1,5 @@
1
- export { useOpenAiGlobal } from "./use-openai-global.js";
2
- export { useToolOutput } from "./use-tool-output.js";
3
- export { useToolResponseMetadata } from "./use-tool-response-metadata.js";
4
- export { useCallTool } from "./use-call-tool.js";
5
1
  export * from "./types.js";
6
2
  export { mountWidget } from "./mount-widget.js";
7
3
  export { skybridge } from "./plugin.js";
4
+ export * from "./hooks/index.js";
5
+ export { createTypedHooks } from "./typed-hooks.js";
@@ -1,8 +1,6 @@
1
- export { useOpenAiGlobal } from "./use-openai-global.js";
2
- export { useToolOutput } from "./use-tool-output.js";
3
- export { useToolResponseMetadata } from "./use-tool-response-metadata.js";
4
- export { useCallTool } from "./use-call-tool.js";
5
1
  export * from "./types.js";
6
2
  export { mountWidget } from "./mount-widget.js";
7
3
  export { skybridge } from "./plugin.js";
4
+ export * from "./hooks/index.js";
5
+ export { createTypedHooks } from "./typed-hooks.js";
8
6
  //# sourceMappingURL=index.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/web/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,eAAe,EAAE,MAAM,wBAAwB,CAAC;AACzD,OAAO,EAAE,aAAa,EAAE,MAAM,sBAAsB,CAAC;AACrD,OAAO,EAAE,uBAAuB,EAAE,MAAM,iCAAiC,CAAC;AAC1E,OAAO,EAAE,WAAW,EAAE,MAAM,oBAAoB,CAAC;AACjD,cAAc,YAAY,CAAC;AAC3B,OAAO,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AAChD,OAAO,EAAE,SAAS,EAAE,MAAM,aAAa,CAAC"}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/web/index.ts"],"names":[],"mappings":"AAAA,cAAc,YAAY,CAAC;AAC3B,OAAO,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AAChD,OAAO,EAAE,SAAS,EAAE,MAAM,aAAa,CAAC;AACxC,cAAc,kBAAkB,CAAC;AACjC,OAAO,EAAE,gBAAgB,EAAE,MAAM,kBAAkB,CAAC"}
@@ -1,5 +1,7 @@
1
+ /// <reference types="vite/client" />
1
2
  import { createElement, StrictMode } from "react";
2
3
  import { createRoot } from "react-dom/client";
4
+ import { installOpenAILoggingProxy } from "./proxy.js";
3
5
  let rootInstance = null;
4
6
  export const mountWidget = (component) => {
5
7
  const rootElement = document.getElementById("root");
@@ -9,6 +11,9 @@ export const mountWidget = (component) => {
9
11
  if (!rootInstance) {
10
12
  rootInstance = createRoot(rootElement);
11
13
  }
14
+ if (import.meta.env.DEV) {
15
+ installOpenAILoggingProxy();
16
+ }
12
17
  rootInstance.render(createElement(StrictMode, null, component));
13
18
  };
14
19
  //# sourceMappingURL=mount-widget.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"mount-widget.js","sourceRoot":"","sources":["../../../src/web/mount-widget.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,aAAa,EAAE,UAAU,EAAE,MAAM,OAAO,CAAC;AAClD,OAAO,EAAE,UAAU,EAAa,MAAM,kBAAkB,CAAC;AAEzD,IAAI,YAAY,GAAgB,IAAI,CAAC;AAErC,MAAM,CAAC,MAAM,WAAW,GAAG,CAAC,SAA0B,EAAE,EAAE;IACxD,MAAM,WAAW,GAAG,QAAQ,CAAC,cAAc,CAAC,MAAM,CAAC,CAAC;IACpD,IAAI,CAAC,WAAW,EAAE,CAAC;QACjB,MAAM,IAAI,KAAK,CAAC,wBAAwB,CAAC,CAAC;IAC5C,CAAC;IAED,IAAI,CAAC,YAAY,EAAE,CAAC;QAClB,YAAY,GAAG,UAAU,CAAC,WAAW,CAAC,CAAC;IACzC,CAAC;IAED,YAAY,CAAC,MAAM,CAAC,aAAa,CAAC,UAAU,EAAE,IAAI,EAAE,SAAS,CAAC,CAAC,CAAC;AAClE,CAAC,CAAC"}
1
+ {"version":3,"file":"mount-widget.js","sourceRoot":"","sources":["../../../src/web/mount-widget.ts"],"names":[],"mappings":"AAAA,qCAAqC;AAErC,OAAO,EAAE,aAAa,EAAE,UAAU,EAAE,MAAM,OAAO,CAAC;AAClD,OAAO,EAAE,UAAU,EAAa,MAAM,kBAAkB,CAAC;AACzD,OAAO,EAAE,yBAAyB,EAAE,MAAM,YAAY,CAAC;AAEvD,IAAI,YAAY,GAAgB,IAAI,CAAC;AAErC,MAAM,CAAC,MAAM,WAAW,GAAG,CAAC,SAA0B,EAAE,EAAE;IACxD,MAAM,WAAW,GAAG,QAAQ,CAAC,cAAc,CAAC,MAAM,CAAC,CAAC;IACpD,IAAI,CAAC,WAAW,EAAE,CAAC;QACjB,MAAM,IAAI,KAAK,CAAC,wBAAwB,CAAC,CAAC;IAC5C,CAAC;IAED,IAAI,CAAC,YAAY,EAAE,CAAC;QAClB,YAAY,GAAG,UAAU,CAAC,WAAW,CAAC,CAAC;IACzC,CAAC;IAED,IAAI,MAAM,CAAC,IAAI,CAAC,GAAG,CAAC,GAAG,EAAE,CAAC;QACxB,yBAAyB,EAAE,CAAC;IAC9B,CAAC;IAED,YAAY,CAAC,MAAM,CAAC,aAAa,CAAC,UAAU,EAAE,IAAI,EAAE,SAAS,CAAC,CAAC,CAAC;AAClE,CAAC,CAAC"}
@@ -12,15 +12,13 @@ export function skybridge() {
12
12
  file,
13
13
  ]));
14
14
  return {
15
+ base: "/assets",
15
16
  build: {
17
+ manifest: true,
16
18
  minify: true,
17
19
  cssCodeSplit: false,
18
20
  rollupOptions: {
19
21
  input,
20
- output: {
21
- entryFileNames: "[name].js",
22
- assetFileNames: "[name][extname]",
23
- },
24
22
  },
25
23
  },
26
24
  };
@@ -1 +1 @@
1
- {"version":3,"file":"plugin.js","sourceRoot":"","sources":["../../../src/web/plugin.ts"],"names":[],"mappings":"AAEA,MAAM,UAAU,SAAS;IACvB,OAAO;QACL,IAAI,EAAE,WAAW;QAEjB,KAAK,CAAC,MAAM,CAAC,MAAM;YACjB,4EAA4E;YAC5E,MAAM,EAAE,QAAQ,EAAE,GAAG,MAAM,MAAM,CAAC,SAAS,CAAC,CAAC;YAC7C,MAAM,EAAE,OAAO,EAAE,GAAG,MAAM,MAAM,CAAC,WAAW,CAAC,CAAC;YAE9C,MAAM,WAAW,GAAG,MAAM,CAAC,IAAI,IAAI,OAAO,CAAC,GAAG,EAAE,CAAC;YACjD,MAAM,cAAc,GAAG,OAAO,CAC5B,WAAW,EACX,oCAAoC,CACrC,CAAC;YAEF,MAAM,KAAK,GAAG,MAAM,CAAC,WAAW,CAC9B,QAAQ,CAAC,cAAc,CAAC,CAAC,GAAG,CAAC,CAAC,IAAI,EAAE,EAAE,CAAC;gBACrC,IAAI,CAAC,KAAK,CAAC,0BAA0B,CAAC,EAAE,CAAC,CAAC,CAAC;gBAC3C,IAAI;aACL,CAAC,CACH,CAAC;YAEF,OAAO;gBACL,KAAK,EAAE;oBACL,MAAM,EAAE,IAAI;oBACZ,YAAY,EAAE,KAAK;oBACnB,aAAa,EAAE;wBACb,KAAK;wBACL,MAAM,EAAE;4BACN,cAAc,EAAE,WAAW;4BAC3B,cAAc,EAAE,iBAAiB;yBAClC;qBACF;iBACF;aACF,CAAC;QACJ,CAAC;KACF,CAAC;AACJ,CAAC"}
1
+ {"version":3,"file":"plugin.js","sourceRoot":"","sources":["../../../src/web/plugin.ts"],"names":[],"mappings":"AAEA,MAAM,UAAU,SAAS;IACvB,OAAO;QACL,IAAI,EAAE,WAAW;QAEjB,KAAK,CAAC,MAAM,CAAC,MAAM;YACjB,4EAA4E;YAC5E,MAAM,EAAE,QAAQ,EAAE,GAAG,MAAM,MAAM,CAAC,SAAS,CAAC,CAAC;YAC7C,MAAM,EAAE,OAAO,EAAE,GAAG,MAAM,MAAM,CAAC,WAAW,CAAC,CAAC;YAE9C,MAAM,WAAW,GAAG,MAAM,CAAC,IAAI,IAAI,OAAO,CAAC,GAAG,EAAE,CAAC;YACjD,MAAM,cAAc,GAAG,OAAO,CAC5B,WAAW,EACX,oCAAoC,CACrC,CAAC;YAEF,MAAM,KAAK,GAAG,MAAM,CAAC,WAAW,CAC9B,QAAQ,CAAC,cAAc,CAAC,CAAC,GAAG,CAAC,CAAC,IAAI,EAAE,EAAE,CAAC;gBACrC,IAAI,CAAC,KAAK,CAAC,0BAA0B,CAAC,EAAE,CAAC,CAAC,CAAC;gBAC3C,IAAI;aACL,CAAC,CACH,CAAC;YAEF,OAAO;gBACL,IAAI,EAAE,SAAS;gBACf,KAAK,EAAE;oBACL,QAAQ,EAAE,IAAI;oBACd,MAAM,EAAE,IAAI;oBACZ,YAAY,EAAE,KAAK;oBACnB,aAAa,EAAE;wBACb,KAAK;qBACN;iBACF;aACF,CAAC;QACJ,CAAC;KACF,CAAC;AACJ,CAAC"}
@@ -0,0 +1 @@
1
+ export declare function installOpenAILoggingProxy(): void;
@@ -0,0 +1,48 @@
1
+ const colors = {
2
+ brand: "#6366f1",
3
+ info: "#22223b",
4
+ success: "#22c55e",
5
+ error: "#ef4444",
6
+ };
7
+ export function installOpenAILoggingProxy() {
8
+ if (typeof window === "undefined" || !window.openai) {
9
+ console.warn("[openai-proxy] window.openai not found, skipping proxy installation");
10
+ return;
11
+ }
12
+ const originalOpenAI = window.openai;
13
+ const handler = {
14
+ get(target, prop, receiver) {
15
+ const value = Reflect.get(target, prop, receiver);
16
+ if (typeof value !== "function") {
17
+ return value;
18
+ }
19
+ return function (...args) {
20
+ const methodName = String(prop);
21
+ console.group(`%c[openai] %cmethod %c${methodName}`, `color: ${colors.brand}; font-weight: normal`, `color: ${colors.info}; font-weight: normal`, `color: ${colors.success}`);
22
+ console.log("%c← args:", `color: ${colors.info}`, args);
23
+ const result = value.apply(target, args);
24
+ if (result && typeof result.then === "function") {
25
+ return result.then((resolved) => {
26
+ console.log("%c→ resolved:", `color: ${colors.success}`, resolved);
27
+ console.groupEnd();
28
+ return resolved;
29
+ }, (error) => {
30
+ console.error("%c→ rejected:", `color: ${colors.error}`, error);
31
+ console.groupEnd();
32
+ throw error;
33
+ });
34
+ }
35
+ console.log("%c→ returned:", `color: ${colors.success}`, result);
36
+ console.groupEnd();
37
+ return result;
38
+ };
39
+ },
40
+ set(target, prop, value, receiver) {
41
+ console.log(`%c[openai] %cupdate %c${String(prop)}`, `color: ${colors.brand}`, `color: ${colors.info}`, `color: ${colors.success}; font-weight: bold`, "←", value);
42
+ return Reflect.set(target, prop, value, receiver);
43
+ },
44
+ };
45
+ window.openai = new Proxy(originalOpenAI, handler);
46
+ console.log("%c[openai-proxy] %cInstalled logging proxy for window.openai", `color: ${colors.brand}`, `color: ${colors.info}`);
47
+ }
48
+ //# sourceMappingURL=proxy.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"proxy.js","sourceRoot":"","sources":["../../../src/web/proxy.ts"],"names":[],"mappings":"AAAA,MAAM,MAAM,GAAG;IACb,KAAK,EAAE,SAAS;IAChB,IAAI,EAAE,SAAS;IACf,OAAO,EAAE,SAAS;IAClB,KAAK,EAAE,SAAS;CACR,CAAC;AAEX,MAAM,UAAU,yBAAyB;IACvC,IAAI,OAAO,MAAM,KAAK,WAAW,IAAI,CAAC,MAAM,CAAC,MAAM,EAAE,CAAC;QACpD,OAAO,CAAC,IAAI,CACV,qEAAqE,CACtE,CAAC;QACF,OAAO;IACT,CAAC;IAED,MAAM,cAAc,GAAG,MAAM,CAAC,MAAM,CAAC;IAErC,MAAM,OAAO,GAAwC;QACnD,GAAG,CAAC,MAAM,EAAE,IAAI,EAAE,QAAQ;YACxB,MAAM,KAAK,GAAG,OAAO,CAAC,GAAG,CAAC,MAAM,EAAE,IAAI,EAAE,QAAQ,CAAC,CAAC;YAElD,IAAI,OAAO,KAAK,KAAK,UAAU,EAAE,CAAC;gBAChC,OAAO,KAAK,CAAC;YACf,CAAC;YAED,OAAO,UAAU,GAAG,IAAe;gBACjC,MAAM,UAAU,GAAG,MAAM,CAAC,IAAI,CAAC,CAAC;gBAEhC,OAAO,CAAC,KAAK,CACX,yBAAyB,UAAU,EAAE,EACrC,UAAU,MAAM,CAAC,KAAK,uBAAuB,EAC7C,UAAU,MAAM,CAAC,IAAI,uBAAuB,EAC5C,UAAU,MAAM,CAAC,OAAO,EAAE,CAC3B,CAAC;gBACF,OAAO,CAAC,GAAG,CAAC,WAAW,EAAE,UAAU,MAAM,CAAC,IAAI,EAAE,EAAE,IAAI,CAAC,CAAC;gBAExD,MAAM,MAAM,GAAG,KAAK,CAAC,KAAK,CAAC,MAAM,EAAE,IAAI,CAAC,CAAC;gBAEzC,IAAI,MAAM,IAAI,OAAO,MAAM,CAAC,IAAI,KAAK,UAAU,EAAE,CAAC;oBAChD,OAAO,MAAM,CAAC,IAAI,CAChB,CAAC,QAAiB,EAAE,EAAE;wBACpB,OAAO,CAAC,GAAG,CACT,eAAe,EACf,UAAU,MAAM,CAAC,OAAO,EAAE,EAC1B,QAAQ,CACT,CAAC;wBACF,OAAO,CAAC,QAAQ,EAAE,CAAC;wBACnB,OAAO,QAAQ,CAAC;oBAClB,CAAC,EACD,CAAC,KAAc,EAAE,EAAE;wBACjB,OAAO,CAAC,KAAK,CAAC,eAAe,EAAE,UAAU,MAAM,CAAC,KAAK,EAAE,EAAE,KAAK,CAAC,CAAC;wBAChE,OAAO,CAAC,QAAQ,EAAE,CAAC;wBACnB,MAAM,KAAK,CAAC;oBACd,CAAC,CACF,CAAC;gBACJ,CAAC;gBAED,OAAO,CAAC,GAAG,CAAC,eAAe,EAAE,UAAU,MAAM,CAAC,OAAO,EAAE,EAAE,MAAM,CAAC,CAAC;gBACjE,OAAO,CAAC,QAAQ,EAAE,CAAC;gBAEnB,OAAO,MAAM,CAAC;YAChB,CAAC,CAAC;QACJ,CAAC;QAED,GAAG,CAAC,MAAM,EAAE,IAAI,EAAE,KAAK,EAAE,QAAQ;YAC/B,OAAO,CAAC,GAAG,CACT,yBAAyB,MAAM,CAAC,IAAI,CAAC,EAAE,EACvC,UAAU,MAAM,CAAC,KAAK,EAAE,EACxB,UAAU,MAAM,CAAC,IAAI,EAAE,EACvB,UAAU,MAAM,CAAC,OAAO,qBAAqB,EAC7C,GAAG,EACH,KAAK,CACN,CAAC;YAEF,OAAO,OAAO,CAAC,GAAG,CAAC,MAAM,EAAE,IAAI,EAAE,KAAK,EAAE,QAAQ,CAAC,CAAC;QACpD,CAAC;KACF,CAAC;IAEF,MAAM,CAAC,MAAM,GAAG,IAAI,KAAK,CAAC,cAAc,EAAE,OAAO,CAAC,CAAC;IAEnD,OAAO,CAAC,GAAG,CACT,8DAA8D,EAC9D,UAAU,MAAM,CAAC,KAAK,EAAE,EACxB,UAAU,MAAM,CAAC,IAAI,EAAE,CACxB,CAAC;AACJ,CAAC"}
@@ -0,0 +1,61 @@
1
+ import { useCallTool } from "./hooks/use-call-tool.js";
2
+ import type { ToolPendingState, ToolSuccessState } from "./hooks/use-tool-info.js";
3
+ import type { McpServer, InferWidgets, AnyWidgetRegistry, WidgetInput, WidgetOutput } from "../server/index.js";
4
+ import type { CallToolArgs, UnknownObject } from "./types.js";
5
+ type TypedCallToolReturn<TInput, TOutput> = ReturnType<typeof useCallTool<TInput & CallToolArgs, {
6
+ structuredContent: TOutput & UnknownObject;
7
+ }>>;
8
+ type TypedToolInfoReturn<TInput extends UnknownObject, TOutput extends UnknownObject, TResponseMetadata extends UnknownObject> = ToolPendingState<TInput> | ToolSuccessState<TInput, TOutput, TResponseMetadata>;
9
+ /**
10
+ * Creates typed versions of skybridge hooks with full type inference
11
+ * for tool names, inputs, and outputs.
12
+ *
13
+ * Set this up once in a dedicated file and export the typed hooks:
14
+ *
15
+ * @example
16
+ * ```typescript
17
+ * // web/src/skybridge.ts (one-time setup)
18
+ * import type { AppType } from "../server";
19
+ * import { createTypedHooks } from "skybridge/web";
20
+ *
21
+ * export const { useCallTool, useToolInfo } = createTypedHooks<AppType>();
22
+ * ```
23
+ *
24
+ * ```typescript
25
+ * // web/src/widgets/search.tsx (usage)
26
+ * import { useCallTool, useToolInfo } from "../skybridge";
27
+ *
28
+ * export function SearchWidget() {
29
+ * const { callTool, data } = useCallTool("search");
30
+ * // ^ autocomplete for tool names
31
+ * callTool({ query: "test" });
32
+ * // ^ autocomplete for input fields
33
+ *
34
+ * const toolInfo = useToolInfo<"search">();
35
+ * // ^ autocomplete for tool names
36
+ * // toolInfo.input is typed based on widget input schema
37
+ * // toolInfo.output is typed based on widget output schema
38
+ * }
39
+ * ```
40
+ */
41
+ export declare function createTypedHooks<T extends McpServer<AnyWidgetRegistry>>(): {
42
+ /**
43
+ * Typed version of useCallTool that provides autocomplete for tool names
44
+ * and type inference for inputs and outputs.
45
+ */
46
+ useCallTool: <K extends keyof InferWidgets<T> & string>(name: K) => TypedCallToolReturn<InferWidgets<T>[K]["input"], InferWidgets<T>[K]["output"]>;
47
+ /**
48
+ * Typed version of useToolInfo that provides autocomplete for widget names
49
+ * and type inference for inputs, outputs, and responseMetadata.
50
+ *
51
+ * @example
52
+ * ```typescript
53
+ * const toolInfo = useToolInfo<"search-voyage">();
54
+ * // toolInfo.input is typed as { destination: string; ... }
55
+ * // toolInfo.output is typed as { results: Array<...>; ... } | undefined
56
+ * // toolInfo.status narrows correctly: "pending" | "success"
57
+ * ```
58
+ */
59
+ useToolInfo: <K extends keyof InferWidgets<T> & string>() => TypedToolInfoReturn<WidgetInput<T, K> & UnknownObject, WidgetOutput<T, K> & UnknownObject, UnknownObject>;
60
+ };
61
+ export {};
@@ -0,0 +1,61 @@
1
+ import { useCallTool } from "./hooks/use-call-tool.js";
2
+ import { useToolInfo } from "./hooks/use-tool-info.js";
3
+ /**
4
+ * Creates typed versions of skybridge hooks with full type inference
5
+ * for tool names, inputs, and outputs.
6
+ *
7
+ * Set this up once in a dedicated file and export the typed hooks:
8
+ *
9
+ * @example
10
+ * ```typescript
11
+ * // web/src/skybridge.ts (one-time setup)
12
+ * import type { AppType } from "../server";
13
+ * import { createTypedHooks } from "skybridge/web";
14
+ *
15
+ * export const { useCallTool, useToolInfo } = createTypedHooks<AppType>();
16
+ * ```
17
+ *
18
+ * ```typescript
19
+ * // web/src/widgets/search.tsx (usage)
20
+ * import { useCallTool, useToolInfo } from "../skybridge";
21
+ *
22
+ * export function SearchWidget() {
23
+ * const { callTool, data } = useCallTool("search");
24
+ * // ^ autocomplete for tool names
25
+ * callTool({ query: "test" });
26
+ * // ^ autocomplete for input fields
27
+ *
28
+ * const toolInfo = useToolInfo<"search">();
29
+ * // ^ autocomplete for tool names
30
+ * // toolInfo.input is typed based on widget input schema
31
+ * // toolInfo.output is typed based on widget output schema
32
+ * }
33
+ * ```
34
+ */
35
+ export function createTypedHooks() {
36
+ return {
37
+ /**
38
+ * Typed version of useCallTool that provides autocomplete for tool names
39
+ * and type inference for inputs and outputs.
40
+ */
41
+ useCallTool: (name) => {
42
+ return useCallTool(name);
43
+ },
44
+ /**
45
+ * Typed version of useToolInfo that provides autocomplete for widget names
46
+ * and type inference for inputs, outputs, and responseMetadata.
47
+ *
48
+ * @example
49
+ * ```typescript
50
+ * const toolInfo = useToolInfo<"search-voyage">();
51
+ * // toolInfo.input is typed as { destination: string; ... }
52
+ * // toolInfo.output is typed as { results: Array<...>; ... } | undefined
53
+ * // toolInfo.status narrows correctly: "pending" | "success"
54
+ * ```
55
+ */
56
+ useToolInfo: () => {
57
+ return useToolInfo();
58
+ },
59
+ };
60
+ }
61
+ //# sourceMappingURL=typed-hooks.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"typed-hooks.js","sourceRoot":"","sources":["../../../src/web/typed-hooks.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,WAAW,EAAE,MAAM,0BAA0B,CAAC;AACvD,OAAO,EAAE,WAAW,EAAE,MAAM,0BAA0B,CAAC;AAgCvD;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA+BG;AACH,MAAM,UAAU,gBAAgB;IAI9B,OAAO;QACL;;;WAGG;QACH,WAAW,EAAE,CACX,IAAO,EAIP,EAAE;YACF,OAAO,WAAW,CAGhB,IAAI,CAGL,CAAC;QACJ,CAAC;QACD;;;;;;;;;;;WAWG;QACH,WAAW,EAAE,GAIX,EAAE;YACF,OAAO,WAAW,EAQjB,CAAC;QACJ,CAAC;KACF,CAAC;AACJ,CAAC"}
@@ -0,0 +1 @@
1
+ export {};