devframe 0.5.3 → 0.6.0-beta.1
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/dist/{_shared-CUFqO4kJ.mjs → _shared-bWRzeSa0.mjs} +2 -3
- package/dist/adapters/build.d.mts +1 -1
- package/dist/adapters/build.mjs +7 -7
- package/dist/adapters/cli.d.mts +1 -1
- package/dist/adapters/cli.mjs +2 -2
- package/dist/adapters/dev.d.mts +8 -2
- package/dist/adapters/dev.mjs +1 -1
- package/dist/adapters/embedded.d.mts +1 -1
- package/dist/adapters/mcp.d.mts +1 -1
- package/dist/adapters/mcp.mjs +4 -4
- package/dist/client/index.d.mts +148 -6
- package/dist/client/index.mjs +272 -49
- package/dist/constants.d.mts +17 -1
- package/dist/constants.mjs +17 -1
- package/dist/context-3x_bgBgZ.mjs +48 -0
- package/dist/{context-DTRcO_UH.d.mts → context-o-TwncyP.d.mts} +1 -1
- package/dist/{dev-Cv43GfqM.mjs → dev-CSpLSEVh.mjs} +39 -13
- package/dist/{devframe-BuR6n9ZD.d.mts → devframe-BwfavB78.d.mts} +365 -15
- package/dist/{diagnostics-GitRGKbr.mjs → diagnostics-BXwBQmoN.mjs} +1 -1
- package/dist/{dump-9lKIJTLh.mjs → dump-DoXkj4ku.mjs} +1 -1
- package/dist/helpers/vite.d.mts +1 -1
- package/dist/helpers/vite.mjs +11 -11
- package/dist/{host-h3-Dgpgr1Ul.mjs → host-h3-C5SZlk03.mjs} +134 -6
- package/dist/{index-C7M1hnvL.d.mts → index-CxaPKDXX.d.mts} +2 -2
- package/dist/{index-DH2sBIwd.d.mts → index-DXHWuwJk.d.mts} +1 -1
- package/dist/index.d.mts +4 -4
- package/dist/index.mjs +1 -1
- package/dist/node/auth.d.mts +43 -23
- package/dist/node/auth.mjs +84 -37
- package/dist/node/hub-internals.d.mts +2 -2
- package/dist/node/hub-internals.mjs +2 -2
- package/dist/node/index.d.mts +22 -6
- package/dist/node/index.mjs +4 -4
- package/dist/recipes/open-helpers.d.mts +1 -1
- package/dist/recipes/open-helpers.mjs +3 -3
- package/dist/revoke-ENfxWkFK.mjs +79 -0
- package/dist/rpc/dump.d.mts +1 -1
- package/dist/rpc/dump.mjs +1 -1
- package/dist/rpc/index.d.mts +3 -3
- package/dist/rpc/index.mjs +4 -4
- package/dist/rpc/transports/ws-client.d.mts +1 -1
- package/dist/rpc/transports/ws-client.mjs +2 -2
- package/dist/rpc/transports/ws-server.d.mts +2 -2
- package/dist/rpc/transports/ws-server.mjs +124 -60
- package/dist/{serialization-BD_qXGjd.mjs → serialization-DpLXCy13.mjs} +1 -1
- package/dist/{server-wHlpcdZ9.d.mts → server-oju7PTi2.d.mts} +30 -3
- package/dist/{server-BBaBJaUL.mjs → server-wyY3zh67.mjs} +18 -14
- package/dist/{shared-state-u0y123fi.mjs → shared-state-D4PPieA0.mjs} +4 -4
- package/dist/{shared-state-BlBNYziY.mjs → storage-l2ezeend.mjs} +128 -6
- package/dist/types/index.d.mts +4 -4
- package/dist/{types-BkkQ0Txg.d.mts → types-DZEx4ffs.d.mts} +9 -1
- package/dist/utils/crypto-token.d.mts +24 -0
- package/dist/utils/crypto-token.mjs +45 -0
- package/dist/utils/events.d.mts +1 -1
- package/dist/utils/hash.mjs +1 -1
- package/dist/utils/launch-editor.mjs +1 -1
- package/dist/utils/open.mjs +1 -1
- package/dist/utils/scope.d.mts +11 -0
- package/dist/utils/scope.mjs +15 -0
- package/dist/utils/shared-state.d.mts +1 -1
- package/dist/utils/shared-state.mjs +1 -1
- package/dist/utils/streaming-channel.d.mts +1 -1
- package/dist/utils/structured-clone.mjs +1 -1
- package/dist/{ws-client-CVYX9niP.d.mts → ws-client-D0z0pOhn.d.mts} +1 -1
- package/dist/ws-server-BVVMDo2n.d.mts +103 -0
- package/package.json +12 -7
- package/skills/devframe/SKILL.md +123 -23
- package/skills/devframe/templates/counter-devframe.ts +14 -4
- package/skills/devframe/templates/spa-devframe.ts +13 -3
- package/skills/devframe/templates/vite-client.ts +3 -2
- package/dist/context-DaKmhhHY.mjs +0 -164
- package/dist/revoke-CL0LSAN9.mjs +0 -803
- package/dist/utils/human-id.d.mts +0 -8
- package/dist/utils/human-id.mjs +0 -769
- package/dist/ws-server-C1LjmRnp.d.mts +0 -61
- /package/dist/{define-CW9gLnyG.mjs → define-BLWPsH6y.mjs} +0 -0
- /package/dist/{diagnostics-reporter-CBBZwoMv.mjs → diagnostics-reporter-CsIG85Q5.mjs} +0 -0
- /package/dist/{hash-bwOD8RgU.mjs → hash-DFc5WwhO.mjs} +0 -0
- /package/dist/{launch-editor-BbNhtg7b.mjs → launch-editor-CgXBgviI.mjs} +0 -0
- /package/dist/{open-DiQn6zCH.mjs → open-Dusa2Zzd.mjs} +0 -0
- /package/dist/{structured-clone-PdCZwt7F.mjs → structured-clone-CeZOHvkd.mjs} +0 -0
- /package/dist/{structured-clone-jegjz0hM.mjs → structured-clone-XpHLZ8nr.mjs} +0 -0
- /package/dist/{transports-DTFoMUbE.mjs → transports-BmDVn4SF.mjs} +0 -0
|
@@ -2,18 +2,28 @@
|
|
|
2
2
|
// Host adapters (e.g. the `vite` adapter for Vite DevTools) auto-derive their
|
|
3
3
|
// mount entry from `id` / `name` / `icon`.
|
|
4
4
|
import { defineDevframe, defineRpcFunction } from 'devframe'
|
|
5
|
+
// Recommended: source version/packageName/homepage/description from your
|
|
6
|
+
// package.json so the published metadata stays in sync. The import-attribute
|
|
7
|
+
// form resolves under both bundlers and Node's native TypeScript execution.
|
|
8
|
+
import pkg from '../package.json' with { type: 'json' }
|
|
5
9
|
import * as v from 'valibot'
|
|
6
10
|
|
|
7
11
|
export default defineDevframe({
|
|
8
12
|
id: 'my-inspector',
|
|
9
13
|
name: 'My Inspector',
|
|
14
|
+
version: pkg.version,
|
|
15
|
+
packageName: pkg.name,
|
|
16
|
+
homepage: pkg.homepage,
|
|
17
|
+
description: pkg.description,
|
|
10
18
|
icon: 'ph:magnifying-glass-duotone',
|
|
11
19
|
setup(ctx) {
|
|
12
|
-
ctx.
|
|
13
|
-
|
|
20
|
+
const my = ctx.scope('my-inspector')
|
|
21
|
+
my.rpc.register(defineRpcFunction({
|
|
22
|
+
name: 'analyze', // -> my-inspector:analyze
|
|
14
23
|
type: 'query',
|
|
15
24
|
args: [v.object({ url: v.string() })],
|
|
16
|
-
|
|
25
|
+
returns: v.object({ url: v.string(), verdict: v.literal('ok') }),
|
|
26
|
+
handler: ({ url }: { url: string }) => {
|
|
17
27
|
// Server-side implementation (used by CLI/build adapters).
|
|
18
28
|
return { url, verdict: 'ok' as const }
|
|
19
29
|
},
|
|
@@ -2,9 +2,10 @@
|
|
|
2
2
|
import { connectDevframe } from 'devframe/client'
|
|
3
3
|
|
|
4
4
|
async function main() {
|
|
5
|
-
|
|
5
|
+
// Scope the client to your devframe id — calls are namespaced for you.
|
|
6
|
+
const my = (await connectDevframe()).scope('my-inspector')
|
|
6
7
|
// The method names below are just examples — replace with your own.
|
|
7
|
-
const data = await rpc.call('
|
|
8
|
+
const data = await my.rpc.call('getStats' as any)
|
|
8
9
|
document.getElementById('root')!.textContent = JSON.stringify(data)
|
|
9
10
|
}
|
|
10
11
|
|
|
@@ -1,164 +0,0 @@
|
|
|
1
|
-
import { i as diagnostics, t as createSharedState } from "./shared-state-BlBNYziY.mjs";
|
|
2
|
-
import { n as revokeAuthToken, r as humanId, t as revokeActiveConnectionsForToken } from "./revoke-CL0LSAN9.mjs";
|
|
3
|
-
import fs from "node:fs";
|
|
4
|
-
import { dirname, join } from "pathe";
|
|
5
|
-
//#region ../../node_modules/.pnpm/perfect-debounce@2.1.0/node_modules/perfect-debounce/dist/index.mjs
|
|
6
|
-
const DEBOUNCE_DEFAULTS = { trailing: true };
|
|
7
|
-
/**
|
|
8
|
-
Debounce functions
|
|
9
|
-
@param fn - Promise-returning/async function to debounce.
|
|
10
|
-
@param wait - Milliseconds to wait before calling `fn`. Default value is 25ms
|
|
11
|
-
@returns A function that delays calling `fn` until after `wait` milliseconds have elapsed since the last time it was called.
|
|
12
|
-
@example
|
|
13
|
-
```
|
|
14
|
-
import { debounce } from 'perfect-debounce';
|
|
15
|
-
const expensiveCall = async input => input;
|
|
16
|
-
const debouncedFn = debounce(expensiveCall, 200);
|
|
17
|
-
for (const number of [1, 2, 3]) {
|
|
18
|
-
console.log(await debouncedFn(number));
|
|
19
|
-
}
|
|
20
|
-
//=> 1
|
|
21
|
-
//=> 2
|
|
22
|
-
//=> 3
|
|
23
|
-
```
|
|
24
|
-
*/
|
|
25
|
-
function debounce(fn, wait = 25, options = {}) {
|
|
26
|
-
options = {
|
|
27
|
-
...DEBOUNCE_DEFAULTS,
|
|
28
|
-
...options
|
|
29
|
-
};
|
|
30
|
-
if (!Number.isFinite(wait)) throw new TypeError("Expected `wait` to be a finite number");
|
|
31
|
-
let leadingValue;
|
|
32
|
-
let timeout;
|
|
33
|
-
let resolveList = [];
|
|
34
|
-
let currentPromise;
|
|
35
|
-
let trailingArgs;
|
|
36
|
-
const applyFn = (_this, args) => {
|
|
37
|
-
currentPromise = _applyPromised(fn, _this, args);
|
|
38
|
-
currentPromise.finally(() => {
|
|
39
|
-
currentPromise = null;
|
|
40
|
-
if (options.trailing && trailingArgs && !timeout) {
|
|
41
|
-
const promise = applyFn(_this, trailingArgs);
|
|
42
|
-
trailingArgs = null;
|
|
43
|
-
return promise;
|
|
44
|
-
}
|
|
45
|
-
});
|
|
46
|
-
return currentPromise;
|
|
47
|
-
};
|
|
48
|
-
const debounced = function(...args) {
|
|
49
|
-
if (options.trailing) trailingArgs = args;
|
|
50
|
-
if (currentPromise) return currentPromise;
|
|
51
|
-
return new Promise((resolve) => {
|
|
52
|
-
const shouldCallNow = !timeout && options.leading;
|
|
53
|
-
clearTimeout(timeout);
|
|
54
|
-
timeout = setTimeout(() => {
|
|
55
|
-
timeout = null;
|
|
56
|
-
const promise = options.leading ? leadingValue : applyFn(this, args);
|
|
57
|
-
trailingArgs = null;
|
|
58
|
-
for (const _resolve of resolveList) _resolve(promise);
|
|
59
|
-
resolveList = [];
|
|
60
|
-
}, wait);
|
|
61
|
-
if (shouldCallNow) {
|
|
62
|
-
leadingValue = applyFn(this, args);
|
|
63
|
-
resolve(leadingValue);
|
|
64
|
-
} else resolveList.push(resolve);
|
|
65
|
-
});
|
|
66
|
-
};
|
|
67
|
-
const _clearTimeout = (timer) => {
|
|
68
|
-
if (timer) {
|
|
69
|
-
clearTimeout(timer);
|
|
70
|
-
timeout = null;
|
|
71
|
-
}
|
|
72
|
-
};
|
|
73
|
-
debounced.isPending = () => !!timeout;
|
|
74
|
-
debounced.cancel = () => {
|
|
75
|
-
_clearTimeout(timeout);
|
|
76
|
-
resolveList = [];
|
|
77
|
-
trailingArgs = null;
|
|
78
|
-
};
|
|
79
|
-
debounced.flush = () => {
|
|
80
|
-
_clearTimeout(timeout);
|
|
81
|
-
if (!trailingArgs || currentPromise) return;
|
|
82
|
-
const args = trailingArgs;
|
|
83
|
-
trailingArgs = null;
|
|
84
|
-
return applyFn(this, args);
|
|
85
|
-
};
|
|
86
|
-
return debounced;
|
|
87
|
-
}
|
|
88
|
-
async function _applyPromised(fn, _this, args) {
|
|
89
|
-
return await fn.apply(_this, args);
|
|
90
|
-
}
|
|
91
|
-
//#endregion
|
|
92
|
-
//#region src/node/storage.ts
|
|
93
|
-
function createStorage(options) {
|
|
94
|
-
const { mergeInitialValue = (initialValue, savedValue) => ({
|
|
95
|
-
...initialValue,
|
|
96
|
-
...savedValue
|
|
97
|
-
}), debounce: debounceTime = 100 } = options;
|
|
98
|
-
let initialValue = options.initialValue;
|
|
99
|
-
if (fs.existsSync(options.filepath)) try {
|
|
100
|
-
const savedValue = JSON.parse(fs.readFileSync(options.filepath, "utf-8"));
|
|
101
|
-
initialValue = mergeInitialValue ? mergeInitialValue(options.initialValue, savedValue) : savedValue;
|
|
102
|
-
} catch (error) {
|
|
103
|
-
diagnostics.DF0012({
|
|
104
|
-
filepath: options.filepath,
|
|
105
|
-
cause: error
|
|
106
|
-
}, { method: "warn" });
|
|
107
|
-
initialValue = options.initialValue;
|
|
108
|
-
}
|
|
109
|
-
const state = createSharedState({
|
|
110
|
-
initialValue,
|
|
111
|
-
enablePatches: false
|
|
112
|
-
});
|
|
113
|
-
state.on("updated", debounce((newState) => {
|
|
114
|
-
fs.mkdirSync(dirname(options.filepath), { recursive: true });
|
|
115
|
-
fs.writeFileSync(options.filepath, `${JSON.stringify(newState, null, 2)}\n`);
|
|
116
|
-
}, debounceTime));
|
|
117
|
-
return state;
|
|
118
|
-
}
|
|
119
|
-
//#endregion
|
|
120
|
-
//#region src/node/hub-internals/context.ts
|
|
121
|
-
const internalContextMap = /* @__PURE__ */ new WeakMap();
|
|
122
|
-
function getInternalContext(context) {
|
|
123
|
-
if (!internalContextMap.has(context)) {
|
|
124
|
-
const storage = createStorage({
|
|
125
|
-
filepath: join(context.host.getStorageDir("global"), "auth.json"),
|
|
126
|
-
initialValue: { trusted: {} }
|
|
127
|
-
});
|
|
128
|
-
const remoteTokens = /* @__PURE__ */ new Map();
|
|
129
|
-
function revokeRemoteToken(token) {
|
|
130
|
-
if (!remoteTokens.delete(token)) return;
|
|
131
|
-
revokeActiveConnectionsForToken(context, token);
|
|
132
|
-
}
|
|
133
|
-
const internalContext = {
|
|
134
|
-
storage: { auth: storage },
|
|
135
|
-
revokeAuthToken: (token) => revokeAuthToken(context, storage, token),
|
|
136
|
-
remoteTokens,
|
|
137
|
-
allocateRemoteToken(dockId, origin, originLock) {
|
|
138
|
-
const token = humanId();
|
|
139
|
-
remoteTokens.set(token, {
|
|
140
|
-
dockId,
|
|
141
|
-
origin,
|
|
142
|
-
originLock
|
|
143
|
-
});
|
|
144
|
-
return token;
|
|
145
|
-
},
|
|
146
|
-
revokeRemoteToken,
|
|
147
|
-
revokeRemoteTokensForDock(dockId) {
|
|
148
|
-
const tokensToRevoke = [];
|
|
149
|
-
for (const [token, record] of remoteTokens) if (record.dockId === dockId) tokensToRevoke.push(token);
|
|
150
|
-
for (const token of tokensToRevoke) revokeRemoteToken(token);
|
|
151
|
-
},
|
|
152
|
-
isRemoteTokenTrusted(token, requestOrigin) {
|
|
153
|
-
const record = remoteTokens.get(token);
|
|
154
|
-
if (!record) return false;
|
|
155
|
-
if (!record.originLock) return true;
|
|
156
|
-
return !!requestOrigin && record.origin === requestOrigin;
|
|
157
|
-
}
|
|
158
|
-
};
|
|
159
|
-
internalContextMap.set(context, internalContext);
|
|
160
|
-
}
|
|
161
|
-
return internalContextMap.get(context);
|
|
162
|
-
}
|
|
163
|
-
//#endregion
|
|
164
|
-
export { internalContextMap as n, createStorage as r, getInternalContext as t };
|