@testsmith/api-spector 0.3.8 → 0.3.9
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/{handle-BCnNIZZr.js → handle-Coax8Nz1.js} +1 -0
- package/out/main/chunks/{import-DUKaMYGO.js → import-Bilo697Z.js} +2 -2
- package/out/main/chunks/{request-collection-CBuPjBwa.js → request-collection-CJoXpvOw.js} +20 -0
- package/out/main/chunks/{request-exec-AQD6cEgT.js → request-exec-C0DnGKdd.js} +1 -1
- package/out/main/chunks/{snapshots-NGkGQNZ4.js → snapshots-CatB4zLh.js} +1 -1
- package/out/main/chunks/{soap-handler-h0dWIjOK.js → soap-handler-B1Huudj7.js} +2 -2
- package/out/main/contract.js +3 -3
- package/out/main/index.js +72 -9
- package/out/main/runner.js +5 -5
- package/out/main/wsdl.js +3 -3
- package/out/preload/index.js +2 -0
- package/out/renderer/assets/{index-BK58GuOI.js → index-BdUvP_cg.js} +38 -7
- package/out/renderer/index.html +1 -1
- package/package.json +1 -1
|
@@ -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-B1Huudj7.js");
|
|
5
|
+
require("./handle-Coax8Nz1.js");
|
|
6
6
|
require("https");
|
|
7
7
|
require("http");
|
|
8
8
|
require("@xmldom/xmldom");
|
|
@@ -85,6 +85,25 @@ function getAllApplicableHooks(folderId, collection) {
|
|
|
85
85
|
}
|
|
86
86
|
return { beforeAll, before, after, afterAll };
|
|
87
87
|
}
|
|
88
|
+
function authIsConfigured(auth) {
|
|
89
|
+
if (!auth || auth.type === "none") return false;
|
|
90
|
+
const set = (s) => !!(s && s.trim());
|
|
91
|
+
switch (auth.type) {
|
|
92
|
+
case "bearer":
|
|
93
|
+
return set(auth.token) || set(auth.tokenSecretRef);
|
|
94
|
+
case "basic":
|
|
95
|
+
case "digest":
|
|
96
|
+
return set(auth.username) || set(auth.password) || set(auth.passwordSecretRef);
|
|
97
|
+
case "ntlm":
|
|
98
|
+
return set(auth.username) || set(auth.password) || set(auth.passwordSecretRef);
|
|
99
|
+
case "apikey":
|
|
100
|
+
return set(auth.apiKeyValue) || set(auth.apiKeySecretRef);
|
|
101
|
+
case "oauth2":
|
|
102
|
+
return set(auth.oauth2TokenUrl) || set(auth.oauth2ClientId) || set(auth.oauth2CachedToken);
|
|
103
|
+
default:
|
|
104
|
+
return true;
|
|
105
|
+
}
|
|
106
|
+
}
|
|
88
107
|
function resolveInheritedAuthAndHeaders(requestId, collection) {
|
|
89
108
|
let inheritedAuth = collection.auth && collection.auth.type !== "none" ? collection.auth : null;
|
|
90
109
|
let inheritedHeaders = collection.headers?.filter((h) => h.enabled && h.key) ?? [];
|
|
@@ -113,6 +132,7 @@ function buildRunPlan(collection, folderId, filterTags) {
|
|
|
113
132
|
);
|
|
114
133
|
}
|
|
115
134
|
}
|
|
135
|
+
exports.authIsConfigured = authIsConfigured;
|
|
116
136
|
exports.buildRunPlan = buildRunPlan;
|
|
117
137
|
exports.getAllApplicableHooks = getAllApplicableHooks;
|
|
118
138
|
exports.resolveInheritedAuthAndHeaders = resolveInheritedAuthAndHeaders;
|
|
@@ -23,7 +23,7 @@ var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__ge
|
|
|
23
23
|
));
|
|
24
24
|
const undici = require("undici");
|
|
25
25
|
const promises = require("fs/promises");
|
|
26
|
-
const handle = require("./handle-
|
|
26
|
+
const handle = require("./handle-Coax8Nz1.js");
|
|
27
27
|
const crypto = require("crypto");
|
|
28
28
|
const path = require("path");
|
|
29
29
|
const dayjs = require("dayjs");
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
const undici = require("undici");
|
|
3
|
-
const requestExec = require("./request-exec-
|
|
3
|
+
const requestExec = require("./request-exec-C0DnGKdd.js");
|
|
4
4
|
const promises = require("fs/promises");
|
|
5
5
|
const path = require("path");
|
|
6
6
|
const Ajv = require("ajv");
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
"use strict";
|
|
2
|
-
const handle = require("./handle-
|
|
2
|
+
const handle = require("./handle-Coax8Nz1.js");
|
|
3
3
|
const https = require("https");
|
|
4
4
|
const http = require("http");
|
|
5
5
|
const xmldom = require("@xmldom/xmldom");
|
|
@@ -315,7 +315,7 @@ function registerSoapHandlers(ipc) {
|
|
|
315
315
|
handle.handleIpc(ipc, handle.IPC.wsdl.import, async (_event, opts) => {
|
|
316
316
|
const { validateWsdlImport } = await Promise.resolve().then(() => require("./ipc-validate-k6KI8adf.js"));
|
|
317
317
|
validateWsdlImport(opts);
|
|
318
|
-
const { importWsdl } = await Promise.resolve().then(() => require("./import-
|
|
318
|
+
const { importWsdl } = await Promise.resolve().then(() => require("./import-Bilo697Z.js"));
|
|
319
319
|
const wsdlText = opts.xml ?? (opts.url ? await fetchUrl(opts.url) : "");
|
|
320
320
|
if (!wsdlText) throw new Error("wsdl:import requires either `url` or `xml`");
|
|
321
321
|
return importWsdl(wsdlText, { name: opts.name, existingMockPorts: opts.existingMockPorts });
|
package/out/main/contract.js
CHANGED
|
@@ -24,14 +24,14 @@ var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__ge
|
|
|
24
24
|
));
|
|
25
25
|
const promises = require("fs/promises");
|
|
26
26
|
const path = require("path");
|
|
27
|
-
const snapshots = require("./chunks/snapshots-
|
|
27
|
+
const snapshots = require("./chunks/snapshots-CatB4zLh.js");
|
|
28
28
|
const crypto = require("crypto");
|
|
29
29
|
const undici = require("undici");
|
|
30
30
|
const os = require("os");
|
|
31
31
|
const cliCommon = require("./chunks/cli-common-CDQY1erJ.js");
|
|
32
32
|
const environments = require("./chunks/environments-iM3SUM-4.js");
|
|
33
|
-
require("./chunks/request-exec-
|
|
34
|
-
require("./chunks/handle-
|
|
33
|
+
require("./chunks/request-exec-C0DnGKdd.js");
|
|
34
|
+
require("./chunks/handle-Coax8Nz1.js");
|
|
35
35
|
require("dayjs");
|
|
36
36
|
require("vm");
|
|
37
37
|
require("tv4");
|
package/out/main/index.js
CHANGED
|
@@ -22,24 +22,24 @@ var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__ge
|
|
|
22
22
|
mod
|
|
23
23
|
));
|
|
24
24
|
const electron = require("electron");
|
|
25
|
-
const handle = require("./chunks/handle-
|
|
25
|
+
const handle = require("./chunks/handle-Coax8Nz1.js");
|
|
26
26
|
const path = require("path");
|
|
27
27
|
const fs = require("fs");
|
|
28
28
|
const promises = require("fs/promises");
|
|
29
|
-
const
|
|
29
|
+
const crypto = require("crypto");
|
|
30
|
+
const requestExec = require("./chunks/request-exec-C0DnGKdd.js");
|
|
30
31
|
const ipcValidate = require("./chunks/ipc-validate-k6KI8adf.js");
|
|
31
32
|
const uuid = require("uuid");
|
|
32
33
|
const jsYaml = require("js-yaml");
|
|
33
34
|
const undici = require("undici");
|
|
34
35
|
const JSZip = require("jszip");
|
|
35
|
-
const requestCollection = require("./chunks/request-collection-
|
|
36
|
+
const requestCollection = require("./chunks/request-collection-CJoXpvOw.js");
|
|
36
37
|
const mockServer = require("./chunks/mock-server-DSLR2ulH.js");
|
|
37
38
|
const http = require("http");
|
|
38
39
|
const WebSocket = require("ws");
|
|
39
|
-
const soapHandler = require("./chunks/soap-handler-
|
|
40
|
+
const soapHandler = require("./chunks/soap-handler-B1Huudj7.js");
|
|
40
41
|
const os = require("os");
|
|
41
|
-
const
|
|
42
|
-
const snapshots = require("./chunks/snapshots-NGkGQNZ4.js");
|
|
42
|
+
const snapshots = require("./chunks/snapshots-CatB4zLh.js");
|
|
43
43
|
const simpleGit = require("simple-git");
|
|
44
44
|
const recorder = require("./chunks/recorder-0Ij921El.js");
|
|
45
45
|
require("dayjs");
|
|
@@ -224,12 +224,27 @@ function registerFileHandlers(ipc) {
|
|
|
224
224
|
});
|
|
225
225
|
if (result.canceled || !result.filePaths[0]) return null;
|
|
226
226
|
const wsPath = result.filePaths[0];
|
|
227
|
+
const raw = await promises.readFile(wsPath, "utf8");
|
|
228
|
+
const parsed = JSON.parse(raw);
|
|
229
|
+
if (looksLikeCollection(parsed)) {
|
|
230
|
+
const { response } = await electron.dialog.showMessageBox({
|
|
231
|
+
type: "question",
|
|
232
|
+
buttons: ["Create Workspace", "Cancel"],
|
|
233
|
+
defaultId: 0,
|
|
234
|
+
cancelId: 1,
|
|
235
|
+
message: "This is a collection, not a workspace.",
|
|
236
|
+
detail: `API Spector opens workspaces, which contain collections.
|
|
237
|
+
|
|
238
|
+
Create a workspace in this folder and add "${path.basename(wsPath)}" to it? The collection is moved into a collections/ folder and this file becomes the workspace.`
|
|
239
|
+
});
|
|
240
|
+
if (response !== 0) return null;
|
|
241
|
+
return wrapCollectionAsWorkspace(wsPath, parsed);
|
|
242
|
+
}
|
|
227
243
|
workspaceDir = path.dirname(wsPath);
|
|
228
244
|
workspaceFile = wsPath;
|
|
229
245
|
await requestExec.loadGlobals(workspaceDir);
|
|
230
246
|
await saveLastWorkspacePath(wsPath);
|
|
231
|
-
|
|
232
|
-
return { workspace: JSON.parse(raw), workspacePath: wsPath };
|
|
247
|
+
return { workspace: parsed, workspacePath: wsPath };
|
|
233
248
|
});
|
|
234
249
|
handle.handleIpc(ipc, handle.IPC.file.newWorkspace, async () => {
|
|
235
250
|
const startDir = dialogStartDir();
|
|
@@ -390,6 +405,30 @@ async function tryOpenWorkspaceInDir(dir) {
|
|
|
390
405
|
function getWorkspaceDir() {
|
|
391
406
|
return workspaceDir;
|
|
392
407
|
}
|
|
408
|
+
function looksLikeCollection(obj) {
|
|
409
|
+
if (!obj || typeof obj !== "object") return false;
|
|
410
|
+
const o = obj;
|
|
411
|
+
return !Array.isArray(o["collections"]) && (!!o["rootFolder"] || !!o["requests"]);
|
|
412
|
+
}
|
|
413
|
+
async function wrapCollectionAsWorkspace(collFilePath, collection) {
|
|
414
|
+
const dir = path.dirname(collFilePath);
|
|
415
|
+
const base = path.basename(collFilePath).replace(/\.(spector|json)$/i, "");
|
|
416
|
+
const safe = base.replace(/[^a-zA-Z0-9._-]+/g, "-").replace(/^-+|-+$/g, "") || "collection";
|
|
417
|
+
const collRel = `collections/${safe}.json`;
|
|
418
|
+
if (!collection.id) collection.id = crypto.randomUUID();
|
|
419
|
+
await promises.mkdir(path.join(dir, "collections"), { recursive: true });
|
|
420
|
+
await atomicWrite(path.join(dir, collRel), JSON.stringify(collection, null, 2));
|
|
421
|
+
const ws = { version: "1.0", collections: [collRel], environments: [], activeEnvironmentId: null };
|
|
422
|
+
await ensureGitignore(dir);
|
|
423
|
+
await ensureVscodeFileAssociation(dir);
|
|
424
|
+
await ensureReadme(dir, path.basename(collFilePath));
|
|
425
|
+
await atomicWrite(collFilePath, JSON.stringify(ws, null, 2));
|
|
426
|
+
workspaceDir = dir;
|
|
427
|
+
workspaceFile = collFilePath;
|
|
428
|
+
await requestExec.loadGlobals(dir);
|
|
429
|
+
await saveLastWorkspacePath(collFilePath);
|
|
430
|
+
return { workspace: ws, workspacePath: collFilePath };
|
|
431
|
+
}
|
|
393
432
|
function asObject(value) {
|
|
394
433
|
return value && typeof value === "object" ? value : null;
|
|
395
434
|
}
|
|
@@ -1593,6 +1632,30 @@ function registerImportHandlers(ipc) {
|
|
|
1593
1632
|
if (result.canceled || !result.filePaths[0]) return null;
|
|
1594
1633
|
return importHttpFile(result.filePaths[0]);
|
|
1595
1634
|
});
|
|
1635
|
+
handle.handleIpc(ipc, handle.IPC.import.spector, async () => {
|
|
1636
|
+
const result = await electron.dialog.showOpenDialog({
|
|
1637
|
+
title: "Import API Spector Collection",
|
|
1638
|
+
filters: [{ name: "API Spector Collection", extensions: ["json", "spector"] }],
|
|
1639
|
+
properties: ["openFile"]
|
|
1640
|
+
});
|
|
1641
|
+
if (result.canceled || !result.filePaths[0]) return null;
|
|
1642
|
+
const raw = await promises.readFile(result.filePaths[0], "utf8");
|
|
1643
|
+
let parsed;
|
|
1644
|
+
try {
|
|
1645
|
+
parsed = JSON.parse(raw);
|
|
1646
|
+
} catch {
|
|
1647
|
+
throw new Error("Not a valid JSON file.");
|
|
1648
|
+
}
|
|
1649
|
+
if (Array.isArray(parsed["collections"])) {
|
|
1650
|
+
throw new Error("This is a workspace file, not a collection. Open it with File > Open Workspace instead.");
|
|
1651
|
+
}
|
|
1652
|
+
if (!parsed["rootFolder"] || !parsed["requests"]) {
|
|
1653
|
+
throw new Error("This does not look like an API Spector collection (no rootFolder / requests).");
|
|
1654
|
+
}
|
|
1655
|
+
const collection = parsed;
|
|
1656
|
+
collection.id = crypto.randomUUID();
|
|
1657
|
+
return collection;
|
|
1658
|
+
});
|
|
1596
1659
|
handle.handleIpc(ipc, handle.IPC.import.openapiSchemas, async () => {
|
|
1597
1660
|
const result = await electron.dialog.showOpenDialog({
|
|
1598
1661
|
title: "Load OpenAPI spec for schema sync",
|
|
@@ -1719,7 +1782,7 @@ function javaClass(name) {
|
|
|
1719
1782
|
return name.replace(/[^\w\s]/g, " ").split(/\s+/).filter(Boolean).map((w) => w.charAt(0).toUpperCase() + w.slice(1)).join("");
|
|
1720
1783
|
}
|
|
1721
1784
|
function resolveEffectiveAuth(req, inherited) {
|
|
1722
|
-
return req.auth
|
|
1785
|
+
return requestCollection.authIsConfigured(req.auth) ? req.auth : inherited.auth ?? req.auth;
|
|
1723
1786
|
}
|
|
1724
1787
|
function mergeHeaders(req, inherited) {
|
|
1725
1788
|
return [...inherited.headers.filter((h) => h.enabled && h.key), ...req.headers.filter((h) => h.enabled && h.key)];
|
package/out/main/runner.js
CHANGED
|
@@ -2,12 +2,12 @@
|
|
|
2
2
|
"use strict";
|
|
3
3
|
const promises = require("fs/promises");
|
|
4
4
|
const path = require("path");
|
|
5
|
-
const requestExec = require("./chunks/request-exec-
|
|
6
|
-
const requestCollection = require("./chunks/request-collection-
|
|
5
|
+
const requestExec = require("./chunks/request-exec-C0DnGKdd.js");
|
|
6
|
+
const requestCollection = require("./chunks/request-collection-CJoXpvOw.js");
|
|
7
7
|
const environments = require("./chunks/environments-iM3SUM-4.js");
|
|
8
8
|
const cliCommon = require("./chunks/cli-common-CDQY1erJ.js");
|
|
9
9
|
require("undici");
|
|
10
|
-
require("./chunks/handle-
|
|
10
|
+
require("./chunks/handle-Coax8Nz1.js");
|
|
11
11
|
require("crypto");
|
|
12
12
|
require("dayjs");
|
|
13
13
|
require("vm");
|
|
@@ -396,7 +396,7 @@ async function main() {
|
|
|
396
396
|
} else if (!envName && workspace.settings?.defaultEnvironment && !env) {
|
|
397
397
|
console.warn(cliCommon.color(`Warning: default environment "${workspace.settings.defaultEnvironment}" not found. Running without environment.`, cliCommon.C.yellow));
|
|
398
398
|
}
|
|
399
|
-
const version = `v${"0.3.
|
|
399
|
+
const version = `v${"0.3.9"}`;
|
|
400
400
|
console.log("");
|
|
401
401
|
console.log(cliCommon.color(" API Test Runner" + (version ? ` ${version}` : ""), cliCommon.C.bold, cliCommon.C.white));
|
|
402
402
|
console.log(cliCommon.color(` Workspace: ${wsPath}`, cliCommon.C.gray));
|
|
@@ -448,7 +448,7 @@ async function main() {
|
|
|
448
448
|
for (const item of items) {
|
|
449
449
|
const req = item.request;
|
|
450
450
|
const inherited = requestCollection.resolveInheritedAuthAndHeaders(req.id, col);
|
|
451
|
-
if (req.auth
|
|
451
|
+
if (!requestCollection.authIsConfigured(req.auth) && inherited.auth && inherited.auth.type !== "none") {
|
|
452
452
|
req.auth = inherited.auth;
|
|
453
453
|
}
|
|
454
454
|
const inheritedHeaders = inherited.headers.filter((h) => h.enabled && h.key);
|
package/out/main/wsdl.js
CHANGED
|
@@ -4,10 +4,10 @@ const promises = require("fs/promises");
|
|
|
4
4
|
const path = require("path");
|
|
5
5
|
const https = require("https");
|
|
6
6
|
const http = require("http");
|
|
7
|
-
const soapHandler = require("./chunks/soap-handler-
|
|
8
|
-
const _import = require("./chunks/import-
|
|
7
|
+
const soapHandler = require("./chunks/soap-handler-B1Huudj7.js");
|
|
8
|
+
const _import = require("./chunks/import-Bilo697Z.js");
|
|
9
9
|
const cliCommon = require("./chunks/cli-common-CDQY1erJ.js");
|
|
10
|
-
require("./chunks/handle-
|
|
10
|
+
require("./chunks/handle-Coax8Nz1.js");
|
|
11
11
|
require("@xmldom/xmldom");
|
|
12
12
|
require("uuid");
|
|
13
13
|
function fetchUrl(url) {
|
package/out/preload/index.js
CHANGED
|
@@ -55,6 +55,7 @@ const IPC = {
|
|
|
55
55
|
insomnia: "import:insomnia",
|
|
56
56
|
bruno: "import:bruno",
|
|
57
57
|
http: "import:http",
|
|
58
|
+
spector: "import:spector",
|
|
58
59
|
openapiSchemas: "import:openapi-schemas",
|
|
59
60
|
openapiSchemasUrl: "import:openapi-schemas-url"
|
|
60
61
|
},
|
|
@@ -198,6 +199,7 @@ const api = {
|
|
|
198
199
|
importInsomnia: () => electron.ipcRenderer.invoke(IPC.import.insomnia),
|
|
199
200
|
importBruno: () => electron.ipcRenderer.invoke(IPC.import.bruno),
|
|
200
201
|
importHttpFile: () => electron.ipcRenderer.invoke(IPC.import.http),
|
|
202
|
+
importSpectorCollection: () => electron.ipcRenderer.invoke(IPC.import.spector),
|
|
201
203
|
/** Extract response-body schemas from an OpenAPI spec file (no full import). */
|
|
202
204
|
extractOpenApiSchemas: () => electron.ipcRenderer.invoke(IPC.import.openapiSchemas),
|
|
203
205
|
/** Extract response-body schemas from an OpenAPI spec URL (no full import). */
|
|
@@ -14350,14 +14350,14 @@ function useWorkspaceLoader() {
|
|
|
14350
14350
|
} else {
|
|
14351
14351
|
useStore.getState().setHistory([]);
|
|
14352
14352
|
}
|
|
14353
|
-
for (const colPath of ws2.collections) {
|
|
14353
|
+
for (const colPath of ws2.collections ?? []) {
|
|
14354
14354
|
try {
|
|
14355
14355
|
const col = await electron$r.loadCollection(colPath);
|
|
14356
14356
|
loadCollection(colPath, col);
|
|
14357
14357
|
} catch {
|
|
14358
14358
|
}
|
|
14359
14359
|
}
|
|
14360
|
-
for (const envPath of ws2.environments) {
|
|
14360
|
+
for (const envPath of ws2.environments ?? []) {
|
|
14361
14361
|
try {
|
|
14362
14362
|
const env = await electron$r.loadEnvironment(envPath);
|
|
14363
14363
|
loadEnvironment(envPath, env);
|
|
@@ -14388,7 +14388,7 @@ function useWorkspaceLoader() {
|
|
|
14388
14388
|
for (const { relPath, snapshot } of snapshots) loadContractSnapshot(relPath, snapshot);
|
|
14389
14389
|
} catch {
|
|
14390
14390
|
}
|
|
14391
|
-
if (ws2.collections.length > 0) {
|
|
14391
|
+
if ((ws2.collections ?? []).length > 0) {
|
|
14392
14392
|
try {
|
|
14393
14393
|
const firstCol = await electron$r.loadCollection(ws2.collections[0]);
|
|
14394
14394
|
setActiveCollection(firstCol.id);
|
|
@@ -36531,6 +36531,10 @@ function DotsBtn({ items: items2 }) {
|
|
|
36531
36531
|
menu && /* @__PURE__ */ jsxRuntimeExports.jsx(ContextMenu, { items: items2, x: menu.x, y: menu.y, onClose: () => setMenu(null) })
|
|
36532
36532
|
] });
|
|
36533
36533
|
}
|
|
36534
|
+
function requestPath(url) {
|
|
36535
|
+
const trimmed = url.trim().replace(/^\{\{[^}]+\}\}/, "").replace(/^https?:\/\/[^/]+/i, "");
|
|
36536
|
+
return trimmed || url.trim();
|
|
36537
|
+
}
|
|
36534
36538
|
const HOOK_LABELS = {
|
|
36535
36539
|
beforeAll: "Before All",
|
|
36536
36540
|
before: "Before",
|
|
@@ -36557,6 +36561,7 @@ function RequestRow({
|
|
|
36557
36561
|
folderId,
|
|
36558
36562
|
reqIndex,
|
|
36559
36563
|
name: name2,
|
|
36564
|
+
url,
|
|
36560
36565
|
method,
|
|
36561
36566
|
protocol,
|
|
36562
36567
|
authType,
|
|
@@ -36658,6 +36663,10 @@ function RequestRow({
|
|
|
36658
36663
|
}
|
|
36659
36664
|
)
|
|
36660
36665
|
] }),
|
|
36666
|
+
(() => {
|
|
36667
|
+
const path = requestPath(url);
|
|
36668
|
+
return path && path !== name2 ? /* @__PURE__ */ jsxRuntimeExports.jsx("span", { className: "block text-[10px] text-surface-500 font-mono truncate leading-tight", title: url, children: path }) : null;
|
|
36669
|
+
})(),
|
|
36661
36670
|
(tags2.length > 0 || addingTag) && /* @__PURE__ */ jsxRuntimeExports.jsx(
|
|
36662
36671
|
TagChips,
|
|
36663
36672
|
{
|
|
@@ -37241,6 +37250,7 @@ function FolderContents({
|
|
|
37241
37250
|
folderId: folder.id,
|
|
37242
37251
|
reqIndex,
|
|
37243
37252
|
name: req.name,
|
|
37253
|
+
url: req.url,
|
|
37244
37254
|
method: req.method,
|
|
37245
37255
|
protocol: req.protocol,
|
|
37246
37256
|
authType: req.auth.type,
|
|
@@ -37358,6 +37368,25 @@ function getHooksForRequest(requestId, collection) {
|
|
|
37358
37368
|
}
|
|
37359
37369
|
return { before, after: afterReversed.reverse() };
|
|
37360
37370
|
}
|
|
37371
|
+
function authIsConfigured(auth) {
|
|
37372
|
+
if (!auth || auth.type === "none") return false;
|
|
37373
|
+
const set2 = (s) => !!(s && s.trim());
|
|
37374
|
+
switch (auth.type) {
|
|
37375
|
+
case "bearer":
|
|
37376
|
+
return set2(auth.token) || set2(auth.tokenSecretRef);
|
|
37377
|
+
case "basic":
|
|
37378
|
+
case "digest":
|
|
37379
|
+
return set2(auth.username) || set2(auth.password) || set2(auth.passwordSecretRef);
|
|
37380
|
+
case "ntlm":
|
|
37381
|
+
return set2(auth.username) || set2(auth.password) || set2(auth.passwordSecretRef);
|
|
37382
|
+
case "apikey":
|
|
37383
|
+
return set2(auth.apiKeyValue) || set2(auth.apiKeySecretRef);
|
|
37384
|
+
case "oauth2":
|
|
37385
|
+
return set2(auth.oauth2TokenUrl) || set2(auth.oauth2ClientId) || set2(auth.oauth2CachedToken);
|
|
37386
|
+
default:
|
|
37387
|
+
return true;
|
|
37388
|
+
}
|
|
37389
|
+
}
|
|
37361
37390
|
function resolveInheritedAuthAndHeaders(requestId, collection) {
|
|
37362
37391
|
let inheritedAuth = collection.auth && collection.auth.type !== "none" ? collection.auth : null;
|
|
37363
37392
|
let inheritedHeaders = collection.headers?.filter((h) => h.enabled && h.key) ?? [];
|
|
@@ -63829,7 +63858,7 @@ function RequestBuilder({ request }) {
|
|
|
63829
63858
|
};
|
|
63830
63859
|
let liveGlobals = { ...globals };
|
|
63831
63860
|
const inherited = useStore.getState().getInheritedAuthAndHeaders(request.id);
|
|
63832
|
-
const mergedAuth = request.auth
|
|
63861
|
+
const mergedAuth = authIsConfigured(request.auth) ? request.auth : inherited.auth ?? request.auth;
|
|
63833
63862
|
const mergedHeaders = [
|
|
63834
63863
|
...inherited.headers.filter((h) => h.enabled),
|
|
63835
63864
|
...request.headers
|
|
@@ -67233,7 +67262,8 @@ const OPTIONS = [
|
|
|
67233
67262
|
{ id: "openapi", label: "OpenAPI", description: "JSON or YAML (v3.x)", supportsUrl: true },
|
|
67234
67263
|
{ id: "insomnia", label: "Insomnia", description: "Export v4 JSON" },
|
|
67235
67264
|
{ id: "bruno", label: "Bruno", description: "bruno.json collection file" },
|
|
67236
|
-
{ id: "http", label: "HTTP file", description: ".http / .rest (REST Client)" }
|
|
67265
|
+
{ id: "http", label: "HTTP file", description: ".http / .rest (REST Client)" },
|
|
67266
|
+
{ id: "spector", label: "API Spector", description: "An existing .spector / .json collection" }
|
|
67237
67267
|
];
|
|
67238
67268
|
function listEndpoints(col) {
|
|
67239
67269
|
const result = [];
|
|
@@ -67304,6 +67334,7 @@ function ImportModal({ onImport, onClose }) {
|
|
|
67304
67334
|
if (opt2.id === "insomnia") col = await electron$9.importInsomnia();
|
|
67305
67335
|
if (opt2.id === "bruno") col = await electron$9.importBruno();
|
|
67306
67336
|
if (opt2.id === "http") col = await electron$9.importHttpFile();
|
|
67337
|
+
if (opt2.id === "spector") col = await electron$9.importSpectorCollection();
|
|
67307
67338
|
if (!col) {
|
|
67308
67339
|
setLoading(false);
|
|
67309
67340
|
return;
|
|
@@ -68506,7 +68537,7 @@ function RunnerModal() {
|
|
|
68506
68537
|
items2 = items2.map((item) => {
|
|
68507
68538
|
const inherited = resolveInheritedAuthAndHeaders(item.request.id, col);
|
|
68508
68539
|
const req = JSON.parse(JSON.stringify(item.request));
|
|
68509
|
-
if (req.auth
|
|
68540
|
+
if (!authIsConfigured(req.auth) && inherited.auth && inherited.auth.type !== "none") {
|
|
68510
68541
|
req.auth = inherited.auth;
|
|
68511
68542
|
}
|
|
68512
68543
|
const inheritedHeaders = inherited.headers.filter((h) => h.enabled && h.key);
|
|
@@ -72054,7 +72085,7 @@ function App() {
|
|
|
72054
72085
|
/* @__PURE__ */ jsxRuntimeExports.jsx("span", { style: { color: "#6aa3c8" }, children: "Spector" }),
|
|
72055
72086
|
/* @__PURE__ */ jsxRuntimeExports.jsxs("span", { className: "ml-2 text-[10px] font-normal opacity-50", children: [
|
|
72056
72087
|
"v",
|
|
72057
|
-
"0.3.
|
|
72088
|
+
"0.3.9"
|
|
72058
72089
|
] }),
|
|
72059
72090
|
/* @__PURE__ */ jsxRuntimeExports.jsx("span", { className: "mx-2 opacity-30", children: "·" }),
|
|
72060
72091
|
/* @__PURE__ */ jsxRuntimeExports.jsx(
|
package/out/renderer/index.html
CHANGED
|
@@ -5,7 +5,7 @@
|
|
|
5
5
|
<meta charset="UTF-8" />
|
|
6
6
|
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
|
7
7
|
<title>API Spector</title>
|
|
8
|
-
<script type="module" crossorigin src="./assets/index-
|
|
8
|
+
<script type="module" crossorigin src="./assets/index-BdUvP_cg.js"></script>
|
|
9
9
|
<link rel="stylesheet" crossorigin href="./assets/index-B6kFQEbI.css">
|
|
10
10
|
</head>
|
|
11
11
|
|