overmux 0.0.1 → 0.0.2
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.
- package/CHANGELOG.md +16 -0
- package/README.md +7 -0
- package/dist/auth/.vite/manifest.json +11 -0
- package/dist/auth/assets/index-Bx8JhwVi.css +1 -0
- package/dist/auth/assets/index-CHIE7qYj.js +72 -0
- package/dist/auth/index.html +14 -0
- package/dist/bin.js +4504 -7870
- package/dist/bin.js.map +1 -0
- package/dist/docs/000-index.md +21 -0
- package/dist/docs/100-introduction/100-what-is-overmux.md +7 -0
- package/dist/docs/100-introduction/200-how-overmux-works.md +7 -0
- package/dist/docs/100-introduction/300-why-overmux.md +22 -0
- package/dist/docs/200-getting-started/100-install-and-run-overmux.md +51 -0
- package/dist/docs/200-getting-started/200-install-overmux-desktop.md +41 -0
- package/dist/docs/200-getting-started/300-install-overmux-pwa.mdx +92 -0
- package/dist/docs/200-getting-started/400-secure-with-https/100-choose-an-https-setup.md +14 -0
- package/dist/docs/200-getting-started/400-secure-with-https/200-tailscale-serve.md +44 -0
- package/dist/docs/200-getting-started/400-secure-with-https/300-cloudflare-tunnel.md +59 -0
- package/dist/docs/200-getting-started/400-secure-with-https/400-self-hosted-reverse-proxy.md +32 -0
- package/dist/docs/300-fundamentals/100-project-structure.md +3 -0
- package/dist/docs/300-fundamentals/200-configuration.md +3 -0
- package/dist/docs/300-fundamentals/300-theming.md +3 -0
- package/dist/docs/300-fundamentals/400-server.md +3 -0
- package/dist/docs/300-fundamentals/500-client.md +3 -0
- package/dist/docs/300-fundamentals/600-operations.md +3 -0
- package/dist/docs/300-fundamentals/700-resources.md +3 -0
- package/dist/docs/300-fundamentals/800-streams.md +3 -0
- package/dist/docs/300-fundamentals/900-authentication-and-security.md +3 -0
- package/dist/docs/400-reference/100-configuration.md +3 -0
- package/dist/docs/400-reference/200-server-api.md +3 -0
- package/dist/docs/400-reference/300-client-api.md +3 -0
- package/dist/docs/400-reference/400-cli/100-serve.md +33 -0
- package/dist/docs/400-reference/400-cli/200-auth.md +52 -0
- package/dist/docs/400-reference/400-cli/300-call.md +28 -0
- package/dist/docs/400-reference/400-cli/400-check.md +20 -0
- package/dist/docs/400-reference/400-cli/500-ai-context.md +102 -0
- package/dist/docs/400-reference/400-cli/600-docs.md +23 -0
- package/dist/docs/400-reference/400-cli/700-desktop.md +35 -0
- package/dist/docs/500-hosted-pages.md +31 -0
- package/dist/exports/client.d.ts +237 -0
- package/dist/exports/client.d.ts.map +1 -0
- package/dist/exports/client.js +1643 -0
- package/dist/exports/client.js.map +1 -0
- package/dist/exports/index-D3_Dpy_T.d.ts +155 -0
- package/dist/exports/index-D3_Dpy_T.d.ts.map +1 -0
- package/dist/exports/index.d.ts +2 -0
- package/dist/exports/index.js +49 -0
- package/dist/exports/index.js.map +1 -0
- package/dist/exports/notifications-kDp16bU_.js +56 -0
- package/dist/exports/notifications-kDp16bU_.js.map +1 -0
- package/dist/exports/server.d.ts +63 -0
- package/dist/exports/server.d.ts.map +1 -0
- package/dist/exports/server.js +1120 -0
- package/dist/exports/server.js.map +1 -0
- package/dist/exports/style.css +368 -0
- package/dist/internal/server/coordinator/server-child.d.ts +1 -0
- package/dist/internal/server/coordinator/server-child.js +3299 -0
- package/dist/internal/server/coordinator/server-child.js.map +1 -0
- package/docs/000-index.md +21 -0
- package/docs/100-introduction/100-what-is-overmux.md +7 -0
- package/docs/100-introduction/200-how-overmux-works.md +7 -0
- package/docs/100-introduction/300-why-overmux.md +22 -0
- package/docs/200-getting-started/100-install-and-run-overmux.md +51 -0
- package/docs/200-getting-started/200-install-overmux-desktop.md +41 -0
- package/docs/200-getting-started/300-install-overmux-pwa.mdx +92 -0
- package/docs/200-getting-started/400-secure-with-https/100-choose-an-https-setup.md +14 -0
- package/docs/200-getting-started/400-secure-with-https/200-tailscale-serve.md +44 -0
- package/docs/200-getting-started/400-secure-with-https/300-cloudflare-tunnel.md +59 -0
- package/docs/200-getting-started/400-secure-with-https/400-self-hosted-reverse-proxy.md +32 -0
- package/docs/300-fundamentals/100-project-structure.md +3 -0
- package/docs/300-fundamentals/200-configuration.md +3 -0
- package/docs/300-fundamentals/300-theming.md +3 -0
- package/docs/300-fundamentals/400-server.md +3 -0
- package/docs/300-fundamentals/500-client.md +3 -0
- package/docs/300-fundamentals/600-operations.md +3 -0
- package/docs/300-fundamentals/700-resources.md +3 -0
- package/docs/300-fundamentals/800-streams.md +3 -0
- package/docs/300-fundamentals/900-authentication-and-security.md +3 -0
- package/docs/400-reference/100-configuration.md +3 -0
- package/docs/400-reference/200-server-api.md +3 -0
- package/docs/400-reference/300-client-api.md +3 -0
- package/docs/400-reference/400-cli/100-serve.md +33 -0
- package/docs/400-reference/400-cli/200-auth.md +52 -0
- package/docs/400-reference/400-cli/300-call.md +28 -0
- package/docs/400-reference/400-cli/400-check.md +20 -0
- package/docs/400-reference/400-cli/500-ai-context.md +102 -0
- package/docs/400-reference/400-cli/600-docs.md +23 -0
- package/docs/400-reference/400-cli/700-desktop.md +35 -0
- package/docs/500-hosted-pages.md +31 -0
- package/package.json +59 -18
- package/src/internal/cli/app.ts +72 -0
- package/src/internal/cli/bin.ts +3 -0
- package/src/internal/cli/commands/ai.ts +44 -0
- package/src/internal/cli/commands/auth.ts +195 -0
- package/src/internal/cli/commands/call.ts +128 -0
- package/src/internal/cli/commands/check.ts +48 -0
- package/src/internal/cli/commands/desktop-installer.ts +446 -0
- package/src/internal/cli/commands/desktop-release.ts +190 -0
- package/src/internal/cli/commands/desktop.ts +47 -0
- package/src/internal/cli/commands/docs.ts +34 -0
- package/src/internal/cli/commands/serve.ts +322 -0
- package/src/internal/cli/environment.ts +54 -0
- package/src/internal/cli/login.ts +46 -0
- package/src/internal/cli/managed-vite.ts +267 -0
- package/src/internal/cli/parse-port.ts +8 -0
- package/src/internal/client/auth/auth-api.ts +53 -0
- package/src/internal/client/auth/auth-shell.css +74 -0
- package/src/internal/client/auth/auth-shell.tsx +167 -0
- package/src/internal/client/auth/entry.tsx +26 -0
- package/src/internal/client/auth/index.html +13 -0
- package/src/internal/client/background-notifications.ts +194 -0
- package/src/internal/client/browser-api.ts +97 -0
- package/src/internal/client/client-definition.ts +184 -0
- package/src/internal/client/commands.tsx +260 -0
- package/src/internal/client/host/browser-log-forwarding.ts +149 -0
- package/src/internal/client/host/hosted-pages/browser-notification-settings.tsx +118 -0
- package/src/internal/client/host/hosted-pages/hosted-page.css +87 -0
- package/src/internal/client/host/hosted-pages/hosted-page.tsx +9 -0
- package/src/internal/client/host/hosted-pages/logout-page.tsx +75 -0
- package/src/internal/client/host/hosted-pages/settings-page.tsx +45 -0
- package/src/internal/client/host/notification-forwarding.ts +22 -0
- package/src/internal/client/host/overmux-host.tsx +200 -0
- package/src/internal/client/host/recovery-screen.css +75 -0
- package/src/internal/client/host/recovery-screen.tsx +17 -0
- package/src/internal/client/host/update-popover.css +82 -0
- package/src/internal/client/host/update-popover.tsx +166 -0
- package/src/internal/client/index.ts +45 -0
- package/src/internal/client/overmux-react.ts +283 -0
- package/src/internal/client/shortcuts.tsx +373 -0
- package/src/internal/client/theme-scope.css +114 -0
- package/src/internal/client/theme-scope.tsx +107 -0
- package/src/internal/client/transport.ts +69 -0
- package/src/internal/client/websocket.ts +441 -0
- package/src/internal/server/auth/auth-http.ts +414 -0
- package/src/internal/server/auth/auth-service.ts +627 -0
- package/src/internal/server/auth/auth-shell-http.ts +90 -0
- package/src/internal/server/auth/instance-control.ts +381 -0
- package/src/internal/server/check-overmux.ts +364 -0
- package/src/internal/server/coordinator/ipc-protocol.ts +44 -0
- package/src/internal/server/coordinator/server-child.ts +108 -0
- package/src/internal/server/coordinator/server-coordinator.ts +262 -0
- package/src/internal/server/coordinator/update-watcher.ts +54 -0
- package/src/internal/server/http/authenticated-http-app-test-helper.ts +45 -0
- package/src/internal/server/http/background-notification-handlers.ts +83 -0
- package/src/internal/server/http/control-handlers.ts +44 -0
- package/src/internal/server/http/create-http-app.ts +53 -0
- package/src/internal/server/http/development-web-backend.ts +83 -0
- package/src/internal/server/http/operation-handler.ts +93 -0
- package/src/internal/server/http/request-logging.ts +34 -0
- package/src/internal/server/http/routes.ts +241 -0
- package/src/internal/server/http/runtime-manifest-handler.ts +12 -0
- package/src/internal/server/index.ts +16 -0
- package/src/internal/server/notifications/background-notification-payload.ts +74 -0
- package/src/internal/server/notifications/background-notification-service.ts +139 -0
- package/src/internal/server/notifications/background-notification-store.ts +162 -0
- package/src/internal/server/notifications/notification-service.ts +70 -0
- package/src/internal/server/notifications/private-json-file.ts +84 -0
- package/src/internal/server/paths.ts +13 -0
- package/src/internal/server/rate-limiter.ts +58 -0
- package/src/internal/server/runtime/create-runtime.ts +87 -0
- package/src/internal/server/runtime/resource-dependency-graph.ts +128 -0
- package/src/internal/server/runtime/runtime-lifecycle.ts +95 -0
- package/src/internal/server/runtime/runtime-operations.ts +78 -0
- package/src/internal/server/runtime/runtime-resources.ts +201 -0
- package/src/internal/server/runtime/runtime-streams.ts +130 -0
- package/src/internal/server/server-logger.ts +110 -0
- package/src/internal/server/server-startup-options.ts +51 -0
- package/src/internal/server/start-application-server.ts +412 -0
- package/src/internal/server/start-overmux-server.ts +26 -0
- package/src/internal/server/test-port.ts +23 -0
- package/src/internal/server/vite-websocket-proxy.ts +201 -0
- package/src/internal/server/websocket-connection.ts +586 -0
- package/src/internal/server/websocket-limits.ts +2 -0
- package/src/internal/server/websocket-server.ts +311 -0
- package/src/internal/shared/background-notifications.ts +37 -0
- package/src/internal/shared/index.ts +2 -0
- package/src/internal/shared/protocol.ts +317 -0
- package/src/internal/shared/routes.ts +3 -0
- package/src/public/ai-context.ts +44 -0
- package/src/public/client.ts +53 -0
- package/src/public/config.ts +287 -0
- package/src/public/contracts.ts +55 -0
- package/src/public/index.ts +57 -0
- package/src/public/notifications.ts +10 -0
- package/src/public/server.ts +16 -0
- package/dist/public/core.ts +0 -119
- package/dist/public/protocol.ts +0 -51
- package/dist/public/terminal.ts +0 -23
- package/dist/web/assets/index-DC___IUw.css +0 -2
- package/dist/web/assets/index-DF9Cptse.js +0 -74
- package/dist/web/assets/terminal-component-BrP-ENHg.css +0 -1
- package/dist/web/assets/terminal-component-DyLEbMrx.js +0 -36
- package/dist/web/index.html +0 -14
|
@@ -0,0 +1,114 @@
|
|
|
1
|
+
@layer theme, base, om;
|
|
2
|
+
|
|
3
|
+
@layer om.components {
|
|
4
|
+
@scope ([data-om-scope]) to ([data-om-scope]) {
|
|
5
|
+
:where(:scope) {
|
|
6
|
+
--_om-color-canvas: #f7f8fa;
|
|
7
|
+
--_om-color-surface: #ffffff;
|
|
8
|
+
--_om-color-panel: #f0f2f5;
|
|
9
|
+
--_om-color-fg: #17202a;
|
|
10
|
+
--_om-color-muted: #5c6875;
|
|
11
|
+
--_om-color-border: #c8ced6;
|
|
12
|
+
--_om-color-accent: #075fd8;
|
|
13
|
+
--_om-color-accent-fg: #ffffff;
|
|
14
|
+
--_om-color-danger: #b42318;
|
|
15
|
+
--_om-color-success: #16794b;
|
|
16
|
+
--_om-resolved-color-success: var(
|
|
17
|
+
--om-color-success,
|
|
18
|
+
var(--_om-color-success)
|
|
19
|
+
);
|
|
20
|
+
color: var(--om-color-fg, var(--_om-color-fg));
|
|
21
|
+
color-scheme: light dark;
|
|
22
|
+
font-family: var(
|
|
23
|
+
--om-font-sans,
|
|
24
|
+
ui-sans-serif,
|
|
25
|
+
system-ui,
|
|
26
|
+
-apple-system,
|
|
27
|
+
BlinkMacSystemFont,
|
|
28
|
+
"Segoe UI",
|
|
29
|
+
sans-serif
|
|
30
|
+
);
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
:where(:scope[data-om-scheme="light"]) {
|
|
34
|
+
color-scheme: light;
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
:where(:scope[data-om-scheme="dark"]) {
|
|
38
|
+
--_om-color-canvas: #101317;
|
|
39
|
+
--_om-color-surface: #171b21;
|
|
40
|
+
--_om-color-panel: #1f252d;
|
|
41
|
+
--_om-color-fg: #f2f4f7;
|
|
42
|
+
--_om-color-muted: #aab3bf;
|
|
43
|
+
--_om-color-border: #46505d;
|
|
44
|
+
--_om-color-accent: #75a7ff;
|
|
45
|
+
--_om-color-accent-fg: #101317;
|
|
46
|
+
--_om-color-danger: #ff8b82;
|
|
47
|
+
--_om-color-success: #65d6a2;
|
|
48
|
+
color-scheme: dark;
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
:where(:scope[data-om-contrast="high"]) {
|
|
52
|
+
--_om-color-canvas: Canvas;
|
|
53
|
+
--_om-color-surface: Canvas;
|
|
54
|
+
--_om-color-panel: Canvas;
|
|
55
|
+
--_om-color-fg: CanvasText;
|
|
56
|
+
--_om-color-muted: CanvasText;
|
|
57
|
+
--_om-color-border: CanvasText;
|
|
58
|
+
--_om-color-accent: Highlight;
|
|
59
|
+
--_om-color-accent-fg: HighlightText;
|
|
60
|
+
--_om-color-danger: Mark;
|
|
61
|
+
--_om-color-success: LinkText;
|
|
62
|
+
}
|
|
63
|
+
|
|
64
|
+
:where([data-om-overlay-root]:empty) {
|
|
65
|
+
display: none;
|
|
66
|
+
}
|
|
67
|
+
|
|
68
|
+
@media (prefers-color-scheme: dark) {
|
|
69
|
+
:where(:scope[data-om-scheme="system"]) {
|
|
70
|
+
--_om-color-canvas: #101317;
|
|
71
|
+
--_om-color-surface: #171b21;
|
|
72
|
+
--_om-color-panel: #1f252d;
|
|
73
|
+
--_om-color-fg: #f2f4f7;
|
|
74
|
+
--_om-color-muted: #aab3bf;
|
|
75
|
+
--_om-color-border: #46505d;
|
|
76
|
+
--_om-color-accent: #75a7ff;
|
|
77
|
+
--_om-color-accent-fg: #101317;
|
|
78
|
+
--_om-color-danger: #ff8b82;
|
|
79
|
+
--_om-color-success: #65d6a2;
|
|
80
|
+
}
|
|
81
|
+
}
|
|
82
|
+
|
|
83
|
+
@media (prefers-contrast: more) {
|
|
84
|
+
:where(:scope[data-om-contrast="auto"]) {
|
|
85
|
+
--_om-color-canvas: Canvas;
|
|
86
|
+
--_om-color-surface: Canvas;
|
|
87
|
+
--_om-color-panel: Canvas;
|
|
88
|
+
--_om-color-fg: CanvasText;
|
|
89
|
+
--_om-color-muted: CanvasText;
|
|
90
|
+
--_om-color-border: CanvasText;
|
|
91
|
+
--_om-color-accent: Highlight;
|
|
92
|
+
--_om-color-accent-fg: HighlightText;
|
|
93
|
+
--_om-color-danger: Mark;
|
|
94
|
+
--_om-color-success: LinkText;
|
|
95
|
+
}
|
|
96
|
+
}
|
|
97
|
+
|
|
98
|
+
@media (forced-colors: active) {
|
|
99
|
+
:where(:scope) {
|
|
100
|
+
--_om-color-canvas: Canvas;
|
|
101
|
+
--_om-color-surface: Canvas;
|
|
102
|
+
--_om-color-panel: Canvas;
|
|
103
|
+
--_om-color-fg: CanvasText;
|
|
104
|
+
--_om-color-muted: CanvasText;
|
|
105
|
+
--_om-color-border: ButtonBorder;
|
|
106
|
+
--_om-color-accent: Highlight;
|
|
107
|
+
--_om-color-accent-fg: HighlightText;
|
|
108
|
+
--_om-color-danger: Mark;
|
|
109
|
+
--_om-color-success: LinkText;
|
|
110
|
+
forced-color-adjust: auto;
|
|
111
|
+
}
|
|
112
|
+
}
|
|
113
|
+
}
|
|
114
|
+
}
|
|
@@ -0,0 +1,107 @@
|
|
|
1
|
+
import "./theme-scope.css";
|
|
2
|
+
|
|
3
|
+
import {
|
|
4
|
+
createContext,
|
|
5
|
+
type CSSProperties,
|
|
6
|
+
type ReactNode,
|
|
7
|
+
useCallback,
|
|
8
|
+
useContext,
|
|
9
|
+
useState,
|
|
10
|
+
} from "react";
|
|
11
|
+
import { createPortal } from "react-dom";
|
|
12
|
+
|
|
13
|
+
export type OvermuxScheme = "dark" | "light" | "system";
|
|
14
|
+
export type OvermuxContrast = "auto" | "high" | "normal";
|
|
15
|
+
|
|
16
|
+
export const overmuxThemeTokens = [
|
|
17
|
+
"--om-color-accent",
|
|
18
|
+
"--om-color-accent-fg",
|
|
19
|
+
"--om-color-border",
|
|
20
|
+
"--om-color-canvas",
|
|
21
|
+
"--om-color-danger",
|
|
22
|
+
"--om-color-fg",
|
|
23
|
+
"--om-color-muted",
|
|
24
|
+
"--om-color-panel",
|
|
25
|
+
"--om-color-success",
|
|
26
|
+
"--om-color-surface",
|
|
27
|
+
"--om-elevation",
|
|
28
|
+
"--om-focus-ring",
|
|
29
|
+
"--om-font-mono",
|
|
30
|
+
"--om-font-sans",
|
|
31
|
+
"--om-motion-duration",
|
|
32
|
+
"--om-radius",
|
|
33
|
+
"--om-spacing",
|
|
34
|
+
] as const;
|
|
35
|
+
|
|
36
|
+
export type OvermuxThemeToken = (typeof overmuxThemeTokens)[number];
|
|
37
|
+
|
|
38
|
+
export type OvermuxStyle = CSSProperties &
|
|
39
|
+
Partial<Record<OvermuxThemeToken, number | string>>;
|
|
40
|
+
|
|
41
|
+
export type OvermuxExternalPortalContainer = {
|
|
42
|
+
container: HTMLElement;
|
|
43
|
+
scopeAttributesAndVariables: "caller-owned";
|
|
44
|
+
};
|
|
45
|
+
|
|
46
|
+
export type OvermuxPortalProps = {
|
|
47
|
+
children: ReactNode;
|
|
48
|
+
external?: OvermuxExternalPortalContainer;
|
|
49
|
+
};
|
|
50
|
+
|
|
51
|
+
export type OvermuxThemeScopeProps = {
|
|
52
|
+
children: ReactNode;
|
|
53
|
+
className?: string;
|
|
54
|
+
contrast?: OvermuxContrast;
|
|
55
|
+
scheme?: OvermuxScheme;
|
|
56
|
+
style?: OvermuxStyle;
|
|
57
|
+
};
|
|
58
|
+
|
|
59
|
+
const PortalRootContext = createContext<HTMLElement | null | undefined>(
|
|
60
|
+
undefined,
|
|
61
|
+
);
|
|
62
|
+
|
|
63
|
+
export const useOvermuxPortalContainer = (
|
|
64
|
+
external?: OvermuxExternalPortalContainer,
|
|
65
|
+
) => {
|
|
66
|
+
const scopeRoot = useContext(PortalRootContext);
|
|
67
|
+
if (external) {
|
|
68
|
+
return external.container;
|
|
69
|
+
}
|
|
70
|
+
if (scopeRoot !== undefined) {
|
|
71
|
+
return scopeRoot;
|
|
72
|
+
}
|
|
73
|
+
return typeof document === "undefined" ? null : document.body;
|
|
74
|
+
};
|
|
75
|
+
|
|
76
|
+
export const OvermuxPortal = ({ children, external }: OvermuxPortalProps) => {
|
|
77
|
+
const container = useOvermuxPortalContainer(external);
|
|
78
|
+
return container ? createPortal(children, container) : null;
|
|
79
|
+
};
|
|
80
|
+
|
|
81
|
+
export const OvermuxThemeScope = ({
|
|
82
|
+
children,
|
|
83
|
+
className,
|
|
84
|
+
contrast = "auto",
|
|
85
|
+
scheme = "system",
|
|
86
|
+
style,
|
|
87
|
+
}: OvermuxThemeScopeProps) => {
|
|
88
|
+
const [portalRoot, setPortalRoot] = useState<HTMLDivElement | null>(null);
|
|
89
|
+
const capturePortalRoot = useCallback((element: HTMLDivElement | null) => {
|
|
90
|
+
setPortalRoot(element);
|
|
91
|
+
}, []);
|
|
92
|
+
|
|
93
|
+
return (
|
|
94
|
+
<div
|
|
95
|
+
className={className}
|
|
96
|
+
data-om-contrast={contrast}
|
|
97
|
+
data-om-scheme={scheme}
|
|
98
|
+
data-om-scope=""
|
|
99
|
+
style={style}
|
|
100
|
+
>
|
|
101
|
+
<PortalRootContext.Provider value={portalRoot}>
|
|
102
|
+
{children}
|
|
103
|
+
</PortalRootContext.Provider>
|
|
104
|
+
<div data-om-overlay-root="" ref={capturePortalRoot} />
|
|
105
|
+
</div>
|
|
106
|
+
);
|
|
107
|
+
};
|
|
@@ -0,0 +1,69 @@
|
|
|
1
|
+
import { createContext, useContext } from "react";
|
|
2
|
+
|
|
3
|
+
import {
|
|
4
|
+
createWebSocketTransport,
|
|
5
|
+
type WebSocketTransport,
|
|
6
|
+
type TransportStatus,
|
|
7
|
+
} from "./websocket";
|
|
8
|
+
|
|
9
|
+
export type ClientTransport = WebSocketTransport & {
|
|
10
|
+
invokeOperation: (input: {
|
|
11
|
+
input?: unknown;
|
|
12
|
+
name: string;
|
|
13
|
+
signal?: AbortSignal;
|
|
14
|
+
}) => Promise<unknown>;
|
|
15
|
+
};
|
|
16
|
+
|
|
17
|
+
export const TransportContext = createContext<ClientTransport | undefined>(
|
|
18
|
+
undefined,
|
|
19
|
+
);
|
|
20
|
+
|
|
21
|
+
export const useTransport = () => {
|
|
22
|
+
const transport = useContext(TransportContext);
|
|
23
|
+
if (!transport) {
|
|
24
|
+
throw new Error(
|
|
25
|
+
"Overmux transport hooks must be used inside an active Overmux client runtime",
|
|
26
|
+
);
|
|
27
|
+
}
|
|
28
|
+
return transport;
|
|
29
|
+
};
|
|
30
|
+
|
|
31
|
+
const operationError = async (response: Response) => {
|
|
32
|
+
const body = await response.text();
|
|
33
|
+
try {
|
|
34
|
+
const error = (JSON.parse(body) as { error?: unknown }).error;
|
|
35
|
+
if (typeof error === "string") {
|
|
36
|
+
return new Error(error);
|
|
37
|
+
}
|
|
38
|
+
} catch {}
|
|
39
|
+
return new Error(
|
|
40
|
+
`Operation request failed: ${response.status} ${response.statusText}`,
|
|
41
|
+
);
|
|
42
|
+
};
|
|
43
|
+
|
|
44
|
+
export const createClientTransport = ({
|
|
45
|
+
createSocket,
|
|
46
|
+
fetch: fetchRequest = globalThis.fetch,
|
|
47
|
+
}: {
|
|
48
|
+
createSocket?: () => WebSocket;
|
|
49
|
+
fetch?: typeof globalThis.fetch;
|
|
50
|
+
} = {}): ClientTransport => ({
|
|
51
|
+
...createWebSocketTransport({ createSocket }),
|
|
52
|
+
invokeOperation: async ({ input, name, signal }) => {
|
|
53
|
+
const response = await fetchRequest(
|
|
54
|
+
`/api/operations/${encodeURIComponent(name)}`,
|
|
55
|
+
{
|
|
56
|
+
body: input === undefined ? undefined : JSON.stringify(input),
|
|
57
|
+
headers: { "content-type": "application/json" },
|
|
58
|
+
method: "POST",
|
|
59
|
+
signal,
|
|
60
|
+
},
|
|
61
|
+
);
|
|
62
|
+
if (!response.ok) {
|
|
63
|
+
throw await operationError(response);
|
|
64
|
+
}
|
|
65
|
+
return response.status === 204 ? undefined : response.json();
|
|
66
|
+
},
|
|
67
|
+
});
|
|
68
|
+
|
|
69
|
+
export type { WebSocketTransport, TransportStatus };
|