@testsmith/api-spector 0.9.1 → 0.9.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/out/main/chunks/{broker-client-JU-AwkVE.js → broker-client-Cl6Fu3oD.js} +1 -1
- package/out/main/chunks/{handle-_4XMUlwm.js → handle-HQp1EXf8.js} +33 -1
- package/out/main/chunks/{import-ujxXe3Uu.js → import-DVpFH9Wb.js} +2 -2
- package/out/main/chunks/{perf-run-BEbf2piB.js → perf-run-BNunvZsG.js} +1 -1
- package/out/main/chunks/{request-exec-DroNv29-.js → request-exec-B8DJ8Id2.js} +1 -1
- package/out/main/chunks/{soap-handler-BF5ii0UV.js → soap-handler-D_Hj9e8S.js} +2 -2
- package/out/main/contract.js +3 -3
- package/out/main/flow.js +3 -3
- package/out/main/index.js +35 -11
- package/out/main/lib.js +2 -2
- package/out/main/perf-worker.js +3 -3
- package/out/main/perf.js +4 -4
- package/out/main/register-handlers.js +217 -5
- package/out/main/runner.js +3 -3
- package/out/main/wsdl.js +3 -3
- package/out/preload/index.js +58 -1
- package/out/renderer/assets/{GraphQLEditor-CJm8glW5.js → GraphQLEditor-RRDuQogA.js} +1 -1
- package/out/renderer/assets/{SoapEditor-C2eMs7-Z.js → SoapEditor-BncNQmjP.js} +1 -1
- package/out/renderer/assets/index--T34lt1s.css +627 -0
- package/out/renderer/assets/{index-Bf9-CiTh.js → index-C6_D_4og.js} +822 -144
- package/out/renderer/index.html +2 -2
- package/package.json +1 -1
- package/out/renderer/assets/index-C5qn-ccU.css +0 -627
|
@@ -3,7 +3,7 @@ const promises = require("node:fs/promises");
|
|
|
3
3
|
const path = require("node:path");
|
|
4
4
|
const crypto = require("node:crypto");
|
|
5
5
|
const undici = require("undici");
|
|
6
|
-
const requestExec = require("./request-exec-
|
|
6
|
+
const requestExec = require("./request-exec-B8DJ8Id2.js");
|
|
7
7
|
const Ajv = require("ajv");
|
|
8
8
|
const jsYaml = require("js-yaml");
|
|
9
9
|
require("node:http");
|
|
@@ -8,6 +8,13 @@ const IPC = {
|
|
|
8
8
|
/** Event (main→renderer): a `spector://open-from-git?url=…` deep link was
|
|
9
9
|
* received; the renderer runs the same open-from-Git flow as the button. */
|
|
10
10
|
openFromGitDeepLink: "file:openFromGitDeepLink",
|
|
11
|
+
/** Event (main→renderer): a `spector://import?token=…` deep link was
|
|
12
|
+
* received; the renderer imports the shared collection/request. */
|
|
13
|
+
importShareDeepLink: "file:importShareDeepLink",
|
|
14
|
+
/** Serialize the open workspace to a secret-free snapshot for cloud sync. */
|
|
15
|
+
serializeWorkspace: "file:serializeWorkspace",
|
|
16
|
+
/** Apply a pulled snapshot to disk (backs up first; merges local secrets). */
|
|
17
|
+
applyWorkspaceSnapshot: "file:applyWorkspaceSnapshot",
|
|
11
18
|
getLastWorkspace: "file:getLastWorkspace",
|
|
12
19
|
getRecentWorkspaces: "file:getRecentWorkspaces",
|
|
13
20
|
saveWorkspace: "file:saveWorkspace",
|
|
@@ -240,6 +247,10 @@ const IPC = {
|
|
|
240
247
|
branches: "git:branches",
|
|
241
248
|
checkout: "git:checkout",
|
|
242
249
|
deleteBranch: "git:deleteBranch",
|
|
250
|
+
stashList: "git:stashList",
|
|
251
|
+
stash: "git:stash",
|
|
252
|
+
stashPop: "git:stashPop",
|
|
253
|
+
stashDrop: "git:stashDrop",
|
|
243
254
|
fetch: "git:fetch",
|
|
244
255
|
pull: "git:pull",
|
|
245
256
|
push: "git:push",
|
|
@@ -308,7 +319,28 @@ const IPC = {
|
|
|
308
319
|
/** Open a flow's page in the cloud UI. */
|
|
309
320
|
openFlow: "cloud:openFlow",
|
|
310
321
|
/** Open the cloud deployment matrix in the browser. */
|
|
311
|
-
openMatrix: "cloud:openMatrix"
|
|
322
|
+
openMatrix: "cloud:openMatrix",
|
|
323
|
+
/** Share a collection as a public read-only link (POST /api/share). */
|
|
324
|
+
shareCollection: "cloud:shareCollection",
|
|
325
|
+
/** Share a single request as a public read-only link (POST /api/share). */
|
|
326
|
+
shareRequest: "cloud:shareRequest",
|
|
327
|
+
/** Share a folder subtree as a public read-only link (POST /api/share). */
|
|
328
|
+
shareFolder: "cloud:shareFolder",
|
|
329
|
+
/** Fetch a shared collection/request by token for import (GET /api/share/{token}). */
|
|
330
|
+
importShare: "cloud:importShare",
|
|
331
|
+
/** Look up an existing share for a local collection/request (GET /api/share-lookup). */
|
|
332
|
+
shareLookup: "cloud:shareLookup",
|
|
333
|
+
/** Restrict a share: set/clear its expiry (PATCH /api/share/{token}). */
|
|
334
|
+
shareUpdate: "cloud:shareUpdate",
|
|
335
|
+
/** Revoke a share link (DELETE /api/share/{token}). */
|
|
336
|
+
shareRevoke: "cloud:shareRevoke",
|
|
337
|
+
/** Cloud-synced workspaces (collaborate without git). */
|
|
338
|
+
workspaceList: "cloud:workspaceList",
|
|
339
|
+
workspaceCreate: "cloud:workspaceCreate",
|
|
340
|
+
workspacePull: "cloud:workspacePull",
|
|
341
|
+
workspacePush: "cloud:workspacePush",
|
|
342
|
+
workspaceVersions: "cloud:workspaceVersions",
|
|
343
|
+
workspaceRestore: "cloud:workspaceRestore"
|
|
312
344
|
}
|
|
313
345
|
};
|
|
314
346
|
function handleIpc(ipc, channel, fn) {
|
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, Symbol.toStringTag, { value: "Module" });
|
|
3
3
|
const uuid = require("uuid");
|
|
4
|
-
const soapHandler = require("./soap-handler-
|
|
5
|
-
require("./handle-
|
|
4
|
+
const soapHandler = require("./soap-handler-D_Hj9e8S.js");
|
|
5
|
+
require("./handle-HQp1EXf8.js");
|
|
6
6
|
require("node:https");
|
|
7
7
|
require("node:http");
|
|
8
8
|
require("@xmldom/xmldom");
|
|
@@ -24,7 +24,7 @@ var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__ge
|
|
|
24
24
|
const undici = require("undici");
|
|
25
25
|
const promises$1 = require("fs/promises");
|
|
26
26
|
const nodeTls = require("tls");
|
|
27
|
-
const handle = require("./handle-
|
|
27
|
+
const handle = require("./handle-HQp1EXf8.js");
|
|
28
28
|
const fs = require("node:fs");
|
|
29
29
|
const os = require("node:os");
|
|
30
30
|
const path = require("node:path");
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
"use strict";
|
|
2
|
-
const handle = require("./handle-
|
|
2
|
+
const handle = require("./handle-HQp1EXf8.js");
|
|
3
3
|
const https = require("node:https");
|
|
4
4
|
const http = require("node:http");
|
|
5
5
|
const xmldom = require("@xmldom/xmldom");
|
|
@@ -324,7 +324,7 @@ function registerSoapHandlers(ipc) {
|
|
|
324
324
|
handle.handleIpc(ipc, handle.IPC.wsdl.import, async (_event, opts) => {
|
|
325
325
|
const { validateWsdlImport } = await Promise.resolve().then(() => require("./ipc-validate-sqUFqRmE.js"));
|
|
326
326
|
validateWsdlImport(opts);
|
|
327
|
-
const { importWsdl } = await Promise.resolve().then(() => require("./import-
|
|
327
|
+
const { importWsdl } = await Promise.resolve().then(() => require("./import-DVpFH9Wb.js"));
|
|
328
328
|
const wsdlText = opts.xml ?? (opts.url ? await fetchUrl(opts.url) : "");
|
|
329
329
|
if (!wsdlText) throw new Error("wsdl:import requires either `url` or `xml`");
|
|
330
330
|
return importWsdl(wsdlText, { name: opts.name, existingMockPorts: opts.existingMockPorts });
|
package/out/main/contract.js
CHANGED
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
"use strict";
|
|
3
3
|
const promises = require("node:fs/promises");
|
|
4
4
|
const path = require("node:path");
|
|
5
|
-
const brokerClient = require("./chunks/broker-client-
|
|
5
|
+
const brokerClient = require("./chunks/broker-client-Cl6Fu3oD.js");
|
|
6
6
|
const escape = require("./chunks/escape-DDVAlOvZ.js");
|
|
7
7
|
const crypto = require("node:crypto");
|
|
8
8
|
const undici = require("undici");
|
|
@@ -11,10 +11,10 @@ const cliCommon = require("./chunks/cli-common-GnihVSjU.js");
|
|
|
11
11
|
const node_child_process = require("node:child_process");
|
|
12
12
|
const jsYaml = require("js-yaml");
|
|
13
13
|
const environments = require("./chunks/environments-iM3SUM-4.js");
|
|
14
|
-
require("./chunks/request-exec-
|
|
14
|
+
require("./chunks/request-exec-B8DJ8Id2.js");
|
|
15
15
|
require("fs/promises");
|
|
16
16
|
require("tls");
|
|
17
|
-
require("./chunks/handle-
|
|
17
|
+
require("./chunks/handle-HQp1EXf8.js");
|
|
18
18
|
require("node:fs");
|
|
19
19
|
require("dayjs");
|
|
20
20
|
require("node:vm");
|
package/out/main/flow.js
CHANGED
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
"use strict";
|
|
3
3
|
const promises = require("node:fs/promises");
|
|
4
4
|
const path = require("node:path");
|
|
5
|
-
const requestExec = require("./chunks/request-exec-
|
|
5
|
+
const requestExec = require("./chunks/request-exec-B8DJ8Id2.js");
|
|
6
6
|
const requestCollection = require("./chunks/request-collection-zRRUfg0X.js");
|
|
7
7
|
const environments = require("./chunks/environments-iM3SUM-4.js");
|
|
8
8
|
const flowEngine = require("./chunks/flow-engine-BxwjEy37.js");
|
|
@@ -10,7 +10,7 @@ const cliCommon = require("./chunks/cli-common-GnihVSjU.js");
|
|
|
10
10
|
require("undici");
|
|
11
11
|
require("fs/promises");
|
|
12
12
|
require("tls");
|
|
13
|
-
require("./chunks/handle-
|
|
13
|
+
require("./chunks/handle-HQp1EXf8.js");
|
|
14
14
|
require("node:fs");
|
|
15
15
|
require("node:os");
|
|
16
16
|
require("node:crypto");
|
|
@@ -281,7 +281,7 @@ async function main() {
|
|
|
281
281
|
const envName = args.environment ?? args.env;
|
|
282
282
|
const env = environments.selectEnvironment(workspace, environments$1, envName);
|
|
283
283
|
const verbose = Boolean(args.verbose);
|
|
284
|
-
const version = `v${"0.9.
|
|
284
|
+
const version = `v${"0.9.2"}`;
|
|
285
285
|
console.log("");
|
|
286
286
|
console.log(cliCommon.color(" API Flow Runner" + (version ? ` ${version}` : ""), cliCommon.C.bold, cliCommon.C.white));
|
|
287
287
|
console.log(cliCommon.color(` Flow: ${flow.name}`, cliCommon.C.gray));
|
package/out/main/index.js
CHANGED
|
@@ -1,10 +1,10 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
const electron = require("electron");
|
|
3
|
-
const handle = require("./chunks/handle-
|
|
3
|
+
const handle = require("./chunks/handle-HQp1EXf8.js");
|
|
4
4
|
const path = require("node:path");
|
|
5
5
|
const fs = require("node:fs");
|
|
6
6
|
const registerHandlers = require("./register-handlers.js");
|
|
7
|
-
const requestExec = require("./chunks/request-exec-
|
|
7
|
+
const requestExec = require("./chunks/request-exec-B8DJ8Id2.js");
|
|
8
8
|
const electronUpdater = require("electron-updater");
|
|
9
9
|
const mockServer = require("./chunks/mock-server-C4kTFkod.js");
|
|
10
10
|
require("node:fs/promises");
|
|
@@ -18,7 +18,7 @@ require("./chunks/ipc-validate-sqUFqRmE.js");
|
|
|
18
18
|
require("ajv");
|
|
19
19
|
require("js-yaml");
|
|
20
20
|
require("undici");
|
|
21
|
-
require("./chunks/soap-handler-
|
|
21
|
+
require("./chunks/soap-handler-D_Hj9e8S.js");
|
|
22
22
|
require("node:https");
|
|
23
23
|
require("node:http");
|
|
24
24
|
require("@xmldom/xmldom");
|
|
@@ -32,7 +32,7 @@ require("node:os");
|
|
|
32
32
|
require("@grpc/grpc-js");
|
|
33
33
|
require("@grpc/proto-loader");
|
|
34
34
|
require("./chunks/escape-DDVAlOvZ.js");
|
|
35
|
-
require("./chunks/broker-client-
|
|
35
|
+
require("./chunks/broker-client-Cl6Fu3oD.js");
|
|
36
36
|
require("./chunks/recorder-BkO8G_mB.js");
|
|
37
37
|
require("fs/promises");
|
|
38
38
|
require("tls");
|
|
@@ -50,7 +50,7 @@ function isNewer(a, b) {
|
|
|
50
50
|
return a2 > b2;
|
|
51
51
|
}
|
|
52
52
|
async function checkForUpdate() {
|
|
53
|
-
const current = "0.9.
|
|
53
|
+
const current = "0.9.2";
|
|
54
54
|
try {
|
|
55
55
|
const res = await fetch(REGISTRY_URL, { signal: AbortSignal.timeout(4e3) });
|
|
56
56
|
if (!res.ok) return null;
|
|
@@ -103,6 +103,7 @@ if (process.env.ELECTRON_NO_SANDBOX === "1") {
|
|
|
103
103
|
}
|
|
104
104
|
const PROTOCOL = "spector";
|
|
105
105
|
let pendingRepoUrl = null;
|
|
106
|
+
let pendingImportToken = null;
|
|
106
107
|
function deepLinkFromArgv(argv) {
|
|
107
108
|
return argv.find((a) => a.startsWith(`${PROTOCOL}://`)) ?? null;
|
|
108
109
|
}
|
|
@@ -119,12 +120,27 @@ function parseOpenFromGit(deepLink) {
|
|
|
119
120
|
const repo = u.searchParams.get("url");
|
|
120
121
|
return repo?.trim() ? repo.trim() : null;
|
|
121
122
|
}
|
|
123
|
+
function parseImportShare(deepLink) {
|
|
124
|
+
let u;
|
|
125
|
+
try {
|
|
126
|
+
u = new URL(deepLink);
|
|
127
|
+
} catch {
|
|
128
|
+
return null;
|
|
129
|
+
}
|
|
130
|
+
if (u.protocol !== `${PROTOCOL}:`) return null;
|
|
131
|
+
const action = u.hostname || u.pathname.replace(/^\/+/, "").split("/")[0];
|
|
132
|
+
if (action !== "import") return null;
|
|
133
|
+
const token = u.searchParams.get("token");
|
|
134
|
+
return token?.trim() ? token.trim() : null;
|
|
135
|
+
}
|
|
122
136
|
function handleDeepLink(deepLink) {
|
|
123
137
|
const repo = parseOpenFromGit(deepLink);
|
|
124
|
-
|
|
138
|
+
const token = repo ? null : parseImportShare(deepLink);
|
|
139
|
+
if (!repo && !token) return;
|
|
125
140
|
const win = electron.BrowserWindow.getAllWindows()[0];
|
|
126
141
|
if (!win) {
|
|
127
142
|
pendingRepoUrl = repo;
|
|
143
|
+
pendingImportToken = token;
|
|
128
144
|
if (electron.app.isReady()) createWindow();
|
|
129
145
|
return;
|
|
130
146
|
}
|
|
@@ -132,15 +148,23 @@ function handleDeepLink(deepLink) {
|
|
|
132
148
|
win.focus();
|
|
133
149
|
if (win.webContents.isLoading()) {
|
|
134
150
|
pendingRepoUrl = repo;
|
|
151
|
+
pendingImportToken = token;
|
|
135
152
|
} else {
|
|
136
|
-
win.webContents.send(handle.IPC.file.openFromGitDeepLink, repo);
|
|
153
|
+
if (repo) win.webContents.send(handle.IPC.file.openFromGitDeepLink, repo);
|
|
154
|
+
if (token) win.webContents.send(handle.IPC.file.importShareDeepLink, token);
|
|
137
155
|
}
|
|
138
156
|
}
|
|
139
157
|
function flushDeepLink(win) {
|
|
140
|
-
if (
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
158
|
+
if (pendingRepoUrl) {
|
|
159
|
+
const repo = pendingRepoUrl;
|
|
160
|
+
pendingRepoUrl = null;
|
|
161
|
+
win.webContents.send(handle.IPC.file.openFromGitDeepLink, repo);
|
|
162
|
+
}
|
|
163
|
+
if (pendingImportToken) {
|
|
164
|
+
const token = pendingImportToken;
|
|
165
|
+
pendingImportToken = null;
|
|
166
|
+
win.webContents.send(handle.IPC.file.importShareDeepLink, token);
|
|
167
|
+
}
|
|
144
168
|
}
|
|
145
169
|
function createSplashWindow() {
|
|
146
170
|
const splash = new electron.BrowserWindow({
|
package/out/main/lib.js
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, Symbol.toStringTag, { value: "Module" });
|
|
3
3
|
const mockServer = require("./chunks/mock-server-C4kTFkod.js");
|
|
4
|
-
const requestExec = require("./chunks/request-exec-
|
|
4
|
+
const requestExec = require("./chunks/request-exec-B8DJ8Id2.js");
|
|
5
5
|
const flowEngine = require("./chunks/flow-engine-BxwjEy37.js");
|
|
6
6
|
require("node:http");
|
|
7
7
|
require("node:crypto");
|
|
@@ -11,7 +11,7 @@ require("@xmldom/xmldom");
|
|
|
11
11
|
require("undici");
|
|
12
12
|
require("fs/promises");
|
|
13
13
|
require("tls");
|
|
14
|
-
require("./chunks/handle-
|
|
14
|
+
require("./chunks/handle-HQp1EXf8.js");
|
|
15
15
|
require("node:fs");
|
|
16
16
|
require("node:os");
|
|
17
17
|
require("node:path");
|
package/out/main/perf-worker.js
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
"use strict";
|
|
2
|
-
const perfRun = require("./chunks/perf-run-
|
|
3
|
-
const requestExec = require("./chunks/request-exec-
|
|
2
|
+
const perfRun = require("./chunks/perf-run-BNunvZsG.js");
|
|
3
|
+
const requestExec = require("./chunks/request-exec-B8DJ8Id2.js");
|
|
4
4
|
require("@grpc/grpc-js");
|
|
5
5
|
require("@grpc/proto-loader");
|
|
6
6
|
require("node:fs");
|
|
@@ -13,7 +13,7 @@ require("uuid");
|
|
|
13
13
|
require("undici");
|
|
14
14
|
require("fs/promises");
|
|
15
15
|
require("tls");
|
|
16
|
-
require("./chunks/handle-
|
|
16
|
+
require("./chunks/handle-HQp1EXf8.js");
|
|
17
17
|
require("node:crypto");
|
|
18
18
|
require("dayjs");
|
|
19
19
|
require("node:vm");
|
package/out/main/perf.js
CHANGED
|
@@ -2,17 +2,17 @@
|
|
|
2
2
|
"use strict";
|
|
3
3
|
const promises = require("node:fs/promises");
|
|
4
4
|
const path = require("node:path");
|
|
5
|
-
const requestExec = require("./chunks/request-exec-
|
|
5
|
+
const requestExec = require("./chunks/request-exec-B8DJ8Id2.js");
|
|
6
6
|
const requestCollection = require("./chunks/request-collection-zRRUfg0X.js");
|
|
7
7
|
const environments = require("./chunks/environments-iM3SUM-4.js");
|
|
8
8
|
const flowEngine = require("./chunks/flow-engine-BxwjEy37.js");
|
|
9
|
-
const perfRun = require("./chunks/perf-run-
|
|
9
|
+
const perfRun = require("./chunks/perf-run-BNunvZsG.js");
|
|
10
10
|
const perfReport = require("./chunks/perf-report-KXGZgCDY.js");
|
|
11
11
|
const cliCommon = require("./chunks/cli-common-GnihVSjU.js");
|
|
12
12
|
require("undici");
|
|
13
13
|
require("fs/promises");
|
|
14
14
|
require("tls");
|
|
15
|
-
require("./chunks/handle-
|
|
15
|
+
require("./chunks/handle-HQp1EXf8.js");
|
|
16
16
|
require("node:fs");
|
|
17
17
|
require("node:os");
|
|
18
18
|
require("node:crypto");
|
|
@@ -191,7 +191,7 @@ async function main() {
|
|
|
191
191
|
targetLabel = `flow: ${flow.name}`;
|
|
192
192
|
}
|
|
193
193
|
const load = perfRun.deriveLoad(plan);
|
|
194
|
-
const version = `v${"0.9.
|
|
194
|
+
const version = `v${"0.9.2"}`;
|
|
195
195
|
console.log("");
|
|
196
196
|
console.log(cliCommon.color(" API Performance" + (version ? ` ${version}` : ""), cliCommon.C.bold, cliCommon.C.white));
|
|
197
197
|
console.log(cliCommon.color(` Plan: ${plan.name}`, cliCommon.C.gray));
|
|
@@ -23,7 +23,7 @@ var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__ge
|
|
|
23
23
|
));
|
|
24
24
|
Object.defineProperty(exports, Symbol.toStringTag, { value: "Module" });
|
|
25
25
|
const electron = require("electron");
|
|
26
|
-
const handle = require("./chunks/handle-
|
|
26
|
+
const handle = require("./chunks/handle-HQp1EXf8.js");
|
|
27
27
|
const promises = require("node:fs/promises");
|
|
28
28
|
const path = require("node:path");
|
|
29
29
|
const crypto = require("node:crypto");
|
|
@@ -31,12 +31,12 @@ const JSZip = require("jszip");
|
|
|
31
31
|
const simpleGit = require("simple-git");
|
|
32
32
|
const dataFiles = require("./chunks/data-files-BYqhsoPe.js");
|
|
33
33
|
const requestCollection = require("./chunks/request-collection-zRRUfg0X.js");
|
|
34
|
-
const requestExec = require("./chunks/request-exec-
|
|
34
|
+
const requestExec = require("./chunks/request-exec-B8DJ8Id2.js");
|
|
35
35
|
const ipcValidate = require("./chunks/ipc-validate-sqUFqRmE.js");
|
|
36
36
|
const uuid = require("uuid");
|
|
37
37
|
const jsYaml = require("js-yaml");
|
|
38
38
|
const undici = require("undici");
|
|
39
|
-
const soapHandler = require("./chunks/soap-handler-
|
|
39
|
+
const soapHandler = require("./chunks/soap-handler-D_Hj9e8S.js");
|
|
40
40
|
const runConcurrent = require("./chunks/run-concurrent-468tH0AX.js");
|
|
41
41
|
const flowEngine = require("./chunks/flow-engine-BxwjEy37.js");
|
|
42
42
|
const mockServer = require("./chunks/mock-server-C4kTFkod.js");
|
|
@@ -50,7 +50,7 @@ const os = require("node:os");
|
|
|
50
50
|
const grpc = require("@grpc/grpc-js");
|
|
51
51
|
const protoLoader = require("@grpc/proto-loader");
|
|
52
52
|
const escape = require("./chunks/escape-DDVAlOvZ.js");
|
|
53
|
-
const brokerClient = require("./chunks/broker-client-
|
|
53
|
+
const brokerClient = require("./chunks/broker-client-Cl6Fu3oD.js");
|
|
54
54
|
const recorder = require("./chunks/recorder-BkO8G_mB.js");
|
|
55
55
|
require("fs/promises");
|
|
56
56
|
require("tls");
|
|
@@ -269,6 +269,62 @@ function defaultWorkspaceName() {
|
|
|
269
269
|
}
|
|
270
270
|
return "my-workspace.spector";
|
|
271
271
|
}
|
|
272
|
+
const SYNC_SKIP_DIRS = /* @__PURE__ */ new Set([".git", "node_modules"]);
|
|
273
|
+
const SYNC_SKIP_FILES = /* @__PURE__ */ new Set(["history.json"]);
|
|
274
|
+
function stripEnvSecrets(text) {
|
|
275
|
+
try {
|
|
276
|
+
const env = JSON.parse(text);
|
|
277
|
+
if (Array.isArray(env.variables)) {
|
|
278
|
+
env.variables = env.variables.map((v) => {
|
|
279
|
+
const rest = { ...v };
|
|
280
|
+
delete rest["secretEncrypted"];
|
|
281
|
+
delete rest["secretSalt"];
|
|
282
|
+
delete rest["secretIv"];
|
|
283
|
+
delete rest["secretHash"];
|
|
284
|
+
if (rest["secret"]) rest["value"] = "";
|
|
285
|
+
return rest;
|
|
286
|
+
});
|
|
287
|
+
}
|
|
288
|
+
return JSON.stringify(env, null, 2);
|
|
289
|
+
} catch {
|
|
290
|
+
return text;
|
|
291
|
+
}
|
|
292
|
+
}
|
|
293
|
+
function mergeEnvSecrets(remoteText, localText) {
|
|
294
|
+
if (!localText) return remoteText;
|
|
295
|
+
try {
|
|
296
|
+
const remote = JSON.parse(remoteText);
|
|
297
|
+
const local = JSON.parse(localText);
|
|
298
|
+
const byKey = /* @__PURE__ */ new Map();
|
|
299
|
+
for (const lv of local.variables ?? []) byKey.set(String(lv["key"]), lv);
|
|
300
|
+
remote.variables = (remote.variables ?? []).map((rv) => {
|
|
301
|
+
const lv = byKey.get(String(rv["key"]));
|
|
302
|
+
if (!lv) return rv;
|
|
303
|
+
const merged = { ...rv };
|
|
304
|
+
for (const f of ["secretEncrypted", "secretSalt", "secretIv", "secretHash"]) {
|
|
305
|
+
if (lv[f] !== void 0) merged[f] = lv[f];
|
|
306
|
+
}
|
|
307
|
+
if (rv["secret"] && lv["value"]) merged["value"] = lv["value"];
|
|
308
|
+
return merged;
|
|
309
|
+
});
|
|
310
|
+
return JSON.stringify(remote, null, 2);
|
|
311
|
+
} catch {
|
|
312
|
+
return remoteText;
|
|
313
|
+
}
|
|
314
|
+
}
|
|
315
|
+
async function walkWorkspaceFiles(dir, base, out) {
|
|
316
|
+
const entries = await promises.readdir(dir, { withFileTypes: true });
|
|
317
|
+
for (const entry of entries) {
|
|
318
|
+
if (entry.isDirectory()) {
|
|
319
|
+
if (SYNC_SKIP_DIRS.has(entry.name)) continue;
|
|
320
|
+
await walkWorkspaceFiles(path.join(dir, entry.name), base, out);
|
|
321
|
+
} else if (entry.isFile()) {
|
|
322
|
+
if (SYNC_SKIP_FILES.has(entry.name)) continue;
|
|
323
|
+
const full = path.join(dir, entry.name);
|
|
324
|
+
out[full.slice(base.length + 1).split(path.sep).join("/")] = await promises.readFile(full, "utf8");
|
|
325
|
+
}
|
|
326
|
+
}
|
|
327
|
+
}
|
|
272
328
|
function registerFileHandlers(ipc) {
|
|
273
329
|
handle.handleIpc(ipc, handle.IPC.file.openWorkspace, async () => {
|
|
274
330
|
const result = await electron.dialog.showOpenDialog({
|
|
@@ -383,6 +439,68 @@ Create a workspace in this folder and add "${path.basename(wsPath)}" to it? The
|
|
|
383
439
|
if (err.code !== "ENOENT") throw err;
|
|
384
440
|
}
|
|
385
441
|
});
|
|
442
|
+
handle.handleIpc(ipc, handle.IPC.file.serializeWorkspace, async () => {
|
|
443
|
+
if (!workspaceDir || !workspaceFile) throw new Error("No workspace open");
|
|
444
|
+
const manifest = JSON.parse(await promises.readFile(workspaceFile, "utf8"));
|
|
445
|
+
const files = {};
|
|
446
|
+
await walkWorkspaceFiles(workspaceDir, workspaceDir, files);
|
|
447
|
+
const manifestName = path.basename(workspaceFile);
|
|
448
|
+
delete files[manifestName];
|
|
449
|
+
for (const rel of Object.keys(files)) {
|
|
450
|
+
if (rel.startsWith("environments/")) files[rel] = stripEnvSecrets(files[rel]);
|
|
451
|
+
}
|
|
452
|
+
const sharedSettings = { ...manifest.settings ?? {} };
|
|
453
|
+
delete sharedSettings["cloud"];
|
|
454
|
+
delete sharedSettings["sync"];
|
|
455
|
+
return { manifest: { ...manifest, settings: sharedSettings }, manifestName, files };
|
|
456
|
+
});
|
|
457
|
+
handle.handleIpc(ipc, handle.IPC.file.applyWorkspaceSnapshot, async (_e, snap) => {
|
|
458
|
+
if (!workspaceDir || !workspaceFile) throw new Error("No workspace open");
|
|
459
|
+
try {
|
|
460
|
+
const backupDir = path.join(electron.app.getPath("userData"), "sync-backups", path.basename(workspaceDir) + "-" + Date.now());
|
|
461
|
+
await promises.cp(workspaceDir, backupDir, {
|
|
462
|
+
recursive: true,
|
|
463
|
+
filter: (src) => {
|
|
464
|
+
const rel = src.slice(workspaceDir.length);
|
|
465
|
+
return !/[\\/](\.git|node_modules)([\\/]|$)/.test(rel);
|
|
466
|
+
}
|
|
467
|
+
});
|
|
468
|
+
} catch (err) {
|
|
469
|
+
console.warn("sync: workspace backup failed (continuing):", err);
|
|
470
|
+
}
|
|
471
|
+
const guard = path.resolve(workspaceDir) + (process.platform === "win32" ? "\\" : "/");
|
|
472
|
+
let filesWritten = 0;
|
|
473
|
+
for (const [rel, content] of Object.entries(snap.files ?? {})) {
|
|
474
|
+
const full = path.resolve(workspaceDir, rel);
|
|
475
|
+
if (!full.startsWith(guard)) continue;
|
|
476
|
+
let out = content;
|
|
477
|
+
if (rel.startsWith("environments/")) {
|
|
478
|
+
let localText = null;
|
|
479
|
+
try {
|
|
480
|
+
localText = await promises.readFile(full, "utf8");
|
|
481
|
+
} catch {
|
|
482
|
+
}
|
|
483
|
+
out = mergeEnvSecrets(content, localText);
|
|
484
|
+
}
|
|
485
|
+
await promises.mkdir(path.dirname(full), { recursive: true });
|
|
486
|
+
await atomicWrite(full, out);
|
|
487
|
+
filesWritten++;
|
|
488
|
+
}
|
|
489
|
+
const local = JSON.parse(await promises.readFile(workspaceFile, "utf8"));
|
|
490
|
+
const merged = {
|
|
491
|
+
...local,
|
|
492
|
+
...snap.manifest,
|
|
493
|
+
settings: { ...snap.manifest.settings ?? {}, ...local.settings ?? {} }
|
|
494
|
+
};
|
|
495
|
+
await atomicWrite(workspaceFile, JSON.stringify(merged, null, 2));
|
|
496
|
+
return {
|
|
497
|
+
ok: true,
|
|
498
|
+
filesWritten,
|
|
499
|
+
collections: Array.isArray(merged.collections) ? merged.collections.length : 0,
|
|
500
|
+
workspace: merged,
|
|
501
|
+
workspacePath: workspaceFile
|
|
502
|
+
};
|
|
503
|
+
});
|
|
386
504
|
handle.handleIpc(ipc, handle.IPC.file.loadHistory, async () => {
|
|
387
505
|
if (!workspaceDir) return [];
|
|
388
506
|
try {
|
|
@@ -2677,7 +2795,7 @@ function registerImportHandlers(ipc) {
|
|
|
2677
2795
|
if (opts.url?.trim()) {
|
|
2678
2796
|
const url = opts.url.trim();
|
|
2679
2797
|
const { validateWsdlFetchUrl } = await Promise.resolve().then(() => require("./chunks/ipc-validate-sqUFqRmE.js"));
|
|
2680
|
-
const { fetchUrl } = await Promise.resolve().then(() => require("./chunks/soap-handler-
|
|
2798
|
+
const { fetchUrl } = await Promise.resolve().then(() => require("./chunks/soap-handler-D_Hj9e8S.js")).then((n) => n.soapHandler);
|
|
2681
2799
|
validateWsdlFetchUrl(url);
|
|
2682
2800
|
wsdlText = await fetchUrl(url);
|
|
2683
2801
|
try {
|
|
@@ -7573,6 +7691,30 @@ function registerGitHandlers(ipc) {
|
|
|
7573
7691
|
handle.handleIpc(ipc, handle.IPC.git.deleteBranch, async (_e, name, force = false) => {
|
|
7574
7692
|
await git().deleteLocalBranch(name, force);
|
|
7575
7693
|
});
|
|
7694
|
+
handle.handleIpc(ipc, handle.IPC.git.stashList, async () => {
|
|
7695
|
+
const raw = await git().raw(["stash", "list", "--format=%gd%gs"]);
|
|
7696
|
+
return raw.split("\n").filter(Boolean).map((line, index) => {
|
|
7697
|
+
const [ref = `stash@{${index}}`, subject = ""] = line.split("");
|
|
7698
|
+
const m = /^(?:WIP on|On) ([^:]+): (.*)$/.exec(subject);
|
|
7699
|
+
return {
|
|
7700
|
+
index,
|
|
7701
|
+
ref,
|
|
7702
|
+
branch: m ? m[1] : "",
|
|
7703
|
+
message: m ? m[2] : subject
|
|
7704
|
+
};
|
|
7705
|
+
});
|
|
7706
|
+
});
|
|
7707
|
+
handle.handleIpc(ipc, handle.IPC.git.stash, async (_e, message) => {
|
|
7708
|
+
const args = ["stash", "push", "-u"];
|
|
7709
|
+
if (message && message.trim()) args.push("-m", message.trim());
|
|
7710
|
+
await git().raw(args);
|
|
7711
|
+
});
|
|
7712
|
+
handle.handleIpc(ipc, handle.IPC.git.stashPop, async (_e, ref) => {
|
|
7713
|
+
await git().raw(["stash", "pop", ...ref ? [ref] : []]);
|
|
7714
|
+
});
|
|
7715
|
+
handle.handleIpc(ipc, handle.IPC.git.stashDrop, async (_e, ref) => {
|
|
7716
|
+
await git().raw(["stash", "drop", ...ref ? [ref] : []]);
|
|
7717
|
+
});
|
|
7576
7718
|
handle.handleIpc(ipc, handle.IPC.git.fetch, async () => {
|
|
7577
7719
|
await git().fetch(["--prune"]);
|
|
7578
7720
|
});
|
|
@@ -7921,6 +8063,76 @@ function registerCloudHandlers(ipc) {
|
|
|
7921
8063
|
handle.handleIpc(ipc, handle.IPC.cloud.openFlow, async (_e, name) => {
|
|
7922
8064
|
await electron.shell.openExternal(CLOUD_ENDPOINT + "/flows/" + encodeURIComponent(slugify(name)));
|
|
7923
8065
|
});
|
|
8066
|
+
const stripRequest = (r) => {
|
|
8067
|
+
const { examples: _examples, ...rest } = r;
|
|
8068
|
+
return rest;
|
|
8069
|
+
};
|
|
8070
|
+
const stripFolder = (f) => {
|
|
8071
|
+
const { dataSet: _d, dataSetRef: _r, ...rest } = f ?? {};
|
|
8072
|
+
const folders = Array.isArray(rest["folders"]) ? rest["folders"].map(stripFolder) : [];
|
|
8073
|
+
return { ...rest, folders };
|
|
8074
|
+
};
|
|
8075
|
+
const stripCollection = (col) => {
|
|
8076
|
+
const { dataSet: _d, dataSetRef: _r, ...rest } = col;
|
|
8077
|
+
const requests = {};
|
|
8078
|
+
for (const [id, req] of Object.entries(col.requests ?? {})) requests[id] = stripRequest(req);
|
|
8079
|
+
return { ...rest, requests, rootFolder: stripFolder(col.rootFolder) };
|
|
8080
|
+
};
|
|
8081
|
+
handle.handleIpc(ipc, handle.IPC.cloud.shareCollection, async (_e, col) => {
|
|
8082
|
+
return cloudFetch("/api/share", "POST", { type: "collection", source_id: col.id, name: col.name, payload: stripCollection(col) });
|
|
8083
|
+
});
|
|
8084
|
+
handle.handleIpc(ipc, handle.IPC.cloud.shareRequest, async (_e, req) => {
|
|
8085
|
+
return cloudFetch("/api/share", "POST", { type: "request", source_id: req.id, name: req.name, payload: stripRequest(req) });
|
|
8086
|
+
});
|
|
8087
|
+
handle.handleIpc(ipc, handle.IPC.cloud.shareFolder, async (_e, arg) => {
|
|
8088
|
+
return cloudFetch("/api/share", "POST", { type: "folder", source_id: arg.sourceId, name: arg.name, payload: stripCollection(arg.payload) });
|
|
8089
|
+
});
|
|
8090
|
+
handle.handleIpc(ipc, handle.IPC.cloud.shareLookup, async (_e, arg) => {
|
|
8091
|
+
const q = new URLSearchParams({ type: arg.type, source_id: arg.sourceId }).toString();
|
|
8092
|
+
return cloudFetch("/api/share-lookup?" + q, "GET");
|
|
8093
|
+
});
|
|
8094
|
+
handle.handleIpc(ipc, handle.IPC.cloud.shareUpdate, async (_e, arg) => {
|
|
8095
|
+
const token = String(arg.token).replace(/[^a-z0-9]/gi, "");
|
|
8096
|
+
return cloudFetch("/api/share/" + encodeURIComponent(token), "PATCH", { expires_days: arg.expiresDays ?? 0 });
|
|
8097
|
+
});
|
|
8098
|
+
handle.handleIpc(ipc, handle.IPC.cloud.shareRevoke, async (_e, token) => {
|
|
8099
|
+
const clean = String(token).replace(/[^a-z0-9]/gi, "");
|
|
8100
|
+
return cloudFetch("/api/share/" + encodeURIComponent(clean), "DELETE");
|
|
8101
|
+
});
|
|
8102
|
+
handle.handleIpc(ipc, handle.IPC.cloud.workspaceList, async () => cloudFetch("/api/workspaces", "GET"));
|
|
8103
|
+
handle.handleIpc(ipc, handle.IPC.cloud.workspaceCreate, async (_e, arg) => cloudFetch("/api/workspaces", "POST", { name: arg.name, payload: arg.payload, author: arg.author }));
|
|
8104
|
+
handle.handleIpc(ipc, handle.IPC.cloud.workspacePull, async (_e, id) => cloudFetch("/api/workspaces/" + encodeURIComponent(String(id)), "GET"));
|
|
8105
|
+
handle.handleIpc(ipc, handle.IPC.cloud.workspaceVersions, async (_e, id) => cloudFetch("/api/workspaces/" + encodeURIComponent(String(id)) + "/versions", "GET"));
|
|
8106
|
+
handle.handleIpc(ipc, handle.IPC.cloud.workspaceRestore, async (_e, arg) => cloudFetch("/api/workspaces/" + encodeURIComponent(String(arg.id)) + "/restore", "POST", { version: arg.version }));
|
|
8107
|
+
handle.handleIpc(ipc, handle.IPC.cloud.workspacePush, async (_e, arg) => {
|
|
8108
|
+
const token = await requestExec.getSecret(CLOUD_TOKEN_REF);
|
|
8109
|
+
if (!token) throw new Error("No cloud API token set. Add one in Settings → Cloud.");
|
|
8110
|
+
const dispatcher = await requestExec.buildDispatcher();
|
|
8111
|
+
const res = await undici.fetch(CLOUD_ENDPOINT + "/api/workspaces/" + encodeURIComponent(String(arg.id)), {
|
|
8112
|
+
method: "PUT",
|
|
8113
|
+
headers: { "Content-Type": "application/json", Accept: "application/json", Authorization: `Bearer ${token}` },
|
|
8114
|
+
body: JSON.stringify({ base_version: arg.baseVersion, payload: arg.payload, author: arg.author }),
|
|
8115
|
+
dispatcher
|
|
8116
|
+
});
|
|
8117
|
+
const json = await res.json().catch(() => ({}));
|
|
8118
|
+
if (res.status === 409) return { conflict: true, currentVersion: json.current_version };
|
|
8119
|
+
if (!res.ok) throw new Error(json.error || json.message || `Push failed (HTTP ${res.status}).`);
|
|
8120
|
+
return { conflict: false, version: json.version };
|
|
8121
|
+
});
|
|
8122
|
+
handle.handleIpc(ipc, handle.IPC.cloud.importShare, async (_e, token) => {
|
|
8123
|
+
const cleaned = String(token).replace(/[^a-z0-9]/gi, "");
|
|
8124
|
+
if (!cleaned) throw new Error("Invalid share link.");
|
|
8125
|
+
const dispatcher = await requestExec.buildDispatcher();
|
|
8126
|
+
const res = await undici.fetch(CLOUD_ENDPOINT + "/api/share/" + encodeURIComponent(cleaned), {
|
|
8127
|
+
method: "GET",
|
|
8128
|
+
headers: { Accept: "application/json" },
|
|
8129
|
+
dispatcher
|
|
8130
|
+
});
|
|
8131
|
+
if (!res.ok) {
|
|
8132
|
+
throw new Error(res.status === 404 || res.status === 410 ? "This share link is invalid or has expired." : `Could not fetch the shared item (HTTP ${res.status}).`);
|
|
8133
|
+
}
|
|
8134
|
+
return res.json();
|
|
8135
|
+
});
|
|
7924
8136
|
handle.handleIpc(ipc, handle.IPC.cloud.pushMonitor, async (_e, input) => {
|
|
7925
8137
|
const { request, environment, collectionVars, globals } = input;
|
|
7926
8138
|
const envVars = await requestExec.buildEnvVars(environment);
|
package/out/main/runner.js
CHANGED
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
"use strict";
|
|
3
3
|
const promises = require("node:fs/promises");
|
|
4
4
|
const path = require("node:path");
|
|
5
|
-
const requestExec = require("./chunks/request-exec-
|
|
5
|
+
const requestExec = require("./chunks/request-exec-B8DJ8Id2.js");
|
|
6
6
|
const requestCollection = require("./chunks/request-collection-zRRUfg0X.js");
|
|
7
7
|
const escape = require("./chunks/escape-DDVAlOvZ.js");
|
|
8
8
|
const runConcurrent = require("./chunks/run-concurrent-468tH0AX.js");
|
|
@@ -11,7 +11,7 @@ const cliCommon = require("./chunks/cli-common-GnihVSjU.js");
|
|
|
11
11
|
require("undici");
|
|
12
12
|
require("fs/promises");
|
|
13
13
|
require("tls");
|
|
14
|
-
require("./chunks/handle-
|
|
14
|
+
require("./chunks/handle-HQp1EXf8.js");
|
|
15
15
|
require("node:fs");
|
|
16
16
|
require("node:os");
|
|
17
17
|
require("node:crypto");
|
|
@@ -551,7 +551,7 @@ async function main() {
|
|
|
551
551
|
} else if (!envName && workspace.settings?.defaultEnvironment && !env) {
|
|
552
552
|
console.warn(cliCommon.color(`Warning: default environment "${workspace.settings.defaultEnvironment}" not found. Running without environment.`, cliCommon.C.yellow));
|
|
553
553
|
}
|
|
554
|
-
const version = `v${"0.9.
|
|
554
|
+
const version = `v${"0.9.2"}`;
|
|
555
555
|
console.log("");
|
|
556
556
|
console.log(cliCommon.color(" API Test Runner" + (version ? ` ${version}` : ""), cliCommon.C.bold, cliCommon.C.white));
|
|
557
557
|
console.log(cliCommon.color(` Workspace: ${wsPath}`, cliCommon.C.gray));
|
package/out/main/wsdl.js
CHANGED
|
@@ -4,10 +4,10 @@ const promises = require("node:fs/promises");
|
|
|
4
4
|
const path = require("node:path");
|
|
5
5
|
const https = require("node:https");
|
|
6
6
|
const http = require("node:http");
|
|
7
|
-
const soapHandler = require("./chunks/soap-handler-
|
|
8
|
-
const _import = require("./chunks/import-
|
|
7
|
+
const soapHandler = require("./chunks/soap-handler-D_Hj9e8S.js");
|
|
8
|
+
const _import = require("./chunks/import-DVpFH9Wb.js");
|
|
9
9
|
const cliCommon = require("./chunks/cli-common-GnihVSjU.js");
|
|
10
|
-
require("./chunks/handle-
|
|
10
|
+
require("./chunks/handle-HQp1EXf8.js");
|
|
11
11
|
require("@xmldom/xmldom");
|
|
12
12
|
require("uuid");
|
|
13
13
|
require("./chunks/data-files-BYqhsoPe.js");
|