@clarify-labs/renderer 0.1.0 → 0.4.0
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/output/{AppShell-DBgUlirU.cjs → AppShell-CZw1MrPG.cjs} +1119 -394
- package/output/AppShell-CZw1MrPG.cjs.map +1 -0
- package/output/{AppShell-C_bj6ZhV.js → AppShell-nQnuKyn2.js} +1098 -397
- package/output/AppShell-nQnuKyn2.js.map +1 -0
- package/output/client.cjs +1 -1
- package/output/client.js +1 -1
- package/output/components/Callout.d.ts +10 -0
- package/output/components/Card.d.ts +15 -0
- package/output/components/PageNavigation.d.ts +5 -0
- package/output/components/index.d.ts +5 -0
- package/output/context.d.ts +2 -0
- package/output/i18n.d.ts +5 -0
- package/output/index.cjs +1357 -346
- package/output/index.cjs.map +1 -1
- package/output/index.d.ts +2 -2
- package/output/index.js +1355 -347
- package/output/index.js.map +1 -1
- package/output/mdx/components.d.ts +3 -0
- package/output/mdx/primitives.d.ts +2 -2
- package/output/openapi/example-panels.d.ts +31 -0
- package/output/openapi/helpers.d.ts +24 -0
- package/output/openapi/index.d.ts +2 -19
- package/output/openapi/openapi-page.d.ts +19 -0
- package/output/openapi/request-code.d.ts +16 -0
- package/output/openapi/schema-properties.d.ts +15 -0
- package/output/openapi/spec-path.d.ts +2 -0
- package/output/openapi/types.d.ts +66 -0
- package/output/{render-Ca4Is683.js → render-BCiQn6Q1.js} +2 -2
- package/output/{render-Ca4Is683.js.map → render-BCiQn6Q1.js.map} +1 -1
- package/output/{render-CLI-MnH_.cjs → render-CZsdzmme.cjs} +2 -2
- package/output/{render-CLI-MnH_.cjs.map → render-CZsdzmme.cjs.map} +1 -1
- package/output/renderer.css +1636 -551
- package/output/server.cjs +1 -1
- package/output/server.js +1 -1
- package/output/shell/ContentActions.d.ts +1 -0
- package/output/shell/Header.d.ts +4 -3
- package/output/shell/icons.d.ts +4 -0
- package/output/shell/mobile.d.ts +2 -1
- package/output/types.d.ts +62 -9
- package/output/utils/path.d.ts +2 -0
- package/package.json +7 -1
- package/output/AppShell-C_bj6ZhV.js.map +0 -1
- package/output/AppShell-DBgUlirU.cjs.map +0 -1
package/output/index.js
CHANGED
|
@@ -1,12 +1,13 @@
|
|
|
1
|
-
import { C as
|
|
2
|
-
import { t as render } from "./render-
|
|
3
|
-
import
|
|
1
|
+
import { A as remToPx, C as useBuiltInText, D as useOpenApis, E as useClarifyConfig, O as SectionProvider, S as BuiltWithClarify, T as OpenApisContext, _ as CodeGroup, a as Heading, b as CardGroup, c as Tag, d as useTheme, f as PageFooter, g as Code, h as Feedback, i as DocShell, k as useSectionStore, l as ThemeToggle, m as HeroPattern, n as ApiEndpointCard, o as Logo, p as GridPattern, r as Button, s as Prose, t as AppShell, u as ThemeProvider, v as Pre, w as ClarifyConfigContext, x as Callout, y as Card } from "./AppShell-nQnuKyn2.js";
|
|
2
|
+
import { t as render } from "./render-BCiQn6Q1.js";
|
|
3
|
+
import clsx from "clsx";
|
|
4
|
+
import { createElement, useState } from "react";
|
|
4
5
|
import { Link, useLocation } from "react-router-dom";
|
|
5
6
|
import { Fragment as Fragment$1, jsx, jsxs } from "react/jsx-runtime";
|
|
6
|
-
import
|
|
7
|
+
import { CheckIcon, ChevronDown, ChevronDownIcon, ChevronRight, ChevronsUpDownIcon, ClipboardIcon, CodeIcon, LockKeyholeIcon, PackageIcon, ServerIcon, UnlockKeyholeIcon } from "lucide-react";
|
|
7
8
|
import { Listbox, ListboxButton, ListboxOption, ListboxOptions } from "@headlessui/react";
|
|
8
|
-
import { CheckIcon, ChevronsUpDownIcon } from "lucide-react";
|
|
9
9
|
import { slug } from "github-slugger";
|
|
10
|
+
import { snippetz } from "@scalar/snippetz";
|
|
10
11
|
//#region \0rolldown/runtime.js
|
|
11
12
|
var __defProp = Object.defineProperty;
|
|
12
13
|
var __exportAll = (all, no_symbols) => {
|
|
@@ -22,6 +23,9 @@ var __exportAll = (all, no_symbols) => {
|
|
|
22
23
|
//#region source/mdx/primitives.tsx
|
|
23
24
|
var primitives_exports = /* @__PURE__ */ __exportAll({
|
|
24
25
|
Button: () => Button,
|
|
26
|
+
Callout: () => Callout,
|
|
27
|
+
Card: () => Card,
|
|
28
|
+
CardGroup: () => CardGroup,
|
|
25
29
|
CodeGroup: () => CodeGroup,
|
|
26
30
|
Col: () => Col,
|
|
27
31
|
Note: () => Note,
|
|
@@ -37,12 +41,12 @@ var primitives_exports = /* @__PURE__ */ __exportAll({
|
|
|
37
41
|
});
|
|
38
42
|
function wrapper(arg0) {
|
|
39
43
|
const { children } = arg0;
|
|
40
|
-
return /* @__PURE__ */
|
|
44
|
+
return /* @__PURE__ */ jsx("article", {
|
|
41
45
|
className: "clarify-mdx-page flex h-full flex-col pt-16 pb-10",
|
|
42
|
-
children:
|
|
46
|
+
children: /* @__PURE__ */ jsx(Prose, {
|
|
43
47
|
className: "flex-auto",
|
|
44
48
|
children
|
|
45
|
-
})
|
|
49
|
+
})
|
|
46
50
|
});
|
|
47
51
|
}
|
|
48
52
|
function a(arg0) {
|
|
@@ -101,8 +105,8 @@ function InfoIcon(props) {
|
|
|
101
105
|
function Note(arg0) {
|
|
102
106
|
const { children } = arg0;
|
|
103
107
|
return /* @__PURE__ */ jsxs("div", {
|
|
104
|
-
className: "clarify-note my-6 flex gap-2.5 rounded-
|
|
105
|
-
children: [/* @__PURE__ */ jsx(InfoIcon, { className: "mt-1 h-4 w-4 flex-none fill-
|
|
108
|
+
className: "clarify-note my-6 flex gap-2.5 rounded-(--clarify-theme-tokens-radius-xl) border border-(--clarify-ui-accent-border) bg-(--clarify-ui-accent-background) p-4 text-sm/6 text-(--clarify-theme-tokens-colors-foreground) dark:text-zinc-100 dark:[--tw-prose-links-hover:var(--clarify-ui-accent-text)] dark:[--tw-prose-links:var(--color-white)]",
|
|
109
|
+
children: [/* @__PURE__ */ jsx(InfoIcon, { className: "mt-1 h-4 w-4 flex-none fill-(--clarify-ui-accent-text) stroke-(--clarify-theme-tokens-colors-surface) dark:fill-(--clarify-ui-accent-background) dark:stroke-(--clarify-ui-accent-text)" }), /* @__PURE__ */ jsx("div", {
|
|
106
110
|
className: "*:first:mt-0 *:last:mb-0",
|
|
107
111
|
children
|
|
108
112
|
})]
|
|
@@ -111,7 +115,7 @@ function Note(arg0) {
|
|
|
111
115
|
function Row(arg0) {
|
|
112
116
|
const { children } = arg0;
|
|
113
117
|
return /* @__PURE__ */ jsx("div", {
|
|
114
|
-
className: "clarify-row grid grid-cols-1 items-start gap-x-
|
|
118
|
+
className: "clarify-row grid grid-cols-1 items-start gap-x-8 gap-y-10 xl:max-w-none xl:grid-cols-2",
|
|
115
119
|
children
|
|
116
120
|
});
|
|
117
121
|
}
|
|
@@ -144,12 +148,15 @@ function Property(arg0) {
|
|
|
144
148
|
className: "sr-only",
|
|
145
149
|
children: "Name"
|
|
146
150
|
}),
|
|
147
|
-
/* @__PURE__ */ jsx("dd", { children: /* @__PURE__ */ jsx("
|
|
151
|
+
/* @__PURE__ */ jsx("dd", { children: /* @__PURE__ */ jsx("span", {
|
|
152
|
+
className: "text-sm/5 font-semibold text-zinc-950 dark:text-white",
|
|
153
|
+
children: name
|
|
154
|
+
}) }),
|
|
148
155
|
type ? /* @__PURE__ */ jsxs(Fragment$1, { children: [/* @__PURE__ */ jsx("dt", {
|
|
149
156
|
className: "sr-only",
|
|
150
157
|
children: "Type"
|
|
151
158
|
}), /* @__PURE__ */ jsx("dd", {
|
|
152
|
-
className: "font-mono text-xs text-
|
|
159
|
+
className: "font-mono text-xs text-(--clarify-theme-tokens-colors-muted) dark:text-zinc-500",
|
|
153
160
|
children: type
|
|
154
161
|
})] }) : null,
|
|
155
162
|
/* @__PURE__ */ jsx("dt", {
|
|
@@ -165,43 +172,7 @@ function Property(arg0) {
|
|
|
165
172
|
});
|
|
166
173
|
}
|
|
167
174
|
//#endregion
|
|
168
|
-
//#region source/openapi/
|
|
169
|
-
var OPENAPI_HTTP_METHODS = [
|
|
170
|
-
"get",
|
|
171
|
-
"put",
|
|
172
|
-
"post",
|
|
173
|
-
"delete",
|
|
174
|
-
"options",
|
|
175
|
-
"head",
|
|
176
|
-
"patch",
|
|
177
|
-
"trace"
|
|
178
|
-
];
|
|
179
|
-
function isOpenAPIHttpMethod(method) {
|
|
180
|
-
return OPENAPI_HTTP_METHODS.includes(method.toLowerCase());
|
|
181
|
-
}
|
|
182
|
-
function getOpenApiOperation(spec, path, method) {
|
|
183
|
-
if (!isOpenAPIHttpMethod(method)) return void 0;
|
|
184
|
-
return spec.paths?.[path]?.[method.toLowerCase()];
|
|
185
|
-
}
|
|
186
|
-
function listOpenApiOperations(spec) {
|
|
187
|
-
const paths = spec.paths ?? {};
|
|
188
|
-
const operations = [];
|
|
189
|
-
for (const [path, pathItem] of Object.entries(paths)) {
|
|
190
|
-
if (!pathItem) continue;
|
|
191
|
-
for (const method of OPENAPI_HTTP_METHODS) {
|
|
192
|
-
const operation = pathItem[method];
|
|
193
|
-
if (operation) operations.push({
|
|
194
|
-
path,
|
|
195
|
-
method,
|
|
196
|
-
operation
|
|
197
|
-
});
|
|
198
|
-
}
|
|
199
|
-
}
|
|
200
|
-
return operations;
|
|
201
|
-
}
|
|
202
|
-
//#endregion
|
|
203
|
-
//#region source/openapi/index.tsx
|
|
204
|
-
var VIRTUAL_PREFIX = "virtual:clarify-page/";
|
|
175
|
+
//#region source/openapi/helpers.ts
|
|
205
176
|
function isRecord(value) {
|
|
206
177
|
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
207
178
|
}
|
|
@@ -211,6 +182,16 @@ function isReference(value) {
|
|
|
211
182
|
function resolveReferenceName(ref) {
|
|
212
183
|
return ref.split("/").filter(Boolean).at(-1) ?? ref;
|
|
213
184
|
}
|
|
185
|
+
function resolveOpenApiRef(spec, ref) {
|
|
186
|
+
if (!ref.startsWith("#/")) return void 0;
|
|
187
|
+
return ref.slice(2).split("/").map((part) => part.replace(/~1/g, "/").replace(/~0/g, "~")).reduce((current, part) => isRecord(current) ? current[part] : void 0, spec);
|
|
188
|
+
}
|
|
189
|
+
function resolveSchema(spec, schema, seen = /* @__PURE__ */ new Set()) {
|
|
190
|
+
if (!isReference(schema)) return schema;
|
|
191
|
+
if (seen.has(schema.$ref)) return schema;
|
|
192
|
+
seen.add(schema.$ref);
|
|
193
|
+
return resolveSchema(spec, resolveOpenApiRef(spec, schema.$ref), seen) ?? schema;
|
|
194
|
+
}
|
|
214
195
|
function getPathItem(spec, path) {
|
|
215
196
|
const pathItem = spec.paths?.[path];
|
|
216
197
|
return isRecord(pathItem) ? pathItem : void 0;
|
|
@@ -220,7 +201,7 @@ function getOperationParameters(spec, path, operation) {
|
|
|
220
201
|
const operationParameters = operation.parameters;
|
|
221
202
|
return [...Array.isArray(pathParameters) ? pathParameters : [], ...Array.isArray(operationParameters) ? operationParameters : []].filter((parameter) => isRecord(parameter) && !isReference(parameter));
|
|
222
203
|
}
|
|
223
|
-
function getRequestBody(operation) {
|
|
204
|
+
function getRequestBody$1(operation) {
|
|
224
205
|
const requestBody = operation.requestBody;
|
|
225
206
|
return isRecord(requestBody) && !isReference(requestBody) ? requestBody : void 0;
|
|
226
207
|
}
|
|
@@ -276,7 +257,7 @@ function getExampleEntries(mediaType) {
|
|
|
276
257
|
const generated = schemaToExample(mediaType.schema);
|
|
277
258
|
return typeof generated === "undefined" ? [] : [{
|
|
278
259
|
key: "schema",
|
|
279
|
-
title: "
|
|
260
|
+
title: "schema",
|
|
280
261
|
value: generated,
|
|
281
262
|
generated: true
|
|
282
263
|
}];
|
|
@@ -287,11 +268,14 @@ function getContentExample(mediaType) {
|
|
|
287
268
|
function schemaToType(schema) {
|
|
288
269
|
if (!isRecord(schema)) return void 0;
|
|
289
270
|
if (isReference(schema)) return resolveReferenceName(schema.$ref);
|
|
271
|
+
if (typeof schema.const !== "undefined") return JSON.stringify(schema.const);
|
|
290
272
|
if (Array.isArray(schema.enum)) return schema.enum.map(String).join(" | ");
|
|
291
273
|
const oneOf = schema.oneOf ?? schema.anyOf;
|
|
292
274
|
if (Array.isArray(oneOf)) return oneOf.map(schemaToType).filter(Boolean).join(" | ");
|
|
275
|
+
if (Array.isArray(schema.allOf)) return schema.allOf.map(schemaToType).filter(Boolean).join(" & ");
|
|
293
276
|
if (schema.type === "array") return `${schemaToType(schema.items) ?? "unknown"}[]`;
|
|
294
|
-
|
|
277
|
+
const type = Array.isArray(schema.type) ? schema.type.map(String).join(" | ") : schema.type;
|
|
278
|
+
return typeof type === "string" ? [type, typeof schema.format === "string" ? `<${schema.format}>` : void 0].filter(Boolean).join("") : void 0;
|
|
295
279
|
}
|
|
296
280
|
function schemaToExample(schema, depth = 0) {
|
|
297
281
|
if (!isRecord(schema) || depth > 3) return void 0;
|
|
@@ -319,33 +303,6 @@ function stringifyExample(value) {
|
|
|
319
303
|
if (typeof value === "string") return value;
|
|
320
304
|
return JSON.stringify(value, null, 2);
|
|
321
305
|
}
|
|
322
|
-
function shellQuote(value) {
|
|
323
|
-
return `'${value.replace(/'/g, `'"'"'`)}'`;
|
|
324
|
-
}
|
|
325
|
-
function getServerUrl(spec) {
|
|
326
|
-
const servers = spec.servers;
|
|
327
|
-
if (!Array.isArray(servers)) return "";
|
|
328
|
-
const firstServer = servers.find(isRecord);
|
|
329
|
-
return typeof firstServer?.url === "string" ? firstServer.url : "";
|
|
330
|
-
}
|
|
331
|
-
function buildOperationUrl(spec, path, parameters) {
|
|
332
|
-
const query = parameters.filter((parameter) => parameter.in === "query" && parameter.name).map((parameter) => `${parameter.name}={${parameter.name}}`).join("&");
|
|
333
|
-
return `${getServerUrl(spec).replace(/\/$/, "")}${path}${query ? `?${query}` : ""}`;
|
|
334
|
-
}
|
|
335
|
-
function buildCurlExample(arg0) {
|
|
336
|
-
const { spec, path, method, parameters, requestContent } = arg0;
|
|
337
|
-
const url = buildOperationUrl(spec, path, parameters);
|
|
338
|
-
const lines = [`curl ${method === "GET" ? "-G " : ""}${shellQuote(url)}`];
|
|
339
|
-
if (method !== "GET") lines.push(` -X ${method}`);
|
|
340
|
-
lines.push(" -H 'Authorization: Bearer {token}'");
|
|
341
|
-
lines.push(" -H 'Accept: application/json'");
|
|
342
|
-
const requestExample = getContentExample(requestContent?.value);
|
|
343
|
-
if (requestContent && typeof requestExample !== "undefined") {
|
|
344
|
-
lines.push(` -H 'Content-Type: ${requestContent.mediaType}'`);
|
|
345
|
-
lines.push(` -d ${shellQuote(stringifyExample(requestExample))}`);
|
|
346
|
-
}
|
|
347
|
-
return lines.join(" \\\n");
|
|
348
|
-
}
|
|
349
306
|
function getResponseEntries(operation) {
|
|
350
307
|
const responses = operation.responses;
|
|
351
308
|
if (!isRecord(responses)) return [];
|
|
@@ -354,45 +311,6 @@ function getResponseEntries(operation) {
|
|
|
354
311
|
response
|
|
355
312
|
}));
|
|
356
313
|
}
|
|
357
|
-
function SchemaProperties(arg0) {
|
|
358
|
-
const { title, schema } = arg0;
|
|
359
|
-
const targetSchema = isReference(schema) ? void 0 : schema;
|
|
360
|
-
const properties = isRecord(targetSchema) && isRecord(targetSchema.properties) ? targetSchema.properties : void 0;
|
|
361
|
-
const required = isRecord(targetSchema) && Array.isArray(targetSchema.required) ? targetSchema.required.map(String) : [];
|
|
362
|
-
if (!properties || Object.keys(properties).length === 0) return null;
|
|
363
|
-
return /* @__PURE__ */ jsxs("div", { children: [/* @__PURE__ */ jsx("h3", { children: title }), /* @__PURE__ */ jsx(Properties, { children: Object.entries(properties).map(([name, propertySchema]) => {
|
|
364
|
-
const property = isRecord(propertySchema) ? propertySchema : {};
|
|
365
|
-
const type = schemaToType(propertySchema);
|
|
366
|
-
const description = typeof property.description === "string" ? property.description : void 0;
|
|
367
|
-
const isRequired = required.includes(name);
|
|
368
|
-
return /* @__PURE__ */ jsx(Property, {
|
|
369
|
-
name,
|
|
370
|
-
type: isRequired && type ? `${type}, required` : type,
|
|
371
|
-
children: description ?? (isRequired ? "Required." : "Optional.")
|
|
372
|
-
}, name);
|
|
373
|
-
}) })] });
|
|
374
|
-
}
|
|
375
|
-
function ParameterList(arg0) {
|
|
376
|
-
const { title, parameters } = arg0;
|
|
377
|
-
if (parameters.length === 0) return null;
|
|
378
|
-
return /* @__PURE__ */ jsxs("div", { children: [/* @__PURE__ */ jsx("h3", { children: title }), /* @__PURE__ */ jsx(Properties, { children: parameters.map((parameter) => /* @__PURE__ */ jsx(Property, {
|
|
379
|
-
name: parameter.name ?? "parameter",
|
|
380
|
-
type: [schemaToType(parameter.schema), parameter.required ? "required" : void 0].filter(Boolean).join(", ") || void 0,
|
|
381
|
-
children: parameter.description ?? `${parameter.in ?? "Operation"} parameter.`
|
|
382
|
-
}, `${parameter.in}-${parameter.name}`)) })] });
|
|
383
|
-
}
|
|
384
|
-
function ResponseList(arg0) {
|
|
385
|
-
const { operation } = arg0;
|
|
386
|
-
const responses = getResponseEntries(operation);
|
|
387
|
-
if (responses.length === 0) return null;
|
|
388
|
-
return /* @__PURE__ */ jsxs("div", { children: [/* @__PURE__ */ jsx("h3", { children: "Responses" }), /* @__PURE__ */ jsx(Properties, { children: responses.map(({ status, response }) => {
|
|
389
|
-
return /* @__PURE__ */ jsx(Property, {
|
|
390
|
-
name: status,
|
|
391
|
-
type: schemaToType(getJsonLikeContent(response.content)?.value.schema),
|
|
392
|
-
children: response.description ?? "Response."
|
|
393
|
-
}, status);
|
|
394
|
-
}) })] });
|
|
395
|
-
}
|
|
396
314
|
function codeLanguageForMediaType(mediaType) {
|
|
397
315
|
if (!mediaType) return "json";
|
|
398
316
|
if (mediaType.includes("json")) return "json";
|
|
@@ -401,112 +319,523 @@ function codeLanguageForMediaType(mediaType) {
|
|
|
401
319
|
if (mediaType.includes("xml")) return "xml";
|
|
402
320
|
return "text";
|
|
403
321
|
}
|
|
322
|
+
//#endregion
|
|
323
|
+
//#region source/openapi/request-code.ts
|
|
324
|
+
var snippetGenerator = snippetz();
|
|
325
|
+
function getDefaultServer(spec) {
|
|
326
|
+
const servers = spec.servers;
|
|
327
|
+
if (!Array.isArray(servers)) return { url: "https://api.example.com" };
|
|
328
|
+
const firstServer = servers.find(isRecord);
|
|
329
|
+
return firstServer && typeof firstServer.url === "string" ? firstServer : { url: "https://api.example.com" };
|
|
330
|
+
}
|
|
331
|
+
function expandServerUrl(server, serverVariables = {}) {
|
|
332
|
+
return (server.url ?? "https://api.example.com").replace(/\{([^}]+)\}/g, (_, name) => {
|
|
333
|
+
const fallback = server.variables?.[name]?.default ?? name;
|
|
334
|
+
return serverVariables[name] ?? fallback;
|
|
335
|
+
});
|
|
336
|
+
}
|
|
337
|
+
function buildOperationUrl(input) {
|
|
338
|
+
return `${expandServerUrl(input.server ?? getDefaultServer(input.spec), input.serverVariables).replace(/\/$/, "")}${input.path}`;
|
|
339
|
+
}
|
|
340
|
+
function getQueryString(parameters, auth) {
|
|
341
|
+
const queryString = parameters.filter((parameter) => parameter.in === "query" && parameter.name).map((parameter) => ({
|
|
342
|
+
name: parameter.name,
|
|
343
|
+
value: encodeUrlPlaceholders(`{${parameter.name}}`)
|
|
344
|
+
}));
|
|
345
|
+
if (auth?.scheme.type === "apiKey" && auth.scheme.in === "query" && auth.scheme.name) queryString.push({
|
|
346
|
+
name: auth.scheme.name,
|
|
347
|
+
value: auth.value
|
|
348
|
+
});
|
|
349
|
+
return queryString;
|
|
350
|
+
}
|
|
351
|
+
function isFormMediaType(mediaType) {
|
|
352
|
+
return mediaType.includes("multipart/form-data") || mediaType.includes("application/x-www-form-urlencoded");
|
|
353
|
+
}
|
|
354
|
+
function isBinarySchema(schema) {
|
|
355
|
+
return isRecord(schema) && schema.type === "string" && schema.format === "binary";
|
|
356
|
+
}
|
|
357
|
+
function getSchemaProperties(schema) {
|
|
358
|
+
return isRecord(schema) && isRecord(schema.properties) ? schema.properties : {};
|
|
359
|
+
}
|
|
360
|
+
function getFieldValue(name, value, schema) {
|
|
361
|
+
if (isRecord(value) && typeof value[name] !== "undefined") return value[name];
|
|
362
|
+
if (isBinarySchema(schema)) return `@${name}`;
|
|
363
|
+
}
|
|
364
|
+
function getFormParams(value, requestContent) {
|
|
365
|
+
const properties = getSchemaProperties(requestContent.value.schema);
|
|
366
|
+
return Array.from(new Set([...Object.keys(properties), ...isRecord(value) ? Object.keys(value) : []])).flatMap((name) => {
|
|
367
|
+
const fieldValue = getFieldValue(name, value, properties[name]);
|
|
368
|
+
if (typeof fieldValue === "undefined") return [];
|
|
369
|
+
const contentType = requestContent.value.encoding?.[name]?.contentType;
|
|
370
|
+
return [{
|
|
371
|
+
name,
|
|
372
|
+
value: typeof fieldValue === "string" ? fieldValue : stringifyExample(fieldValue),
|
|
373
|
+
...contentType ? { contentType } : {}
|
|
374
|
+
}];
|
|
375
|
+
});
|
|
376
|
+
}
|
|
377
|
+
function getBodySize(requestBody) {
|
|
378
|
+
if (requestBody?.serialized) return requestBody.serialized.length;
|
|
379
|
+
return requestBody?.params?.reduce((size, param) => size + param.name.length + String(param.value ?? "").length, 0) ?? 0;
|
|
380
|
+
}
|
|
381
|
+
function getRequestBody(requestContent) {
|
|
382
|
+
const value = getContentExample(requestContent?.value);
|
|
383
|
+
if (!requestContent || typeof value === "undefined") return void 0;
|
|
384
|
+
if (isFormMediaType(requestContent.mediaType)) {
|
|
385
|
+
const params = getFormParams(value, requestContent);
|
|
386
|
+
return params.length > 0 ? { params } : void 0;
|
|
387
|
+
}
|
|
388
|
+
return { serialized: stringifyExample(value) };
|
|
389
|
+
}
|
|
390
|
+
function getAuthorizationValue(auth) {
|
|
391
|
+
if (auth.scheme.type === "http" && auth.scheme.scheme?.toLowerCase() === "bearer") return `Bearer ${auth.value}`;
|
|
392
|
+
if (auth.scheme.type === "http" && auth.scheme.scheme?.toLowerCase() === "basic") return `Basic ${auth.value}`;
|
|
393
|
+
if (auth.scheme.type === "oauth2" || auth.scheme.type === "openIdConnect") return `Bearer ${auth.value}`;
|
|
394
|
+
}
|
|
395
|
+
function getAuthHeaders(auth) {
|
|
396
|
+
if (!auth) return {};
|
|
397
|
+
if (auth.scheme.type === "apiKey" && auth.scheme.in === "header" && auth.scheme.name) return { [auth.scheme.name]: auth.value };
|
|
398
|
+
const authorization = getAuthorizationValue(auth);
|
|
399
|
+
return authorization ? { Authorization: authorization } : {};
|
|
400
|
+
}
|
|
401
|
+
function getRequestHeaders(requestContent, auth) {
|
|
402
|
+
return {
|
|
403
|
+
...getAuthHeaders(auth),
|
|
404
|
+
Accept: "application/json",
|
|
405
|
+
...requestContent ? { "Content-Type": requestContent.mediaType } : {}
|
|
406
|
+
};
|
|
407
|
+
}
|
|
408
|
+
function encodeUrlPlaceholders(url) {
|
|
409
|
+
return url.replace(/\{([^}]+)\}/g, (_, name) => `%7B${encodeURIComponent(name)}%7D`);
|
|
410
|
+
}
|
|
411
|
+
function decodeUrlPlaceholders(code) {
|
|
412
|
+
return code.replace(/%7B([^%]+)%7D/g, (_, name) => `{${decodeURIComponent(name)}}`);
|
|
413
|
+
}
|
|
414
|
+
function buildHarRequest(input) {
|
|
415
|
+
const requestBody = getRequestBody(input.requestContent);
|
|
416
|
+
const url = encodeUrlPlaceholders(buildOperationUrl(input));
|
|
417
|
+
return {
|
|
418
|
+
method: input.method,
|
|
419
|
+
url,
|
|
420
|
+
httpVersion: "HTTP/1.1",
|
|
421
|
+
cookies: [],
|
|
422
|
+
headers: Object.entries(getRequestHeaders(input.requestContent, input.auth)).map(([name, value]) => ({
|
|
423
|
+
name,
|
|
424
|
+
value
|
|
425
|
+
})),
|
|
426
|
+
queryString: getQueryString(input.parameters, input.auth),
|
|
427
|
+
headersSize: -1,
|
|
428
|
+
bodySize: getBodySize(requestBody),
|
|
429
|
+
postData: requestBody ? {
|
|
430
|
+
mimeType: input.requestContent?.mediaType ?? "",
|
|
431
|
+
...requestBody.serialized ? { text: requestBody.serialized } : {},
|
|
432
|
+
...requestBody.params ? { params: requestBody.params } : {}
|
|
433
|
+
} : void 0
|
|
434
|
+
};
|
|
435
|
+
}
|
|
436
|
+
function buildSnippet(input, target) {
|
|
437
|
+
return decodeUrlPlaceholders(snippetGenerator.print(target.target, target.client, buildHarRequest(input)) || "");
|
|
438
|
+
}
|
|
439
|
+
var requestSnippetOptions = [
|
|
440
|
+
{
|
|
441
|
+
languageKey: "shell",
|
|
442
|
+
title: "Shell",
|
|
443
|
+
language: "bash",
|
|
444
|
+
target: "shell",
|
|
445
|
+
client: "curl",
|
|
446
|
+
clientTitle: "cURL"
|
|
447
|
+
},
|
|
448
|
+
{
|
|
449
|
+
languageKey: "shell",
|
|
450
|
+
title: "Shell",
|
|
451
|
+
language: "bash",
|
|
452
|
+
target: "shell",
|
|
453
|
+
client: "wget",
|
|
454
|
+
clientTitle: "Wget"
|
|
455
|
+
},
|
|
456
|
+
{
|
|
457
|
+
languageKey: "shell",
|
|
458
|
+
title: "Shell",
|
|
459
|
+
language: "bash",
|
|
460
|
+
target: "shell",
|
|
461
|
+
client: "httpie",
|
|
462
|
+
clientTitle: "HTTPie"
|
|
463
|
+
},
|
|
464
|
+
{
|
|
465
|
+
languageKey: "javascript",
|
|
466
|
+
title: "JavaScript",
|
|
467
|
+
language: "javascript",
|
|
468
|
+
target: "js",
|
|
469
|
+
client: "fetch",
|
|
470
|
+
clientTitle: "Fetch"
|
|
471
|
+
},
|
|
472
|
+
{
|
|
473
|
+
languageKey: "javascript",
|
|
474
|
+
title: "JavaScript",
|
|
475
|
+
language: "javascript",
|
|
476
|
+
target: "js",
|
|
477
|
+
client: "axios",
|
|
478
|
+
clientTitle: "Axios"
|
|
479
|
+
},
|
|
480
|
+
{
|
|
481
|
+
languageKey: "javascript",
|
|
482
|
+
title: "JavaScript",
|
|
483
|
+
language: "javascript",
|
|
484
|
+
target: "js",
|
|
485
|
+
client: "ofetch",
|
|
486
|
+
clientTitle: "ofetch"
|
|
487
|
+
},
|
|
488
|
+
{
|
|
489
|
+
languageKey: "javascript",
|
|
490
|
+
title: "JavaScript",
|
|
491
|
+
language: "javascript",
|
|
492
|
+
target: "js",
|
|
493
|
+
client: "xhr",
|
|
494
|
+
clientTitle: "XHR"
|
|
495
|
+
},
|
|
496
|
+
{
|
|
497
|
+
languageKey: "typescript",
|
|
498
|
+
title: "TypeScript",
|
|
499
|
+
language: "typescript",
|
|
500
|
+
target: "js",
|
|
501
|
+
client: "fetch",
|
|
502
|
+
clientTitle: "Fetch"
|
|
503
|
+
},
|
|
504
|
+
{
|
|
505
|
+
languageKey: "typescript",
|
|
506
|
+
title: "TypeScript",
|
|
507
|
+
language: "typescript",
|
|
508
|
+
target: "js",
|
|
509
|
+
client: "axios",
|
|
510
|
+
clientTitle: "Axios"
|
|
511
|
+
},
|
|
512
|
+
{
|
|
513
|
+
languageKey: "typescript",
|
|
514
|
+
title: "TypeScript",
|
|
515
|
+
language: "typescript",
|
|
516
|
+
target: "js",
|
|
517
|
+
client: "ofetch",
|
|
518
|
+
clientTitle: "ofetch"
|
|
519
|
+
},
|
|
520
|
+
{
|
|
521
|
+
languageKey: "python",
|
|
522
|
+
title: "Python",
|
|
523
|
+
language: "python",
|
|
524
|
+
target: "python",
|
|
525
|
+
client: "requests",
|
|
526
|
+
clientTitle: "Requests"
|
|
527
|
+
},
|
|
528
|
+
{
|
|
529
|
+
languageKey: "python",
|
|
530
|
+
title: "Python",
|
|
531
|
+
language: "python",
|
|
532
|
+
target: "python",
|
|
533
|
+
client: "python3",
|
|
534
|
+
clientTitle: "http.client"
|
|
535
|
+
},
|
|
536
|
+
{
|
|
537
|
+
languageKey: "python",
|
|
538
|
+
title: "Python",
|
|
539
|
+
language: "python",
|
|
540
|
+
target: "python",
|
|
541
|
+
client: "httpx_sync",
|
|
542
|
+
clientTitle: "HTTPX"
|
|
543
|
+
},
|
|
544
|
+
{
|
|
545
|
+
languageKey: "python",
|
|
546
|
+
title: "Python",
|
|
547
|
+
language: "python",
|
|
548
|
+
target: "python",
|
|
549
|
+
client: "aiohttp",
|
|
550
|
+
clientTitle: "aiohttp"
|
|
551
|
+
},
|
|
552
|
+
{
|
|
553
|
+
languageKey: "go",
|
|
554
|
+
title: "Go",
|
|
555
|
+
language: "go",
|
|
556
|
+
target: "go",
|
|
557
|
+
client: "native",
|
|
558
|
+
clientTitle: "NewRequest"
|
|
559
|
+
},
|
|
560
|
+
{
|
|
561
|
+
languageKey: "node",
|
|
562
|
+
title: "Node.js",
|
|
563
|
+
language: "javascript",
|
|
564
|
+
target: "node",
|
|
565
|
+
client: "fetch",
|
|
566
|
+
clientTitle: "Fetch"
|
|
567
|
+
},
|
|
568
|
+
{
|
|
569
|
+
languageKey: "node",
|
|
570
|
+
title: "Node.js",
|
|
571
|
+
language: "javascript",
|
|
572
|
+
target: "node",
|
|
573
|
+
client: "axios",
|
|
574
|
+
clientTitle: "Axios"
|
|
575
|
+
},
|
|
576
|
+
{
|
|
577
|
+
languageKey: "node",
|
|
578
|
+
title: "Node.js",
|
|
579
|
+
language: "javascript",
|
|
580
|
+
target: "node",
|
|
581
|
+
client: "ofetch",
|
|
582
|
+
clientTitle: "ofetch"
|
|
583
|
+
},
|
|
584
|
+
{
|
|
585
|
+
languageKey: "node",
|
|
586
|
+
title: "Node.js",
|
|
587
|
+
language: "javascript",
|
|
588
|
+
target: "node",
|
|
589
|
+
client: "undici",
|
|
590
|
+
clientTitle: "undici"
|
|
591
|
+
},
|
|
592
|
+
{
|
|
593
|
+
languageKey: "java",
|
|
594
|
+
title: "Java",
|
|
595
|
+
language: "java",
|
|
596
|
+
target: "java",
|
|
597
|
+
client: "nethttp",
|
|
598
|
+
clientTitle: "java.net.http"
|
|
599
|
+
},
|
|
600
|
+
{
|
|
601
|
+
languageKey: "java",
|
|
602
|
+
title: "Java",
|
|
603
|
+
language: "java",
|
|
604
|
+
target: "java",
|
|
605
|
+
client: "okhttp",
|
|
606
|
+
clientTitle: "OkHttp"
|
|
607
|
+
},
|
|
608
|
+
{
|
|
609
|
+
languageKey: "java",
|
|
610
|
+
title: "Java",
|
|
611
|
+
language: "java",
|
|
612
|
+
target: "java",
|
|
613
|
+
client: "unirest",
|
|
614
|
+
clientTitle: "Unirest"
|
|
615
|
+
},
|
|
616
|
+
{
|
|
617
|
+
languageKey: "java",
|
|
618
|
+
title: "Java",
|
|
619
|
+
language: "java",
|
|
620
|
+
target: "java",
|
|
621
|
+
client: "asynchttp",
|
|
622
|
+
clientTitle: "AsyncHttp"
|
|
623
|
+
},
|
|
624
|
+
{
|
|
625
|
+
languageKey: "csharp",
|
|
626
|
+
title: "C#",
|
|
627
|
+
language: "csharp",
|
|
628
|
+
target: "csharp",
|
|
629
|
+
client: "httpclient",
|
|
630
|
+
clientTitle: "HttpClient"
|
|
631
|
+
},
|
|
632
|
+
{
|
|
633
|
+
languageKey: "csharp",
|
|
634
|
+
title: "C#",
|
|
635
|
+
language: "csharp",
|
|
636
|
+
target: "csharp",
|
|
637
|
+
client: "restsharp",
|
|
638
|
+
clientTitle: "RestSharp"
|
|
639
|
+
},
|
|
640
|
+
{
|
|
641
|
+
languageKey: "php",
|
|
642
|
+
title: "PHP",
|
|
643
|
+
language: "php",
|
|
644
|
+
target: "php",
|
|
645
|
+
client: "guzzle",
|
|
646
|
+
clientTitle: "Guzzle"
|
|
647
|
+
},
|
|
648
|
+
{
|
|
649
|
+
languageKey: "php",
|
|
650
|
+
title: "PHP",
|
|
651
|
+
language: "php",
|
|
652
|
+
target: "php",
|
|
653
|
+
client: "curl",
|
|
654
|
+
clientTitle: "cURL"
|
|
655
|
+
},
|
|
656
|
+
{
|
|
657
|
+
languageKey: "php",
|
|
658
|
+
title: "PHP",
|
|
659
|
+
language: "php",
|
|
660
|
+
target: "php",
|
|
661
|
+
client: "laravel",
|
|
662
|
+
clientTitle: "Laravel HTTP Client"
|
|
663
|
+
},
|
|
664
|
+
{
|
|
665
|
+
languageKey: "ruby",
|
|
666
|
+
title: "Ruby",
|
|
667
|
+
language: "ruby",
|
|
668
|
+
target: "ruby",
|
|
669
|
+
client: "native",
|
|
670
|
+
clientTitle: "net::http"
|
|
671
|
+
},
|
|
672
|
+
{
|
|
673
|
+
languageKey: "rust",
|
|
674
|
+
title: "Rust",
|
|
675
|
+
language: "rust",
|
|
676
|
+
target: "rust",
|
|
677
|
+
client: "reqwest",
|
|
678
|
+
clientTitle: "reqwest"
|
|
679
|
+
},
|
|
680
|
+
{
|
|
681
|
+
languageKey: "swift",
|
|
682
|
+
title: "Swift",
|
|
683
|
+
language: "swift",
|
|
684
|
+
target: "swift",
|
|
685
|
+
client: "nsurlsession",
|
|
686
|
+
clientTitle: "NSURLSession"
|
|
687
|
+
},
|
|
688
|
+
{
|
|
689
|
+
languageKey: "kotlin",
|
|
690
|
+
title: "Kotlin",
|
|
691
|
+
language: "kotlin",
|
|
692
|
+
target: "kotlin",
|
|
693
|
+
client: "okhttp",
|
|
694
|
+
clientTitle: "OkHttp"
|
|
695
|
+
},
|
|
696
|
+
{
|
|
697
|
+
languageKey: "powershell",
|
|
698
|
+
title: "PowerShell",
|
|
699
|
+
language: "powershell",
|
|
700
|
+
target: "powershell",
|
|
701
|
+
client: "restmethod",
|
|
702
|
+
clientTitle: "Invoke-RestMethod"
|
|
703
|
+
},
|
|
704
|
+
{
|
|
705
|
+
languageKey: "powershell",
|
|
706
|
+
title: "PowerShell",
|
|
707
|
+
language: "powershell",
|
|
708
|
+
target: "powershell",
|
|
709
|
+
client: "webrequest",
|
|
710
|
+
clientTitle: "Invoke-WebRequest"
|
|
711
|
+
}
|
|
712
|
+
];
|
|
713
|
+
function buildRequestCodeExamples(input) {
|
|
714
|
+
return requestSnippetOptions.map((option) => ({
|
|
715
|
+
key: `${option.languageKey}:${option.client}`,
|
|
716
|
+
title: option.title,
|
|
717
|
+
language: option.language,
|
|
718
|
+
languageKey: option.languageKey,
|
|
719
|
+
clientKey: option.client,
|
|
720
|
+
clientTitle: option.clientTitle,
|
|
721
|
+
code: buildSnippet(input, option)
|
|
722
|
+
}));
|
|
723
|
+
}
|
|
724
|
+
//#endregion
|
|
725
|
+
//#region source/openapi/example-panels.tsx
|
|
404
726
|
function SelectControl(arg0) {
|
|
405
|
-
const { label, value, options, onChange } = arg0;
|
|
406
|
-
|
|
727
|
+
const { label, value, options, onChange, icon, compact = false } = arg0;
|
|
728
|
+
const normalizedOptions = options.map((option) => typeof option === "string" ? {
|
|
729
|
+
value: option,
|
|
730
|
+
label: option
|
|
731
|
+
} : option);
|
|
732
|
+
const selectedOption = normalizedOptions.find((option) => option.value === value) ?? normalizedOptions[0];
|
|
733
|
+
const wrapperClassName = compact ? "clarify-api-select relative min-w-0 text-xs" : "clarify-api-select relative shrink-0 text-xs";
|
|
734
|
+
const buttonSizeClassName = compact ? "w-full min-w-0 max-w-32" : "min-w-28 max-w-48";
|
|
735
|
+
if (normalizedOptions.length <= 1) return null;
|
|
407
736
|
return /* @__PURE__ */ jsx(Listbox, {
|
|
408
737
|
value,
|
|
409
738
|
onChange,
|
|
410
739
|
children: /* @__PURE__ */ jsxs("div", {
|
|
411
|
-
className:
|
|
740
|
+
className: wrapperClassName,
|
|
412
741
|
children: [/* @__PURE__ */ jsxs(ListboxButton, {
|
|
413
|
-
|
|
742
|
+
"aria-label": label,
|
|
743
|
+
className: `clarify-api-select-button flex ${buttonSizeClassName} items-center justify-between gap-2 rounded-lg bg-black/30 px-2 py-1 font-mono text-xs font-medium whitespace-nowrap text-zinc-100 outline-hidden transition hover:bg-black/50 focus:ring-2 focus:ring-emerald-400/25 data-open:bg-white/10 data-open:ring-2 data-open:ring-emerald-400/25`,
|
|
414
744
|
children: [/* @__PURE__ */ jsxs("span", {
|
|
415
|
-
className: "flex
|
|
416
|
-
children: [/* @__PURE__ */ jsx("span", {
|
|
417
|
-
className: "
|
|
418
|
-
children:
|
|
419
|
-
}), /* @__PURE__ */ jsx("span", {
|
|
745
|
+
className: "flex min-w-0 items-center gap-1.5 overflow-hidden",
|
|
746
|
+
children: [icon ? /* @__PURE__ */ jsx("span", {
|
|
747
|
+
className: "shrink-0 text-zinc-500",
|
|
748
|
+
children: icon
|
|
749
|
+
}) : null, /* @__PURE__ */ jsx("span", {
|
|
420
750
|
className: "truncate",
|
|
421
|
-
children: value
|
|
751
|
+
children: selectedOption?.label ?? value
|
|
422
752
|
})]
|
|
423
753
|
}), /* @__PURE__ */ jsx(ChevronsUpDownIcon, {
|
|
424
754
|
className: "h-3.5 w-3.5 shrink-0 text-zinc-500",
|
|
425
755
|
"aria-hidden": "true"
|
|
426
756
|
})]
|
|
427
757
|
}), /* @__PURE__ */ jsx(ListboxOptions, {
|
|
428
|
-
anchor: "bottom
|
|
429
|
-
className: "clarify-api-select-options z-30 mt-1 max-h-64 w-(--button-width)
|
|
430
|
-
children:
|
|
431
|
-
value: option,
|
|
432
|
-
className: "clarify-api-select-option group flex cursor-default items-center justify-between gap-3 rounded-lg px-2.5 py-2 font-mono text-xs text-zinc-300 select-none data-focus:bg-white/10 data-focus:text-white data-selected:text-emerald-300",
|
|
433
|
-
children: [/* @__PURE__ */ jsx("span", {
|
|
434
|
-
className: "truncate",
|
|
435
|
-
children: option
|
|
436
|
-
}), /* @__PURE__ */ jsx(CheckIcon, {
|
|
758
|
+
anchor: "bottom end",
|
|
759
|
+
className: "clarify-api-select-options z-30 mt-1 max-h-64 w-max min-w-(--button-width) max-w-[min(32rem,calc(100vw-2rem))] overflow-auto rounded-xl bg-zinc-900 p-1 text-xs shadow-lg shadow-black/20 ring-1 ring-white/10 [--anchor-gap:--spacing(1)] focus:outline-none",
|
|
760
|
+
children: normalizedOptions.map((option) => /* @__PURE__ */ jsxs(ListboxOption, {
|
|
761
|
+
value: option.value,
|
|
762
|
+
className: "clarify-api-select-option group flex cursor-default items-center justify-between gap-3 rounded-lg px-2.5 py-2 font-mono text-xs whitespace-nowrap text-zinc-300 select-none data-focus:bg-white/10 data-focus:text-white data-selected:text-emerald-300",
|
|
763
|
+
children: [/* @__PURE__ */ jsx("span", { children: option.label }), /* @__PURE__ */ jsx(CheckIcon, {
|
|
437
764
|
className: "h-3.5 w-3.5 shrink-0 opacity-0 group-data-selected:opacity-100",
|
|
438
765
|
"aria-hidden": "true"
|
|
439
766
|
})]
|
|
440
|
-
}, option))
|
|
767
|
+
}, option.value))
|
|
441
768
|
})]
|
|
442
769
|
})
|
|
443
770
|
});
|
|
444
771
|
}
|
|
445
|
-
function
|
|
446
|
-
|
|
447
|
-
|
|
448
|
-
|
|
449
|
-
|
|
450
|
-
|
|
451
|
-
|
|
452
|
-
|
|
453
|
-
|
|
454
|
-
|
|
455
|
-
|
|
456
|
-
|
|
457
|
-
return
|
|
458
|
-
|
|
459
|
-
|
|
460
|
-
|
|
461
|
-
|
|
462
|
-
|
|
463
|
-
|
|
464
|
-
|
|
465
|
-
|
|
466
|
-
|
|
467
|
-
|
|
468
|
-
|
|
469
|
-
|
|
470
|
-
|
|
471
|
-
|
|
472
|
-
|
|
473
|
-
|
|
474
|
-
|
|
475
|
-
|
|
476
|
-
|
|
477
|
-
|
|
478
|
-
|
|
479
|
-
|
|
480
|
-
|
|
481
|
-
|
|
482
|
-
|
|
483
|
-
|
|
484
|
-
|
|
485
|
-
|
|
486
|
-
|
|
487
|
-
|
|
488
|
-
|
|
489
|
-
|
|
490
|
-
|
|
491
|
-
|
|
492
|
-
|
|
493
|
-
|
|
494
|
-
|
|
495
|
-
|
|
496
|
-
|
|
497
|
-
|
|
498
|
-
|
|
499
|
-
|
|
500
|
-
|
|
501
|
-
|
|
502
|
-
|
|
503
|
-
|
|
504
|
-
|
|
772
|
+
function getExampleLabel(example, t) {
|
|
773
|
+
return example.generated && example.title === "schema" ? t("openapi.schemaExample") : example.title;
|
|
774
|
+
}
|
|
775
|
+
function getLanguageOptions(codeOptions) {
|
|
776
|
+
const languages = /* @__PURE__ */ new Map();
|
|
777
|
+
for (const option of codeOptions ?? []) languages.set(option.languageKey, option.title);
|
|
778
|
+
return Array.from(languages, ([value, label]) => ({
|
|
779
|
+
value,
|
|
780
|
+
label
|
|
781
|
+
}));
|
|
782
|
+
}
|
|
783
|
+
function getClientOptions(codeOptions, languageKey) {
|
|
784
|
+
return (codeOptions ?? []).filter((option) => option.languageKey === languageKey).map((option) => ({
|
|
785
|
+
value: option.clientKey,
|
|
786
|
+
label: option.clientTitle
|
|
787
|
+
}));
|
|
788
|
+
}
|
|
789
|
+
function getServers(spec, operation) {
|
|
790
|
+
const operationServers = operation.servers;
|
|
791
|
+
const servers = Array.isArray(operationServers) ? operationServers : spec.servers;
|
|
792
|
+
if (!Array.isArray(servers)) return [{ url: "https://api.example.com" }];
|
|
793
|
+
const validServers = servers.filter((server) => isRecord(server) && typeof server.url === "string");
|
|
794
|
+
return validServers.length > 0 ? validServers : [{ url: "https://api.example.com" }];
|
|
795
|
+
}
|
|
796
|
+
function getServerKey(server, index) {
|
|
797
|
+
return `${index}:${server.url ?? ""}`;
|
|
798
|
+
}
|
|
799
|
+
function getServerLabel(server, index) {
|
|
800
|
+
return server.description ? `${server.description} (${server.url})` : server.url ?? `Server ${index + 1}`;
|
|
801
|
+
}
|
|
802
|
+
function defaultServerVariables(server) {
|
|
803
|
+
return Object.fromEntries(Object.entries(server?.variables ?? {}).map(([name, variable]) => [name, variable.default ?? variable.enum?.[0] ?? ""]));
|
|
804
|
+
}
|
|
805
|
+
function getSecuritySchemes(spec) {
|
|
806
|
+
const schemes = spec.components;
|
|
807
|
+
if (!isRecord(schemes) || !isRecord(schemes.securitySchemes)) return {};
|
|
808
|
+
return Object.fromEntries(Object.entries(schemes.securitySchemes).filter((entry) => isRecord(entry[1])));
|
|
809
|
+
}
|
|
810
|
+
function getSecurityRequirements(spec, operation) {
|
|
811
|
+
const operationSecurity = operation.security;
|
|
812
|
+
if (Array.isArray(operationSecurity)) return operationSecurity.filter(isRecord);
|
|
813
|
+
const specSecurity = spec.security;
|
|
814
|
+
return Array.isArray(specSecurity) ? specSecurity.filter(isRecord) : [];
|
|
815
|
+
}
|
|
816
|
+
function getAuthOptions(spec, operation) {
|
|
817
|
+
const schemes = getSecuritySchemes(spec);
|
|
818
|
+
const requirements = getSecurityRequirements(spec, operation);
|
|
819
|
+
const names = new Set(requirements.flatMap((requirement) => Object.keys(requirement)));
|
|
820
|
+
return Array.from(names).map((name) => ({
|
|
821
|
+
name,
|
|
822
|
+
scheme: schemes[name]
|
|
823
|
+
})).filter((option) => Boolean(option.scheme));
|
|
824
|
+
}
|
|
825
|
+
function authPlaceholder(auth) {
|
|
826
|
+
if (!auth) return "";
|
|
827
|
+
if (auth.scheme.type === "apiKey") return "{api_key}";
|
|
828
|
+
if (auth.scheme.type === "http" && auth.scheme.scheme?.toLowerCase() === "basic") return "{base64_credentials}";
|
|
829
|
+
return "{token}";
|
|
830
|
+
}
|
|
831
|
+
function authLabel(name, scheme) {
|
|
832
|
+
return `${name}${scheme.type === "apiKey" && scheme.in && scheme.name ? ` · ${scheme.in}: ${scheme.name}` : ""}`;
|
|
505
833
|
}
|
|
506
834
|
function CopyCodeButton(arg0) {
|
|
507
835
|
const { code } = arg0;
|
|
836
|
+
const t = useBuiltInText();
|
|
508
837
|
const [copied, setCopied] = useState(false);
|
|
509
|
-
return /* @__PURE__ */
|
|
838
|
+
return /* @__PURE__ */ jsxs("button", {
|
|
510
839
|
type: "button",
|
|
511
840
|
onClick: () => {
|
|
512
841
|
window.navigator.clipboard.writeText(code).then(() => {
|
|
@@ -514,64 +843,144 @@ function CopyCodeButton(arg0) {
|
|
|
514
843
|
window.setTimeout(() => setCopied(false), 1e3);
|
|
515
844
|
});
|
|
516
845
|
},
|
|
517
|
-
className: "
|
|
518
|
-
children: copied ?
|
|
846
|
+
className: "flex items-center gap-1.5 rounded-full bg-black/ px-2.5 py-1.5 text-2xs font-medium text-zinc-400 transition hover:bg-black/50 hover:text-zinc-200 focus:bg-black/50 focus:text-zinc-200",
|
|
847
|
+
children: [copied ? /* @__PURE__ */ jsx(CheckIcon, {
|
|
848
|
+
className: "h-3.5 w-3.5 text-emerald-300",
|
|
849
|
+
"aria-hidden": "true"
|
|
850
|
+
}) : /* @__PURE__ */ jsx(ClipboardIcon, {
|
|
851
|
+
className: "h-3.5 w-3.5 text-zinc-500",
|
|
852
|
+
"aria-hidden": "true"
|
|
853
|
+
}), /* @__PURE__ */ jsx("span", { children: copied ? t("actions.copied") : t("actions.copy") })]
|
|
854
|
+
});
|
|
855
|
+
}
|
|
856
|
+
function ExampleMetaValue(arg0) {
|
|
857
|
+
const { label, value, options, onChange, className } = arg0;
|
|
858
|
+
if (options && options.length > 1 && onChange) return /* @__PURE__ */ jsx(SelectControl, {
|
|
859
|
+
label,
|
|
860
|
+
value,
|
|
861
|
+
options,
|
|
862
|
+
onChange
|
|
863
|
+
});
|
|
864
|
+
return /* @__PURE__ */ jsx("span", {
|
|
865
|
+
className,
|
|
866
|
+
children: value
|
|
867
|
+
});
|
|
868
|
+
}
|
|
869
|
+
function CodeToolbar(arg0) {
|
|
870
|
+
const { code, languageOptions, selectedLanguageKey, onSelectLanguage, clientOptions, selectedClientKey, onSelectClient } = arg0;
|
|
871
|
+
const t = useBuiltInText();
|
|
872
|
+
return /* @__PURE__ */ jsxs("div", {
|
|
873
|
+
className: "absolute top-3.5 right-4 left-4 z-10 flex items-center justify-between gap-3",
|
|
874
|
+
children: [/* @__PURE__ */ jsxs("div", {
|
|
875
|
+
className: "flex min-w-0 items-center gap-2",
|
|
876
|
+
children: [languageOptions && languageOptions.length > 1 && selectedLanguageKey && onSelectLanguage ? /* @__PURE__ */ jsx(SelectControl, {
|
|
877
|
+
label: t("openapi.language"),
|
|
878
|
+
value: selectedLanguageKey,
|
|
879
|
+
options: languageOptions,
|
|
880
|
+
onChange: onSelectLanguage,
|
|
881
|
+
icon: /* @__PURE__ */ jsx(CodeIcon, {
|
|
882
|
+
className: "h-3.5 w-3.5",
|
|
883
|
+
"aria-hidden": "true"
|
|
884
|
+
})
|
|
885
|
+
}) : null, clientOptions && clientOptions.length > 1 && selectedClientKey && onSelectClient ? /* @__PURE__ */ jsx(SelectControl, {
|
|
886
|
+
label: t("openapi.client"),
|
|
887
|
+
value: selectedClientKey,
|
|
888
|
+
options: clientOptions,
|
|
889
|
+
onChange: onSelectClient,
|
|
890
|
+
icon: /* @__PURE__ */ jsx(PackageIcon, {
|
|
891
|
+
className: "h-3.5 w-3.5",
|
|
892
|
+
"aria-hidden": "true"
|
|
893
|
+
})
|
|
894
|
+
}) : null]
|
|
895
|
+
}), /* @__PURE__ */ jsx(CopyCodeButton, { code })]
|
|
519
896
|
});
|
|
520
897
|
}
|
|
521
898
|
function ApiExampleCodeGroup(arg0) {
|
|
522
|
-
const { title, tag, label, code, language, examples, selectedExampleKey, onSelectExample } = arg0;
|
|
899
|
+
const { title, tag, tagOptions, onSelectTag, label, labelOptions, onSelectLabel, comfortableMeta = false, code, language, mediaTypes, selectedMediaType, onSelectMediaType, examples, selectedExampleKey, onSelectExample, languageOptions, selectedLanguageKey, onSelectLanguage, clientOptions, selectedClientKey, onSelectClient } = arg0;
|
|
900
|
+
const t = useBuiltInText();
|
|
901
|
+
const metaClassName = comfortableMeta ? "flex min-h-11 min-w-0 items-center gap-2 border-y border-t-transparent border-b-white/7.5 bg-zinc-900 px-4 py-2 dark:border-b-white/5 dark:bg-white/1" : "flex h-9 min-w-0 items-center gap-2 border-y border-t-transparent border-b-white/7.5 bg-zinc-900 px-4 dark:border-b-white/5 dark:bg-white/1";
|
|
523
902
|
return /* @__PURE__ */ jsx("div", {
|
|
524
903
|
className: "clarify-api-example my-6 overflow-hidden rounded-2xl bg-zinc-900 shadow-md dark:ring-1 dark:ring-white/10",
|
|
525
904
|
children: /* @__PURE__ */ jsxs("div", {
|
|
526
905
|
className: "not-prose",
|
|
527
906
|
children: [
|
|
528
907
|
/* @__PURE__ */ jsxs("div", {
|
|
529
|
-
className: "clarify-api-example-header flex min-h-[calc(--spacing(12)+1px)]
|
|
908
|
+
className: "clarify-api-example-header flex min-h-[calc(--spacing(12)+1px)] items-center gap-3 border-b border-zinc-700 bg-zinc-800 px-4 py-2 dark:border-zinc-800 dark:bg-transparent",
|
|
530
909
|
children: [/* @__PURE__ */ jsx("h3", {
|
|
531
|
-
className: "
|
|
910
|
+
className: "mr-auto min-w-16 truncate py-1 text-xs font-semibold text-white",
|
|
532
911
|
children: title
|
|
533
|
-
}),
|
|
534
|
-
|
|
535
|
-
|
|
536
|
-
|
|
537
|
-
|
|
912
|
+
}), /* @__PURE__ */ jsxs("div", {
|
|
913
|
+
className: "ml-auto flex min-w-0 items-center gap-2 whitespace-nowrap",
|
|
914
|
+
children: [mediaTypes && mediaTypes.length > 1 && selectedMediaType && onSelectMediaType ? /* @__PURE__ */ jsx(SelectControl, {
|
|
915
|
+
label: t("openapi.mediaType"),
|
|
916
|
+
value: selectedMediaType,
|
|
917
|
+
options: mediaTypes,
|
|
918
|
+
onChange: onSelectMediaType,
|
|
919
|
+
compact: true
|
|
920
|
+
}) : null, examples && examples.length > 1 && selectedExampleKey && onSelectExample ? /* @__PURE__ */ jsx(SelectControl, {
|
|
921
|
+
label: t("openapi.example"),
|
|
922
|
+
value: selectedExampleKey,
|
|
923
|
+
options: examples.map((example) => ({
|
|
924
|
+
value: example.key,
|
|
925
|
+
label: getExampleLabel(example, t)
|
|
926
|
+
})),
|
|
927
|
+
onChange: onSelectExample,
|
|
928
|
+
compact: true
|
|
929
|
+
}) : null]
|
|
930
|
+
})]
|
|
538
931
|
}),
|
|
539
932
|
tag || label ? /* @__PURE__ */ jsxs("div", {
|
|
540
|
-
className:
|
|
933
|
+
className: metaClassName,
|
|
541
934
|
children: [
|
|
542
|
-
tag ? /* @__PURE__ */ jsx(
|
|
543
|
-
|
|
544
|
-
|
|
935
|
+
tag ? /* @__PURE__ */ jsx(ExampleMetaValue, {
|
|
936
|
+
label: t("openapi.status"),
|
|
937
|
+
value: tag,
|
|
938
|
+
options: tagOptions,
|
|
939
|
+
onChange: onSelectTag,
|
|
940
|
+
className: "font-mono text-[0.625rem]/6 font-semibold text-emerald-400"
|
|
545
941
|
}) : null,
|
|
546
|
-
tag && label ? /* @__PURE__ */ jsx("span", { className: "h-0.5 w-0.5 rounded-full bg-zinc-500" }) : null,
|
|
547
|
-
label ? /* @__PURE__ */ jsx(
|
|
548
|
-
|
|
549
|
-
|
|
942
|
+
tag && label ? /* @__PURE__ */ jsx("span", { className: "h-0.5 w-0.5 shrink-0 rounded-full bg-zinc-500" }) : null,
|
|
943
|
+
label ? /* @__PURE__ */ jsx(ExampleMetaValue, {
|
|
944
|
+
label: t("openapi.mediaType"),
|
|
945
|
+
value: label,
|
|
946
|
+
options: labelOptions,
|
|
947
|
+
onChange: onSelectLabel,
|
|
948
|
+
className: "min-w-0 truncate font-mono text-xs text-zinc-400"
|
|
550
949
|
}) : null
|
|
551
950
|
]
|
|
552
951
|
}) : null,
|
|
553
952
|
/* @__PURE__ */ jsxs("div", {
|
|
554
953
|
className: "clarify-api-example-code group relative",
|
|
555
|
-
children: [/* @__PURE__ */ jsx(
|
|
556
|
-
|
|
954
|
+
children: [/* @__PURE__ */ jsx(CodeToolbar, {
|
|
955
|
+
code,
|
|
956
|
+
languageOptions,
|
|
957
|
+
selectedLanguageKey,
|
|
958
|
+
onSelectLanguage,
|
|
959
|
+
clientOptions,
|
|
960
|
+
selectedClientKey,
|
|
961
|
+
onSelectClient
|
|
962
|
+
}), /* @__PURE__ */ jsx("pre", {
|
|
963
|
+
className: `overflow-x-auto p-4 text-xs text-white ${languageOptions && languageOptions.length > 1 ? "pt-14" : ""}`,
|
|
557
964
|
children: /* @__PURE__ */ jsx("code", {
|
|
558
965
|
className: `language-${language}`,
|
|
559
966
|
children: code
|
|
560
967
|
})
|
|
561
|
-
})
|
|
968
|
+
})]
|
|
562
969
|
})
|
|
563
970
|
]
|
|
564
971
|
})
|
|
565
972
|
});
|
|
566
973
|
}
|
|
567
974
|
function RequestExamplesPanel(arg0) {
|
|
568
|
-
const { spec, path, method, parameters, requestContents } = arg0;
|
|
569
|
-
const
|
|
975
|
+
const { spec, path, method, parameters, requestContents, selectedMediaType, onSelectMediaType, selectedServer, serverVariables, auth } = arg0;
|
|
976
|
+
const t = useBuiltInText();
|
|
570
977
|
const selectedContent = requestContents.find((content) => content.mediaType === selectedMediaType) ?? requestContents[0];
|
|
571
978
|
const examples = getExampleEntries(selectedContent?.value);
|
|
572
979
|
const [selectedExampleKey, setSelectedExampleKey] = useState(examples[0]?.key ?? "");
|
|
980
|
+
const [selectedLanguageKey, setSelectedLanguageKey] = useState("shell");
|
|
981
|
+
const [selectedClientKey, setSelectedClientKey] = useState("curl");
|
|
573
982
|
const selectedExample = examples.find((example) => example.key === selectedExampleKey) ?? examples[0];
|
|
574
|
-
const
|
|
983
|
+
const codeOptions = buildRequestCodeExamples({
|
|
575
984
|
spec,
|
|
576
985
|
path,
|
|
577
986
|
method,
|
|
@@ -583,32 +992,45 @@ function RequestExamplesPanel(arg0) {
|
|
|
583
992
|
example: selectedExample?.value,
|
|
584
993
|
examples: void 0
|
|
585
994
|
}
|
|
586
|
-
} : void 0
|
|
995
|
+
} : void 0,
|
|
996
|
+
server: selectedServer,
|
|
997
|
+
serverVariables,
|
|
998
|
+
auth
|
|
587
999
|
});
|
|
588
|
-
|
|
589
|
-
|
|
590
|
-
|
|
591
|
-
|
|
592
|
-
|
|
593
|
-
|
|
594
|
-
onChange: (value) => {
|
|
595
|
-
setSelectedMediaType(value);
|
|
596
|
-
setSelectedExampleKey(getExampleEntries(requestContents.find((content) => content.mediaType === value)?.value)[0]?.key ?? "");
|
|
597
|
-
}
|
|
598
|
-
})
|
|
599
|
-
}), /* @__PURE__ */ jsx(ApiExampleCodeGroup, {
|
|
600
|
-
title: "Request",
|
|
1000
|
+
const selectedLanguage = codeOptions.find((option) => option.languageKey === selectedLanguageKey) ?? codeOptions[0];
|
|
1001
|
+
const selectedCode = codeOptions.find((option) => option.languageKey === selectedLanguage.languageKey && option.clientKey === selectedClientKey) ?? selectedLanguage;
|
|
1002
|
+
const languageOptions = getLanguageOptions(codeOptions);
|
|
1003
|
+
const clientOptions = getClientOptions(codeOptions, selectedCode.languageKey);
|
|
1004
|
+
return /* @__PURE__ */ jsx(ApiExampleCodeGroup, {
|
|
1005
|
+
title: t("openapi.request"),
|
|
601
1006
|
tag: method,
|
|
602
1007
|
label: path,
|
|
603
|
-
code:
|
|
604
|
-
language:
|
|
1008
|
+
code: selectedCode.code,
|
|
1009
|
+
language: selectedCode.language,
|
|
1010
|
+
mediaTypes: requestContents.map((content) => content.mediaType),
|
|
1011
|
+
selectedMediaType: selectedContent?.mediaType,
|
|
1012
|
+
onSelectMediaType: (value) => {
|
|
1013
|
+
onSelectMediaType(value);
|
|
1014
|
+
setSelectedExampleKey(getExampleEntries(requestContents.find((content) => content.mediaType === value)?.value)[0]?.key ?? "");
|
|
1015
|
+
},
|
|
605
1016
|
examples,
|
|
606
1017
|
selectedExampleKey: selectedExample?.key,
|
|
607
|
-
onSelectExample: setSelectedExampleKey
|
|
608
|
-
|
|
1018
|
+
onSelectExample: setSelectedExampleKey,
|
|
1019
|
+
languageOptions,
|
|
1020
|
+
selectedLanguageKey: selectedCode.languageKey,
|
|
1021
|
+
onSelectLanguage: (value) => {
|
|
1022
|
+
const nextCode = codeOptions.find((option) => option.languageKey === value);
|
|
1023
|
+
setSelectedLanguageKey(nextCode?.languageKey ?? value);
|
|
1024
|
+
setSelectedClientKey(nextCode?.clientKey ?? "");
|
|
1025
|
+
},
|
|
1026
|
+
clientOptions,
|
|
1027
|
+
selectedClientKey: selectedCode.clientKey,
|
|
1028
|
+
onSelectClient: setSelectedClientKey
|
|
1029
|
+
});
|
|
609
1030
|
}
|
|
610
1031
|
function ResponseExamplesPanel(arg0) {
|
|
611
1032
|
const { operation } = arg0;
|
|
1033
|
+
const t = useBuiltInText();
|
|
612
1034
|
const responses = getResponseEntries(operation).filter(({ response }) => getMediaTypeEntries(response.content).length > 0);
|
|
613
1035
|
const [selectedStatus, setSelectedStatus] = useState(responses.find(({ status }) => status.startsWith("2"))?.status ?? responses[0]?.status ?? "");
|
|
614
1036
|
const selectedResponse = responses.find(({ status }) => status === selectedStatus) ?? responses[0];
|
|
@@ -620,40 +1042,328 @@ function ResponseExamplesPanel(arg0) {
|
|
|
620
1042
|
const selectedExample = examples.find((example) => example.key === selectedExampleKey) ?? examples[0];
|
|
621
1043
|
const responseCode = stringifyExample(selectedExample?.value);
|
|
622
1044
|
if (!selectedResponse || !selectedContent || !responseCode) return null;
|
|
623
|
-
return /* @__PURE__ */
|
|
624
|
-
|
|
625
|
-
children: [/* @__PURE__ */ jsx(SelectControl, {
|
|
626
|
-
label: "Status",
|
|
627
|
-
value: selectedResponse.status,
|
|
628
|
-
options: responses.map(({ status }) => status),
|
|
629
|
-
onChange: (value) => {
|
|
630
|
-
const nextContents = getMediaTypeEntries(responses.find(({ status }) => status === value)?.response.content);
|
|
631
|
-
setSelectedStatus(value);
|
|
632
|
-
setSelectedMediaType(nextContents[0]?.mediaType ?? "");
|
|
633
|
-
setSelectedExampleKey(getExampleEntries(nextContents[0]?.value)[0]?.key ?? "");
|
|
634
|
-
}
|
|
635
|
-
}), /* @__PURE__ */ jsx(SelectControl, {
|
|
636
|
-
label: "Media type",
|
|
637
|
-
value: selectedContent.mediaType,
|
|
638
|
-
options: responseContents.map((content) => content.mediaType),
|
|
639
|
-
onChange: (value) => {
|
|
640
|
-
setSelectedMediaType(value);
|
|
641
|
-
setSelectedExampleKey(getExampleEntries(responseContents.find((content) => content.mediaType === value)?.value)[0]?.key ?? "");
|
|
642
|
-
}
|
|
643
|
-
})]
|
|
644
|
-
}), /* @__PURE__ */ jsx(ApiExampleCodeGroup, {
|
|
645
|
-
title: "Response",
|
|
1045
|
+
return /* @__PURE__ */ jsx(ApiExampleCodeGroup, {
|
|
1046
|
+
title: t("openapi.response"),
|
|
646
1047
|
tag: selectedResponse.status,
|
|
1048
|
+
tagOptions: responses.map(({ status }) => status),
|
|
1049
|
+
onSelectTag: (value) => {
|
|
1050
|
+
const nextContents = getMediaTypeEntries(responses.find(({ status }) => status === value)?.response.content);
|
|
1051
|
+
setSelectedStatus(value);
|
|
1052
|
+
setSelectedMediaType(nextContents[0]?.mediaType ?? "");
|
|
1053
|
+
setSelectedExampleKey(getExampleEntries(nextContents[0]?.value)[0]?.key ?? "");
|
|
1054
|
+
},
|
|
647
1055
|
label: selectedContent.mediaType,
|
|
1056
|
+
labelOptions: responseContents.map((content) => content.mediaType),
|
|
1057
|
+
onSelectLabel: (value) => {
|
|
1058
|
+
setSelectedMediaType(value);
|
|
1059
|
+
setSelectedExampleKey(getExampleEntries(responseContents.find((content) => content.mediaType === value)?.value)[0]?.key ?? "");
|
|
1060
|
+
},
|
|
1061
|
+
comfortableMeta: true,
|
|
648
1062
|
code: responseCode,
|
|
649
1063
|
language: codeLanguageForMediaType(selectedContent.mediaType),
|
|
650
1064
|
examples,
|
|
651
1065
|
selectedExampleKey: selectedExample?.key,
|
|
652
1066
|
onSelectExample: setSelectedExampleKey
|
|
1067
|
+
});
|
|
1068
|
+
}
|
|
1069
|
+
//#endregion
|
|
1070
|
+
//#region source/openapi/schema-properties.tsx
|
|
1071
|
+
function getSchemaDescription(schema) {
|
|
1072
|
+
const details = [
|
|
1073
|
+
Array.isArray(schema.enum) ? `enum: ${schema.enum.map(String).join(", ")}` : void 0,
|
|
1074
|
+
typeof schema.const !== "undefined" ? `const: ${String(schema.const)}` : void 0,
|
|
1075
|
+
typeof schema.default !== "undefined" ? `default: ${String(schema.default)}` : void 0,
|
|
1076
|
+
typeof schema.pattern === "string" ? `pattern: ${schema.pattern}` : void 0,
|
|
1077
|
+
typeof schema.minimum === "number" ? `minimum: ${String(schema.minimum)}` : void 0,
|
|
1078
|
+
typeof schema.maximum === "number" ? `maximum: ${String(schema.maximum)}` : void 0,
|
|
1079
|
+
typeof schema.additionalProperties === "boolean" ? `additionalProperties: ${String(schema.additionalProperties)}` : void 0
|
|
1080
|
+
].filter(Boolean);
|
|
1081
|
+
return [typeof schema.description === "string" ? schema.description : void 0, details.length > 0 ? details.join("; ") : void 0].filter(Boolean).join(" ");
|
|
1082
|
+
}
|
|
1083
|
+
function getComposedBranches(schema) {
|
|
1084
|
+
const entries = [];
|
|
1085
|
+
for (const key of [
|
|
1086
|
+
"allOf",
|
|
1087
|
+
"oneOf",
|
|
1088
|
+
"anyOf"
|
|
1089
|
+
]) {
|
|
1090
|
+
const items = schema[key];
|
|
1091
|
+
if (!Array.isArray(items)) continue;
|
|
1092
|
+
for (const [index, item] of items.entries()) entries.push({
|
|
1093
|
+
label: `${key}[${index}]`,
|
|
1094
|
+
schema: item
|
|
1095
|
+
});
|
|
1096
|
+
}
|
|
1097
|
+
return entries;
|
|
1098
|
+
}
|
|
1099
|
+
function getSchemaChildren(arg0) {
|
|
1100
|
+
const { spec, schema, path, required = [], depth = 0, seen = /* @__PURE__ */ new Set() } = arg0;
|
|
1101
|
+
if (depth > 12) return [];
|
|
1102
|
+
if (isReference(schema)) {
|
|
1103
|
+
if (seen.has(schema.$ref)) return [];
|
|
1104
|
+
return getSchemaChildren({
|
|
1105
|
+
spec,
|
|
1106
|
+
schema: resolveSchema(spec, schema),
|
|
1107
|
+
path,
|
|
1108
|
+
required,
|
|
1109
|
+
depth,
|
|
1110
|
+
seen: new Set([...seen, schema.$ref])
|
|
1111
|
+
});
|
|
1112
|
+
}
|
|
1113
|
+
if (!isRecord(schema)) return [];
|
|
1114
|
+
const arrayChildren = schema.type === "array" ? getSchemaChildren({
|
|
1115
|
+
spec,
|
|
1116
|
+
schema: schema.items,
|
|
1117
|
+
path: `${path}[]`,
|
|
1118
|
+
depth: depth + 1,
|
|
1119
|
+
seen
|
|
1120
|
+
}) : [];
|
|
1121
|
+
const objectRequired = Array.isArray(schema.required) ? schema.required.map(String) : required;
|
|
1122
|
+
const properties = isRecord(schema.properties) ? schema.properties : {};
|
|
1123
|
+
const propertyChildren = Object.entries(properties).map(([name, propertySchema]) => {
|
|
1124
|
+
const resolvedProperty = resolveSchema(spec, propertySchema);
|
|
1125
|
+
const property = isRecord(resolvedProperty) ? resolvedProperty : isRecord(propertySchema) ? propertySchema : {};
|
|
1126
|
+
const isArray = isRecord(property) && property.type === "array";
|
|
1127
|
+
const childPath = path ? `${path}.${name}` : name;
|
|
1128
|
+
const children = getSchemaChildren({
|
|
1129
|
+
spec,
|
|
1130
|
+
schema: isArray ? property.items : propertySchema,
|
|
1131
|
+
path: isArray ? `${childPath}[]` : childPath,
|
|
1132
|
+
depth: depth + 1,
|
|
1133
|
+
seen
|
|
1134
|
+
});
|
|
1135
|
+
return {
|
|
1136
|
+
key: childPath,
|
|
1137
|
+
name,
|
|
1138
|
+
type: schemaToType(propertySchema),
|
|
1139
|
+
description: getSchemaDescription(property),
|
|
1140
|
+
required: objectRequired.includes(name),
|
|
1141
|
+
children
|
|
1142
|
+
};
|
|
1143
|
+
});
|
|
1144
|
+
const additionalPropertyChildren = isRecord(schema.additionalProperties) ? [{
|
|
1145
|
+
key: `${path || "root"}.*`,
|
|
1146
|
+
name: "*",
|
|
1147
|
+
type: schemaToType(schema.additionalProperties),
|
|
1148
|
+
description: getSchemaDescription(schema.additionalProperties),
|
|
1149
|
+
required: false,
|
|
1150
|
+
children: getSchemaChildren({
|
|
1151
|
+
spec,
|
|
1152
|
+
schema: schema.additionalProperties,
|
|
1153
|
+
path: `${path || "root"}.*`,
|
|
1154
|
+
depth: depth + 1,
|
|
1155
|
+
seen
|
|
1156
|
+
})
|
|
1157
|
+
}] : [];
|
|
1158
|
+
const composedChildren = getComposedBranches(schema).map(({ label, schema: branchSchema }) => ({
|
|
1159
|
+
key: `${path || "root"}.${label}`,
|
|
1160
|
+
name: label,
|
|
1161
|
+
type: schemaToType(branchSchema),
|
|
1162
|
+
description: isRecord(resolveSchema(spec, branchSchema)) ? getSchemaDescription(resolveSchema(spec, branchSchema)) : void 0,
|
|
1163
|
+
required: false,
|
|
1164
|
+
children: getSchemaChildren({
|
|
1165
|
+
spec,
|
|
1166
|
+
schema: branchSchema,
|
|
1167
|
+
path: `${path || "root"}.${label}`,
|
|
1168
|
+
required: objectRequired,
|
|
1169
|
+
depth: depth + 1,
|
|
1170
|
+
seen
|
|
1171
|
+
})
|
|
1172
|
+
}));
|
|
1173
|
+
return [
|
|
1174
|
+
...arrayChildren,
|
|
1175
|
+
...propertyChildren,
|
|
1176
|
+
...additionalPropertyChildren,
|
|
1177
|
+
...composedChildren
|
|
1178
|
+
];
|
|
1179
|
+
}
|
|
1180
|
+
function getRootSchemaNode(spec, schema) {
|
|
1181
|
+
if (isReference(schema)) {
|
|
1182
|
+
const resolvedSchema = resolveSchema(spec, schema);
|
|
1183
|
+
const resolved = isRecord(resolvedSchema) ? resolvedSchema : {};
|
|
1184
|
+
return {
|
|
1185
|
+
key: schema.$ref,
|
|
1186
|
+
name: resolveReferenceName(schema.$ref),
|
|
1187
|
+
type: schemaToType(schema),
|
|
1188
|
+
description: getSchemaDescription(resolved),
|
|
1189
|
+
required: false,
|
|
1190
|
+
children: getSchemaChildren({
|
|
1191
|
+
spec,
|
|
1192
|
+
schema: resolvedSchema,
|
|
1193
|
+
path: resolveReferenceName(schema.$ref),
|
|
1194
|
+
seen: new Set([schema.$ref])
|
|
1195
|
+
})
|
|
1196
|
+
};
|
|
1197
|
+
}
|
|
1198
|
+
if (!isRecord(schema)) return void 0;
|
|
1199
|
+
return {
|
|
1200
|
+
key: "root",
|
|
1201
|
+
name: "body",
|
|
1202
|
+
type: schemaToType(schema),
|
|
1203
|
+
description: getSchemaDescription(schema),
|
|
1204
|
+
required: false,
|
|
1205
|
+
children: getSchemaChildren({
|
|
1206
|
+
spec,
|
|
1207
|
+
schema,
|
|
1208
|
+
path: ""
|
|
1209
|
+
})
|
|
1210
|
+
};
|
|
1211
|
+
}
|
|
1212
|
+
function SchemaNode(arg0) {
|
|
1213
|
+
const { node, depth = 0 } = arg0;
|
|
1214
|
+
const t = useBuiltInText();
|
|
1215
|
+
const [expanded, setExpanded] = useState(depth < 1);
|
|
1216
|
+
const hasChildren = node.children.length > 0;
|
|
1217
|
+
const type = [node.type, node.required ? t("openapi.requiredBadge") : void 0].filter(Boolean).join(", ") || void 0;
|
|
1218
|
+
const description = node.description || (node.required ? t("openapi.required") : t("openapi.optional"));
|
|
1219
|
+
const rowClassName = clsx("flex min-w-0 items-start rounded py-0.5 text-left", depth > 0 ? "-mx-2 w-[calc(100%+1rem)] px-2" : "w-full px-1");
|
|
1220
|
+
const content = /* @__PURE__ */ jsxs(Fragment$1, { children: [/* @__PURE__ */ jsxs("div", {
|
|
1221
|
+
className: "min-w-0 flex-1",
|
|
1222
|
+
children: [/* @__PURE__ */ jsxs("div", {
|
|
1223
|
+
className: "flex min-w-0 flex-wrap items-center gap-x-2 gap-y-0.5",
|
|
1224
|
+
children: [/* @__PURE__ */ jsx("span", {
|
|
1225
|
+
className: "text-sm/5 font-semibold text-zinc-950 dark:text-white",
|
|
1226
|
+
children: node.name
|
|
1227
|
+
}), type ? /* @__PURE__ */ jsx("span", {
|
|
1228
|
+
className: "font-mono text-xs text-(--clarify-theme-tokens-colors-muted) dark:text-zinc-500",
|
|
1229
|
+
children: type
|
|
1230
|
+
}) : null]
|
|
1231
|
+
}), description ? /* @__PURE__ */ jsx("div", {
|
|
1232
|
+
className: "mt-0.5 text-sm/5 text-zinc-600 dark:text-zinc-400",
|
|
1233
|
+
children: description
|
|
1234
|
+
}) : null]
|
|
1235
|
+
}), hasChildren ? /* @__PURE__ */ jsx("span", {
|
|
1236
|
+
className: "ml-2 flex h-5 w-5 flex-none items-center justify-center text-zinc-500 dark:text-zinc-400",
|
|
1237
|
+
"aria-hidden": "true",
|
|
1238
|
+
children: expanded ? /* @__PURE__ */ jsx(ChevronDown, { className: "h-4 w-4" }) : /* @__PURE__ */ jsx(ChevronRight, { className: "h-4 w-4" })
|
|
1239
|
+
}) : null] });
|
|
1240
|
+
return /* @__PURE__ */ jsxs("li", {
|
|
1241
|
+
className: "clarify-schema-node m-0 px-0 py-2 first:pt-0 last:pb-0",
|
|
1242
|
+
children: [hasChildren ? /* @__PURE__ */ jsx("button", {
|
|
1243
|
+
type: "button",
|
|
1244
|
+
"aria-label": expanded ? t("openapi.collapse") : t("openapi.expand"),
|
|
1245
|
+
"aria-expanded": expanded,
|
|
1246
|
+
onClick: () => setExpanded((value) => !value),
|
|
1247
|
+
className: clsx(rowClassName, "cursor-pointer transition"),
|
|
1248
|
+
children: content
|
|
1249
|
+
}) : /* @__PURE__ */ jsx("div", {
|
|
1250
|
+
className: rowClassName,
|
|
1251
|
+
children: content
|
|
1252
|
+
}), hasChildren && expanded ? /* @__PURE__ */ jsx(SchemaTree, {
|
|
1253
|
+
nodes: node.children,
|
|
1254
|
+
depth: depth + 1
|
|
1255
|
+
}) : null]
|
|
1256
|
+
});
|
|
1257
|
+
}
|
|
1258
|
+
function SchemaTree(arg0) {
|
|
1259
|
+
const { nodes, depth = 0 } = arg0;
|
|
1260
|
+
if (nodes.length === 0) return null;
|
|
1261
|
+
return /* @__PURE__ */ jsx("ul", {
|
|
1262
|
+
role: "list",
|
|
1263
|
+
className: clsx("m-0 list-none divide-y divide-zinc-900/5 p-0 dark:divide-white/5", depth > 0 && "mt-2 rounded-lg bg-zinc-950/[0.025] px-2 py-1 dark:bg-white/[0.04]"),
|
|
1264
|
+
children: nodes.map((node) => /* @__PURE__ */ jsx(SchemaNode, {
|
|
1265
|
+
node,
|
|
1266
|
+
depth
|
|
1267
|
+
}, node.key))
|
|
1268
|
+
});
|
|
1269
|
+
}
|
|
1270
|
+
function SchemaProperties(arg0) {
|
|
1271
|
+
const { title, schema, spec } = arg0;
|
|
1272
|
+
const root = getRootSchemaNode(spec, schema);
|
|
1273
|
+
if (!root || root.children.length === 0) return null;
|
|
1274
|
+
return /* @__PURE__ */ jsxs("div", { children: [/* @__PURE__ */ jsx("h3", { children: title }), /* @__PURE__ */ jsx("div", {
|
|
1275
|
+
className: "clarify-schema-properties my-6",
|
|
1276
|
+
children: /* @__PURE__ */ jsx(SchemaTree, { nodes: root.children })
|
|
653
1277
|
})] });
|
|
654
1278
|
}
|
|
1279
|
+
function ParameterList(arg0) {
|
|
1280
|
+
const { title, parameters } = arg0;
|
|
1281
|
+
const t = useBuiltInText();
|
|
1282
|
+
if (parameters.length === 0) return null;
|
|
1283
|
+
return /* @__PURE__ */ jsxs("div", { children: [/* @__PURE__ */ jsx("h3", { children: title }), /* @__PURE__ */ jsx(Properties, { children: parameters.map((parameter) => /* @__PURE__ */ jsx(Property, {
|
|
1284
|
+
name: parameter.name ?? t("openapi.parameter"),
|
|
1285
|
+
type: [schemaToType(parameter.schema), parameter.required ? t("openapi.requiredBadge") : void 0].filter(Boolean).join(", ") || void 0,
|
|
1286
|
+
children: parameter.description ?? t("openapi.operationParameter")
|
|
1287
|
+
}, `${parameter.in}-${parameter.name}`)) })] });
|
|
1288
|
+
}
|
|
1289
|
+
function ResponseList(arg0) {
|
|
1290
|
+
const { operation } = arg0;
|
|
1291
|
+
const t = useBuiltInText();
|
|
1292
|
+
const responses = getResponseEntries(operation);
|
|
1293
|
+
if (responses.length === 0) return null;
|
|
1294
|
+
return /* @__PURE__ */ jsxs("div", { children: [/* @__PURE__ */ jsx("h3", { children: t("openapi.responses") }), /* @__PURE__ */ jsx(Properties, { children: responses.map(({ status, response }) => {
|
|
1295
|
+
return /* @__PURE__ */ jsx(Property, {
|
|
1296
|
+
name: status,
|
|
1297
|
+
type: schemaToType(getJsonLikeContent(response.content)?.value.schema),
|
|
1298
|
+
children: response.description ?? `${t("openapi.response")}.`
|
|
1299
|
+
}, status);
|
|
1300
|
+
}) })] });
|
|
1301
|
+
}
|
|
1302
|
+
//#endregion
|
|
1303
|
+
//#region source/openapi/spec-path.ts
|
|
1304
|
+
var VIRTUAL_PREFIX = "virtual:clarify-page/";
|
|
1305
|
+
function resolveRelativePath(fromDir, to) {
|
|
1306
|
+
const parts = (fromDir + "/" + to).split("/").filter(Boolean);
|
|
1307
|
+
const stack = [];
|
|
1308
|
+
for (const part of parts) if (part === "..") stack.pop();
|
|
1309
|
+
else if (part !== ".") stack.push(part);
|
|
1310
|
+
return stack.join("/");
|
|
1311
|
+
}
|
|
1312
|
+
function normalizeSpecPath(specPath, currentRoutePath, routePrefix = "") {
|
|
1313
|
+
if (specPath.startsWith(VIRTUAL_PREFIX)) return specPath;
|
|
1314
|
+
const normalizedRoutePrefix = routePrefix.replace(/^\/+|\/+$/g, "");
|
|
1315
|
+
const normalizedSpecPath = specPath.startsWith("/") && normalizedRoutePrefix && specPath.slice(1).startsWith(`${normalizedRoutePrefix}/`) ? "/" + specPath.slice(normalizedRoutePrefix.length + 2) : specPath;
|
|
1316
|
+
if (normalizedSpecPath.startsWith("/")) return VIRTUAL_PREFIX + normalizedSpecPath.replace(/^\//, "");
|
|
1317
|
+
const fromDir = currentRoutePath === "/" ? "" : currentRoutePath?.replace(/^\//, "").replace(/\/[^/]*$/, "") ?? "";
|
|
1318
|
+
return VIRTUAL_PREFIX + resolveRelativePath(normalizedRoutePrefix && fromDir.startsWith(`${normalizedRoutePrefix}/`) ? fromDir.slice(normalizedRoutePrefix.length + 1) : fromDir, normalizedSpecPath);
|
|
1319
|
+
}
|
|
1320
|
+
function useOpenApiSpec(spec, specPath) {
|
|
1321
|
+
const specs = useOpenApis();
|
|
1322
|
+
const location = useLocation();
|
|
1323
|
+
const config = useClarifyConfig();
|
|
1324
|
+
if (spec) return spec;
|
|
1325
|
+
if (!specPath) return null;
|
|
1326
|
+
return specs[normalizeSpecPath(specPath, location.pathname, config.routePrefix)] ?? null;
|
|
1327
|
+
}
|
|
1328
|
+
//#endregion
|
|
1329
|
+
//#region source/openapi/utils.ts
|
|
1330
|
+
var OPENAPI_HTTP_METHODS = [
|
|
1331
|
+
"get",
|
|
1332
|
+
"put",
|
|
1333
|
+
"post",
|
|
1334
|
+
"delete",
|
|
1335
|
+
"options",
|
|
1336
|
+
"head",
|
|
1337
|
+
"patch",
|
|
1338
|
+
"trace"
|
|
1339
|
+
];
|
|
1340
|
+
function isOpenAPIHttpMethod(method) {
|
|
1341
|
+
return OPENAPI_HTTP_METHODS.includes(method.toLowerCase());
|
|
1342
|
+
}
|
|
1343
|
+
function getOpenApiOperation(spec, path, method) {
|
|
1344
|
+
if (!isOpenAPIHttpMethod(method)) return void 0;
|
|
1345
|
+
return spec.paths?.[path]?.[method.toLowerCase()];
|
|
1346
|
+
}
|
|
1347
|
+
function listOpenApiOperations(spec) {
|
|
1348
|
+
const paths = spec.paths ?? {};
|
|
1349
|
+
const operations = [];
|
|
1350
|
+
for (const [path, pathItem] of Object.entries(paths)) {
|
|
1351
|
+
if (!pathItem) continue;
|
|
1352
|
+
for (const method of OPENAPI_HTTP_METHODS) {
|
|
1353
|
+
const operation = pathItem[method];
|
|
1354
|
+
if (operation) operations.push({
|
|
1355
|
+
path,
|
|
1356
|
+
method,
|
|
1357
|
+
operation
|
|
1358
|
+
});
|
|
1359
|
+
}
|
|
1360
|
+
}
|
|
1361
|
+
return operations;
|
|
1362
|
+
}
|
|
1363
|
+
//#endregion
|
|
1364
|
+
//#region source/openapi/openapi-page.tsx
|
|
655
1365
|
function EndpointExamples(arg0) {
|
|
656
|
-
const { spec, path, method, operation, parameters, requestContents } = arg0;
|
|
1366
|
+
const { spec, path, method, operation, parameters, requestContents, selectedRequestMediaType, onSelectRequestMediaType, selectedServer, serverVariables, auth } = arg0;
|
|
657
1367
|
return /* @__PURE__ */ jsxs("div", {
|
|
658
1368
|
className: "space-y-6",
|
|
659
1369
|
children: [/* @__PURE__ */ jsx(RequestExamplesPanel, {
|
|
@@ -661,93 +1371,416 @@ function EndpointExamples(arg0) {
|
|
|
661
1371
|
path,
|
|
662
1372
|
method,
|
|
663
1373
|
parameters,
|
|
664
|
-
requestContents
|
|
1374
|
+
requestContents,
|
|
1375
|
+
selectedMediaType: selectedRequestMediaType,
|
|
1376
|
+
onSelectMediaType: onSelectRequestMediaType,
|
|
1377
|
+
selectedServer,
|
|
1378
|
+
serverVariables,
|
|
1379
|
+
auth
|
|
665
1380
|
}), /* @__PURE__ */ jsx(ResponseExamplesPanel, { operation })]
|
|
666
1381
|
});
|
|
667
1382
|
}
|
|
668
1383
|
function OpenApiHeader(arg0) {
|
|
669
1384
|
const { spec } = arg0;
|
|
1385
|
+
const t = useBuiltInText();
|
|
670
1386
|
return /* @__PURE__ */ jsxs("header", {
|
|
671
1387
|
className: "mb-16",
|
|
672
1388
|
children: [
|
|
673
1389
|
/* @__PURE__ */ jsx("p", {
|
|
674
1390
|
className: "mb-3 font-mono text-xs/6 font-medium tracking-widest text-emerald-500 uppercase dark:text-emerald-400",
|
|
675
|
-
children: "
|
|
1391
|
+
children: t("openapi.openApiReference")
|
|
676
1392
|
}),
|
|
677
|
-
/* @__PURE__ */ jsx("h1", { children: spec.info?.title ?? "
|
|
1393
|
+
/* @__PURE__ */ jsx("h1", { children: spec.info?.title ?? t("openapi.apiDocumentation") }),
|
|
678
1394
|
spec.info?.description ? /* @__PURE__ */ jsx("p", {
|
|
679
1395
|
className: "lead",
|
|
680
1396
|
children: spec.info.description
|
|
681
1397
|
}) : null,
|
|
682
|
-
spec.info?.version ? /* @__PURE__ */
|
|
1398
|
+
spec.info?.version ? /* @__PURE__ */ jsx("p", {
|
|
683
1399
|
className: "text-sm text-zinc-500 dark:text-zinc-400",
|
|
684
|
-
children:
|
|
1400
|
+
children: t("openapi.version", { version: spec.info.version })
|
|
1401
|
+
}) : null
|
|
1402
|
+
]
|
|
1403
|
+
});
|
|
1404
|
+
}
|
|
1405
|
+
var endpointMethodStyles = {
|
|
1406
|
+
GET: "bg-emerald-400/15 text-emerald-600 dark:bg-emerald-400/20 dark:text-emerald-300",
|
|
1407
|
+
POST: "bg-sky-400/15 text-sky-600 dark:bg-sky-400/20 dark:text-sky-300",
|
|
1408
|
+
PUT: "bg-amber-400/15 text-amber-600 dark:bg-amber-400/20 dark:text-amber-300",
|
|
1409
|
+
PATCH: "bg-amber-400/15 text-amber-600 dark:bg-amber-400/20 dark:text-amber-300",
|
|
1410
|
+
DELETE: "bg-rose-400/15 text-rose-600 dark:bg-rose-400/20 dark:text-rose-300"
|
|
1411
|
+
};
|
|
1412
|
+
function EndpointMethodBadge(arg0) {
|
|
1413
|
+
const { method } = arg0;
|
|
1414
|
+
return /* @__PURE__ */ jsx("span", {
|
|
1415
|
+
className: clsx("rounded-(--clarify-theme-tokens-radius-md) px-2.5 py-0.5 font-mono text-xs/6 font-black tracking-wide", endpointMethodStyles[method] ?? "bg-zinc-400/15 text-zinc-700 dark:bg-zinc-400/20 dark:text-zinc-200"),
|
|
1416
|
+
children: method
|
|
1417
|
+
});
|
|
1418
|
+
}
|
|
1419
|
+
function InlineListbox(arg0) {
|
|
1420
|
+
const { label, value, options, onChange, compact = false } = arg0;
|
|
1421
|
+
const selected = options.find((option) => option.value === value) ?? options[0];
|
|
1422
|
+
return /* @__PURE__ */ jsx(Listbox, {
|
|
1423
|
+
value: selected?.value ?? value,
|
|
1424
|
+
onChange,
|
|
1425
|
+
children: /* @__PURE__ */ jsxs("div", {
|
|
1426
|
+
className: "pointer-events-auto relative inline-flex min-w-0",
|
|
1427
|
+
children: [/* @__PURE__ */ jsxs(ListboxButton, {
|
|
1428
|
+
"aria-label": label,
|
|
1429
|
+
className: clsx("inline-flex min-w-0 items-center gap-1 rounded-md border border-zinc-200 bg-white font-mono font-semibold text-zinc-900 shadow-xs outline-hidden transition hover:border-zinc-300 hover:bg-zinc-50 data-open:border-zinc-300 data-open:bg-zinc-50 dark:border-white/10 dark:bg-zinc-950 dark:text-zinc-100 dark:hover:border-white/15 dark:hover:bg-zinc-900 dark:data-open:border-white/15 dark:data-open:bg-zinc-900", compact ? "max-w-32 px-1.5 py-0.5 text-xs" : "w-full px-2.5 py-1.5 text-xs"),
|
|
1430
|
+
children: [/* @__PURE__ */ jsx("span", {
|
|
1431
|
+
className: "truncate",
|
|
1432
|
+
children: selected?.label ?? value
|
|
1433
|
+
}), /* @__PURE__ */ jsx(ChevronDownIcon, {
|
|
1434
|
+
className: "h-3.5 w-3.5 shrink-0 text-zinc-500 dark:text-zinc-400",
|
|
1435
|
+
"aria-hidden": "true"
|
|
1436
|
+
})]
|
|
1437
|
+
}), /* @__PURE__ */ jsx(ListboxOptions, {
|
|
1438
|
+
anchor: "bottom start",
|
|
1439
|
+
className: "z-30 mt-1 max-h-64 w-max min-w-(--button-width) max-w-[min(32rem,calc(100vw-2rem))] overflow-auto rounded-xl bg-white p-1 text-xs shadow-lg shadow-black/10 ring-1 ring-zinc-950/10 [--anchor-gap:--spacing(1)] focus:outline-none dark:bg-zinc-950 dark:ring-white/10",
|
|
1440
|
+
children: options.map((option) => /* @__PURE__ */ jsxs(ListboxOption, {
|
|
1441
|
+
value: option.value,
|
|
1442
|
+
className: "group flex cursor-default items-center justify-between gap-3 rounded-lg px-2.5 py-2 font-mono text-xs text-zinc-700 select-none data-focus:bg-zinc-100 data-selected:text-emerald-700 dark:text-zinc-200 dark:data-focus:bg-white/10 dark:data-selected:text-emerald-300",
|
|
1443
|
+
children: [/* @__PURE__ */ jsxs("span", {
|
|
1444
|
+
className: "min-w-0",
|
|
1445
|
+
children: [/* @__PURE__ */ jsx("span", {
|
|
1446
|
+
className: "block truncate",
|
|
1447
|
+
children: option.label
|
|
1448
|
+
}), option.description ? /* @__PURE__ */ jsx("span", {
|
|
1449
|
+
className: "mt-0.5 block truncate text-2xs text-zinc-500 dark:text-zinc-400",
|
|
1450
|
+
children: option.description
|
|
1451
|
+
}) : null]
|
|
1452
|
+
}), /* @__PURE__ */ jsx(CheckIcon, {
|
|
1453
|
+
className: "h-3.5 w-3.5 shrink-0 opacity-0 group-data-selected:opacity-100",
|
|
1454
|
+
"aria-hidden": "true"
|
|
1455
|
+
})]
|
|
1456
|
+
}, option.value))
|
|
1457
|
+
})]
|
|
1458
|
+
})
|
|
1459
|
+
});
|
|
1460
|
+
}
|
|
1461
|
+
function getServerPreviewUrl(server, variables) {
|
|
1462
|
+
return (server.url ?? "").replace(/\{([^}]+)\}/g, (_, name) => variables[name] ?? server.variables?.[name]?.default ?? `{${name}}`);
|
|
1463
|
+
}
|
|
1464
|
+
function ServerUrlValue(arg0) {
|
|
1465
|
+
const { server, variables, open, onToggle } = arg0;
|
|
1466
|
+
const url = getServerPreviewUrl(server, variables);
|
|
1467
|
+
return /* @__PURE__ */ jsxs("button", {
|
|
1468
|
+
type: "button",
|
|
1469
|
+
"aria-expanded": open,
|
|
1470
|
+
"aria-label": "Server",
|
|
1471
|
+
onClick: onToggle,
|
|
1472
|
+
className: clsx("flex h-8 w-8 shrink-0 items-center justify-center rounded-lg bg-zinc-100/50 text-zinc-600 transition hover:bg-zinc-100 hover:text-zinc-950 dark:bg-white/5 dark:text-zinc-300 dark:hover:bg-white/10 dark:hover:text-white sm:w-auto sm:min-w-16 sm:max-w-[min(36%,16rem)] sm:px-1.5", open ? "bg-zinc-200 text-zinc-950 dark:bg-white/12 dark:text-white" : null),
|
|
1473
|
+
children: [/* @__PURE__ */ jsx("span", {
|
|
1474
|
+
className: "sm:hidden",
|
|
1475
|
+
children: /* @__PURE__ */ jsx(ServerIcon, {
|
|
1476
|
+
className: "h-4 w-4",
|
|
1477
|
+
"aria-hidden": "true"
|
|
1478
|
+
})
|
|
1479
|
+
}), /* @__PURE__ */ jsxs("span", {
|
|
1480
|
+
className: "hidden min-w-0 items-center gap-1 overflow-hidden sm:flex",
|
|
1481
|
+
children: [/* @__PURE__ */ jsx("span", {
|
|
1482
|
+
className: "truncate font-mono text-xs",
|
|
1483
|
+
children: url
|
|
1484
|
+
}), /* @__PURE__ */ jsx(ChevronDownIcon, {
|
|
1485
|
+
className: "h-3.5 w-3.5 shrink-0 text-zinc-400",
|
|
1486
|
+
"aria-hidden": "true"
|
|
1487
|
+
})]
|
|
1488
|
+
})]
|
|
1489
|
+
});
|
|
1490
|
+
}
|
|
1491
|
+
function ServerVariableControl(arg0) {
|
|
1492
|
+
const { name, variable, value, onChange, compact = false } = arg0;
|
|
1493
|
+
if (variable?.enum?.length) return /* @__PURE__ */ jsx(InlineListbox, {
|
|
1494
|
+
label: name,
|
|
1495
|
+
value,
|
|
1496
|
+
options: variable.enum.map((option) => ({
|
|
1497
|
+
value: option,
|
|
1498
|
+
label: option
|
|
1499
|
+
})),
|
|
1500
|
+
onChange,
|
|
1501
|
+
compact
|
|
1502
|
+
});
|
|
1503
|
+
return /* @__PURE__ */ jsx("input", {
|
|
1504
|
+
"aria-label": name,
|
|
1505
|
+
value,
|
|
1506
|
+
placeholder: variable?.default ?? name,
|
|
1507
|
+
onChange: (event) => onChange(event.target.value),
|
|
1508
|
+
className: clsx("pointer-events-auto rounded-md border border-zinc-200 bg-white font-mono text-xs font-semibold text-zinc-900 shadow-xs outline-hidden transition placeholder:text-zinc-500 hover:border-zinc-300 hover:bg-zinc-50 focus:border-zinc-400 focus:bg-white dark:border-white/10 dark:bg-zinc-950 dark:text-zinc-100 dark:placeholder:text-zinc-500 dark:hover:border-white/15 dark:hover:bg-zinc-900 dark:focus:border-white/20 dark:focus:bg-zinc-950", compact ? "mx-0.5 w-24 px-1.5 py-0.5" : "w-full px-2.5 py-1.5")
|
|
1509
|
+
});
|
|
1510
|
+
}
|
|
1511
|
+
function ServerPanel(arg0) {
|
|
1512
|
+
const { servers, selectedKey, selectedServer, variables, onSelectServer, onChangeVariable } = arg0;
|
|
1513
|
+
const variableEntries = Object.entries(selectedServer.variables ?? {});
|
|
1514
|
+
return /* @__PURE__ */ jsx("div", {
|
|
1515
|
+
className: "border-t border-zinc-200 bg-zinc-100/70 p-3 dark:border-white/10 dark:bg-zinc-900/60",
|
|
1516
|
+
children: /* @__PURE__ */ jsxs("div", {
|
|
1517
|
+
className: "grid gap-3 sm:grid-cols-[minmax(0,1fr)_minmax(0,1.2fr)]",
|
|
1518
|
+
children: [servers.length > 1 ? /* @__PURE__ */ jsxs("label", {
|
|
1519
|
+
className: "flex min-w-0 flex-col gap-1.5",
|
|
1520
|
+
children: [/* @__PURE__ */ jsx("span", {
|
|
1521
|
+
className: "text-2xs font-semibold text-zinc-700 dark:text-zinc-300",
|
|
1522
|
+
children: "Server"
|
|
1523
|
+
}), /* @__PURE__ */ jsx(InlineListbox, {
|
|
1524
|
+
label: "Server",
|
|
1525
|
+
value: selectedKey,
|
|
1526
|
+
options: servers.map((server, index) => ({
|
|
1527
|
+
value: getServerKey(server, index),
|
|
1528
|
+
label: getServerLabel(server, index),
|
|
1529
|
+
description: server.description
|
|
1530
|
+
})),
|
|
1531
|
+
onChange: onSelectServer
|
|
1532
|
+
})]
|
|
1533
|
+
}) : null, variableEntries.map(([name, variable]) => /* @__PURE__ */ jsxs("label", {
|
|
1534
|
+
className: "flex min-w-0 flex-col gap-1.5",
|
|
1535
|
+
children: [/* @__PURE__ */ jsx("span", {
|
|
1536
|
+
className: "text-2xs font-semibold text-zinc-700 dark:text-zinc-300",
|
|
1537
|
+
children: name
|
|
1538
|
+
}), /* @__PURE__ */ jsx(ServerVariableControl, {
|
|
1539
|
+
name,
|
|
1540
|
+
variable,
|
|
1541
|
+
value: variables[name] ?? variable.default ?? "",
|
|
1542
|
+
onChange: (value) => onChangeVariable(name, value)
|
|
1543
|
+
})]
|
|
1544
|
+
}, name))]
|
|
1545
|
+
})
|
|
1546
|
+
});
|
|
1547
|
+
}
|
|
1548
|
+
function AuthPanel(arg0) {
|
|
1549
|
+
const { authOptions, selectedAuthName, selectedAuth, authValues, onSelectAuth, onChangeAuthValue } = arg0;
|
|
1550
|
+
if (authOptions.length === 0) return null;
|
|
1551
|
+
return /* @__PURE__ */ jsx("div", {
|
|
1552
|
+
className: "border-t border-zinc-200 bg-zinc-100/70 p-3 dark:border-white/10 dark:bg-zinc-900/60",
|
|
1553
|
+
children: /* @__PURE__ */ jsxs("div", {
|
|
1554
|
+
className: "grid gap-3 sm:grid-cols-[minmax(0,1fr)_minmax(0,1.2fr)]",
|
|
1555
|
+
children: [/* @__PURE__ */ jsxs("label", {
|
|
1556
|
+
className: "flex min-w-0 flex-col gap-1.5",
|
|
1557
|
+
children: [/* @__PURE__ */ jsx("span", {
|
|
1558
|
+
className: "text-2xs font-semibold text-zinc-700 dark:text-zinc-300",
|
|
1559
|
+
children: "Auth"
|
|
1560
|
+
}), /* @__PURE__ */ jsx(InlineListbox, {
|
|
1561
|
+
label: "Auth",
|
|
1562
|
+
value: selectedAuthName,
|
|
1563
|
+
options: authOptions.map(({ name, scheme }) => ({
|
|
1564
|
+
value: name,
|
|
1565
|
+
label: name,
|
|
1566
|
+
description: authLabel(name, scheme)
|
|
1567
|
+
})),
|
|
1568
|
+
onChange: onSelectAuth
|
|
1569
|
+
})]
|
|
1570
|
+
}), selectedAuth ? /* @__PURE__ */ jsxs("label", {
|
|
1571
|
+
className: "flex min-w-0 flex-col gap-1.5",
|
|
1572
|
+
children: [/* @__PURE__ */ jsx("span", {
|
|
1573
|
+
className: "text-2xs font-semibold text-zinc-700 dark:text-zinc-300",
|
|
1574
|
+
children: "Credential"
|
|
1575
|
+
}), /* @__PURE__ */ jsxs("div", {
|
|
1576
|
+
className: "flex min-w-0 items-center rounded-md border border-zinc-200 bg-white px-2.5 py-1.5 shadow-xs dark:border-white/10 dark:bg-zinc-950",
|
|
1577
|
+
children: [/* @__PURE__ */ jsx("span", {
|
|
1578
|
+
className: "mr-2 shrink-0 font-mono text-2xs font-semibold text-zinc-600 dark:text-zinc-400",
|
|
1579
|
+
children: selectedAuth.scheme.type === "apiKey" ? selectedAuth.scheme.in ?? "apiKey" : selectedAuth.scheme.scheme ?? selectedAuth.scheme.type ?? "token"
|
|
1580
|
+
}), /* @__PURE__ */ jsx("input", {
|
|
1581
|
+
value: authValues[selectedAuth.name] ?? authPlaceholder(selectedAuth),
|
|
1582
|
+
onChange: (event) => onChangeAuthValue(selectedAuth.name, event.target.value),
|
|
1583
|
+
className: "min-w-0 flex-1 border-0 bg-transparent px-0 py-0 font-mono text-xs font-semibold text-zinc-900 outline-hidden placeholder:text-zinc-500 dark:text-zinc-100 dark:placeholder:text-zinc-500"
|
|
1584
|
+
})]
|
|
1585
|
+
})]
|
|
1586
|
+
}) : null]
|
|
1587
|
+
})
|
|
1588
|
+
});
|
|
1589
|
+
}
|
|
1590
|
+
function EndpointIdentity(arg0) {
|
|
1591
|
+
const { method, path, servers, selectedServerKey, selectedServer, serverVariables, serverOpen, authOptions, selectedAuthName, selectedAuth, authValues, authOpen, onSelectServer, onChangeServerVariable, onToggleServer, onToggleAuth, onSelectAuth, onChangeAuthValue } = arg0;
|
|
1592
|
+
const segments = path.split("/").filter(Boolean);
|
|
1593
|
+
return /* @__PURE__ */ jsxs("div", {
|
|
1594
|
+
className: "not-prose flex w-full flex-col overflow-hidden rounded-xl border border-zinc-200 bg-white shadow-xs dark:border-white/10 dark:bg-zinc-950",
|
|
1595
|
+
children: [
|
|
1596
|
+
/* @__PURE__ */ jsxs("div", {
|
|
1597
|
+
className: "flex min-w-0 items-center gap-1.5 overflow-hidden px-2.5 py-2",
|
|
1598
|
+
children: [
|
|
1599
|
+
/* @__PURE__ */ jsx(EndpointMethodBadge, { method }),
|
|
1600
|
+
/* @__PURE__ */ jsx(ServerUrlValue, {
|
|
1601
|
+
server: selectedServer,
|
|
1602
|
+
variables: serverVariables,
|
|
1603
|
+
open: serverOpen,
|
|
1604
|
+
onToggle: onToggleServer
|
|
1605
|
+
}),
|
|
1606
|
+
/* @__PURE__ */ jsx("div", {
|
|
1607
|
+
className: "flex min-w-0 flex-1 items-center overflow-x-auto font-mono text-sm font-bold leading-6 whitespace-nowrap",
|
|
1608
|
+
children: segments.length > 0 ? /* @__PURE__ */ jsxs(Fragment$1, { children: [/* @__PURE__ */ jsx("span", {
|
|
1609
|
+
className: "text-zinc-400",
|
|
1610
|
+
children: "/"
|
|
1611
|
+
}), segments.map((segment, index) => /* @__PURE__ */ jsxs("span", {
|
|
1612
|
+
className: "flex items-center",
|
|
1613
|
+
children: [index > 0 ? /* @__PURE__ */ jsx("span", {
|
|
1614
|
+
className: "text-zinc-400",
|
|
1615
|
+
children: "/"
|
|
1616
|
+
}) : null, /* @__PURE__ */ jsx("span", {
|
|
1617
|
+
className: "font-bold text-zinc-800 dark:text-white",
|
|
1618
|
+
children: segment
|
|
1619
|
+
})]
|
|
1620
|
+
}, `${segment}-${index}`))] }) : /* @__PURE__ */ jsx("span", {
|
|
1621
|
+
className: "font-bold text-zinc-800 dark:text-white",
|
|
1622
|
+
children: "/"
|
|
1623
|
+
})
|
|
1624
|
+
}),
|
|
1625
|
+
authOptions.length > 0 ? /* @__PURE__ */ jsx("button", {
|
|
1626
|
+
type: "button",
|
|
1627
|
+
"aria-expanded": authOpen,
|
|
1628
|
+
"aria-label": "Auth",
|
|
1629
|
+
onClick: onToggleAuth,
|
|
1630
|
+
className: clsx("ml-auto flex h-8 w-8 shrink-0 items-center justify-center rounded-lg text-zinc-600 transition hover:bg-zinc-100 hover:text-emerald-700 dark:text-zinc-300 dark:hover:bg-white/10 dark:hover:text-emerald-200", authOpen ? "bg-emerald-100 text-emerald-800 dark:bg-emerald-400/15 dark:text-emerald-100" : "bg-zinc-50 dark:bg-white/5"),
|
|
1631
|
+
children: authOpen ? /* @__PURE__ */ jsx(UnlockKeyholeIcon, {
|
|
1632
|
+
className: "h-4 w-4",
|
|
1633
|
+
"aria-hidden": "true"
|
|
1634
|
+
}) : /* @__PURE__ */ jsx(LockKeyholeIcon, {
|
|
1635
|
+
className: "h-4 w-4",
|
|
1636
|
+
"aria-hidden": "true"
|
|
1637
|
+
})
|
|
1638
|
+
}) : null
|
|
1639
|
+
]
|
|
1640
|
+
}),
|
|
1641
|
+
serverOpen ? /* @__PURE__ */ jsx(ServerPanel, {
|
|
1642
|
+
servers,
|
|
1643
|
+
selectedKey: selectedServerKey,
|
|
1644
|
+
selectedServer,
|
|
1645
|
+
variables: serverVariables,
|
|
1646
|
+
onSelectServer,
|
|
1647
|
+
onChangeVariable: onChangeServerVariable
|
|
1648
|
+
}) : null,
|
|
1649
|
+
authOpen ? /* @__PURE__ */ jsx(AuthPanel, {
|
|
1650
|
+
authOptions,
|
|
1651
|
+
selectedAuthName,
|
|
1652
|
+
selectedAuth,
|
|
1653
|
+
authValues,
|
|
1654
|
+
onSelectAuth,
|
|
1655
|
+
onChangeAuthValue
|
|
685
1656
|
}) : null
|
|
686
1657
|
]
|
|
687
1658
|
});
|
|
688
1659
|
}
|
|
689
1660
|
function OpenApiOperation(arg0) {
|
|
690
1661
|
const { spec, path, method, operation } = arg0;
|
|
1662
|
+
const t = useBuiltInText();
|
|
691
1663
|
const id = slug(`${method.toLowerCase()} ${path}`);
|
|
692
1664
|
const summary = operation.summary ?? `${method} ${path}`;
|
|
693
1665
|
const description = operation.description;
|
|
694
1666
|
const parameters = getOperationParameters(spec, path, operation);
|
|
695
|
-
const requestBody = getRequestBody(operation);
|
|
1667
|
+
const requestBody = getRequestBody$1(operation);
|
|
696
1668
|
const requestContents = getMediaTypeEntries(requestBody?.content);
|
|
697
|
-
const
|
|
1669
|
+
const [selectedRequestMediaType, setSelectedRequestMediaType] = useState(requestContents[0]?.mediaType ?? "");
|
|
1670
|
+
const selectedRequestContent = requestContents.find((content) => content.mediaType === selectedRequestMediaType) ?? requestContents[0];
|
|
1671
|
+
const requestSchema = selectedRequestContent?.value.schema;
|
|
1672
|
+
const servers = getServers(spec, operation);
|
|
1673
|
+
const [selectedServerKey, setSelectedServerKey] = useState(getServerKey(servers[0], 0));
|
|
1674
|
+
const selectedServer = servers.find((server, index) => getServerKey(server, index) === selectedServerKey) ?? servers[0];
|
|
1675
|
+
const [serverVariables, setServerVariables] = useState(defaultServerVariables(selectedServer));
|
|
1676
|
+
const [serverOpen, setServerOpen] = useState(false);
|
|
1677
|
+
const authOptions = getAuthOptions(spec, operation);
|
|
1678
|
+
const [selectedAuthName, setSelectedAuthName] = useState(authOptions[0]?.name ?? "");
|
|
1679
|
+
const selectedAuth = authOptions.find((option) => option.name === selectedAuthName);
|
|
1680
|
+
const [authValues, setAuthValues] = useState({});
|
|
1681
|
+
const [authOpen, setAuthOpen] = useState(false);
|
|
1682
|
+
const authInput = selectedAuth ? {
|
|
1683
|
+
name: selectedAuth.name,
|
|
1684
|
+
scheme: selectedAuth.scheme,
|
|
1685
|
+
value: authValues[selectedAuth.name] ?? authPlaceholder(selectedAuth)
|
|
1686
|
+
} : void 0;
|
|
698
1687
|
const groupedParameters = {
|
|
699
1688
|
path: parameters.filter((parameter) => parameter.in === "path"),
|
|
700
1689
|
query: parameters.filter((parameter) => parameter.in === "query"),
|
|
701
1690
|
header: parameters.filter((parameter) => parameter.in === "header")
|
|
702
1691
|
};
|
|
703
1692
|
return /* @__PURE__ */ jsxs("section", {
|
|
704
|
-
className: "clarify-api-endpoint scroll-mt-24",
|
|
1693
|
+
className: "clarify-api-endpoint scroll-mt-24 py-16 first:pt-0 last:pb-0",
|
|
705
1694
|
"aria-labelledby": id,
|
|
706
|
-
children: [
|
|
707
|
-
|
|
708
|
-
|
|
709
|
-
|
|
710
|
-
|
|
711
|
-
|
|
712
|
-
|
|
713
|
-
|
|
714
|
-
|
|
715
|
-
|
|
716
|
-
|
|
717
|
-
|
|
718
|
-
|
|
719
|
-
|
|
1695
|
+
children: [
|
|
1696
|
+
/* @__PURE__ */ jsx(EndpointIdentity, {
|
|
1697
|
+
method,
|
|
1698
|
+
path,
|
|
1699
|
+
servers,
|
|
1700
|
+
selectedServerKey,
|
|
1701
|
+
selectedServer,
|
|
1702
|
+
serverVariables,
|
|
1703
|
+
serverOpen,
|
|
1704
|
+
authOptions,
|
|
1705
|
+
selectedAuthName,
|
|
1706
|
+
selectedAuth,
|
|
1707
|
+
authValues,
|
|
1708
|
+
authOpen,
|
|
1709
|
+
onSelectServer: (value) => {
|
|
1710
|
+
const nextServer = servers.find((server, index) => getServerKey(server, index) === value) ?? servers[0];
|
|
1711
|
+
setSelectedServerKey(value);
|
|
1712
|
+
setServerVariables(defaultServerVariables(nextServer));
|
|
1713
|
+
},
|
|
1714
|
+
onChangeServerVariable: (name, value) => setServerVariables((current) => ({
|
|
1715
|
+
...current,
|
|
1716
|
+
[name]: value
|
|
1717
|
+
})),
|
|
1718
|
+
onToggleServer: () => {
|
|
1719
|
+
setServerOpen((current) => !current);
|
|
1720
|
+
setAuthOpen(false);
|
|
1721
|
+
},
|
|
1722
|
+
onToggleAuth: () => {
|
|
1723
|
+
setAuthOpen((current) => !current);
|
|
1724
|
+
setServerOpen(false);
|
|
1725
|
+
},
|
|
1726
|
+
onSelectAuth: setSelectedAuthName,
|
|
1727
|
+
onChangeAuthValue: (name, value) => setAuthValues((current) => ({
|
|
1728
|
+
...current,
|
|
1729
|
+
[name]: value
|
|
1730
|
+
}))
|
|
720
1731
|
}),
|
|
721
|
-
/* @__PURE__ */ jsx(
|
|
722
|
-
|
|
723
|
-
|
|
1732
|
+
/* @__PURE__ */ jsx(Heading, {
|
|
1733
|
+
id,
|
|
1734
|
+
className: "mt-4",
|
|
1735
|
+
children: summary
|
|
724
1736
|
}),
|
|
725
|
-
|
|
726
|
-
/* @__PURE__ */ jsx("
|
|
727
|
-
|
|
728
|
-
|
|
729
|
-
|
|
730
|
-
|
|
1737
|
+
/* @__PURE__ */ jsxs(Row, { children: [/* @__PURE__ */ jsxs(Col, { children: [
|
|
1738
|
+
description ? /* @__PURE__ */ jsx("p", { children: description }) : null,
|
|
1739
|
+
/* @__PURE__ */ jsx(ParameterList, {
|
|
1740
|
+
title: t("openapi.pathParameters"),
|
|
1741
|
+
parameters: groupedParameters.path
|
|
1742
|
+
}),
|
|
1743
|
+
/* @__PURE__ */ jsx(ParameterList, {
|
|
1744
|
+
title: t("openapi.queryParameters"),
|
|
1745
|
+
parameters: groupedParameters.query
|
|
1746
|
+
}),
|
|
1747
|
+
/* @__PURE__ */ jsx(ParameterList, {
|
|
1748
|
+
title: t("openapi.headers"),
|
|
1749
|
+
parameters: groupedParameters.header
|
|
1750
|
+
}),
|
|
1751
|
+
requestBody && requestContents.length > 0 ? /* @__PURE__ */ jsxs(Fragment$1, { children: [
|
|
1752
|
+
/* @__PURE__ */ jsx("h3", { children: t("openapi.requestBody") }),
|
|
1753
|
+
typeof requestBody.description === "string" ? /* @__PURE__ */ jsx("p", { children: requestBody.description }) : null,
|
|
1754
|
+
/* @__PURE__ */ jsx(SchemaProperties, {
|
|
1755
|
+
title: t("openapi.bodyProperties"),
|
|
1756
|
+
schema: requestSchema,
|
|
1757
|
+
spec
|
|
1758
|
+
})
|
|
1759
|
+
] }) : null,
|
|
1760
|
+
/* @__PURE__ */ jsx(ResponseList, { operation })
|
|
1761
|
+
] }), /* @__PURE__ */ jsx(Col, {
|
|
1762
|
+
sticky: true,
|
|
1763
|
+
children: /* @__PURE__ */ jsx(EndpointExamples, {
|
|
1764
|
+
spec,
|
|
1765
|
+
path,
|
|
1766
|
+
method,
|
|
1767
|
+
operation,
|
|
1768
|
+
parameters,
|
|
1769
|
+
requestContents,
|
|
1770
|
+
selectedRequestMediaType: selectedRequestContent?.mediaType ?? "",
|
|
1771
|
+
onSelectRequestMediaType: setSelectedRequestMediaType,
|
|
1772
|
+
selectedServer,
|
|
1773
|
+
serverVariables,
|
|
1774
|
+
auth: authInput
|
|
731
1775
|
})
|
|
732
|
-
] })
|
|
733
|
-
|
|
734
|
-
] }), /* @__PURE__ */ jsx(Col, {
|
|
735
|
-
sticky: true,
|
|
736
|
-
children: /* @__PURE__ */ jsx(EndpointExamples, {
|
|
737
|
-
spec,
|
|
738
|
-
path,
|
|
739
|
-
method,
|
|
740
|
-
operation,
|
|
741
|
-
parameters,
|
|
742
|
-
requestContents
|
|
743
|
-
})
|
|
744
|
-
})] })]
|
|
1776
|
+
})] })
|
|
1777
|
+
]
|
|
745
1778
|
});
|
|
746
1779
|
}
|
|
747
1780
|
function OpenApiPaths(arg0) {
|
|
748
1781
|
const { spec } = arg0;
|
|
749
1782
|
return /* @__PURE__ */ jsx("div", {
|
|
750
|
-
className: "clarify-api-endpoints
|
|
1783
|
+
className: "clarify-api-endpoints divide-y divide-zinc-200/70 dark:divide-white/10",
|
|
751
1784
|
children: listOpenApiOperations(spec).map(({ path, method, operation }) => ({
|
|
752
1785
|
path,
|
|
753
1786
|
method: method.toUpperCase(),
|
|
@@ -760,29 +1793,6 @@ function OpenApiPaths(arg0) {
|
|
|
760
1793
|
}, `${method}-${path}`))
|
|
761
1794
|
});
|
|
762
1795
|
}
|
|
763
|
-
function resolveRelativePath(fromDir, to) {
|
|
764
|
-
const parts = (fromDir + "/" + to).split("/").filter(Boolean);
|
|
765
|
-
const stack = [];
|
|
766
|
-
for (const part of parts) if (part === "..") stack.pop();
|
|
767
|
-
else if (part !== ".") stack.push(part);
|
|
768
|
-
return stack.join("/");
|
|
769
|
-
}
|
|
770
|
-
function normalizeSpecPath(specPath, currentRoutePath, routePrefix = "") {
|
|
771
|
-
if (specPath.startsWith(VIRTUAL_PREFIX)) return specPath;
|
|
772
|
-
const normalizedRoutePrefix = routePrefix.replace(/^\/+|\/+$/g, "");
|
|
773
|
-
const normalizedSpecPath = specPath.startsWith("/") && normalizedRoutePrefix && specPath.slice(1).startsWith(`${normalizedRoutePrefix}/`) ? "/" + specPath.slice(normalizedRoutePrefix.length + 2) : specPath;
|
|
774
|
-
if (normalizedSpecPath.startsWith("/")) return VIRTUAL_PREFIX + normalizedSpecPath.replace(/^\//, "");
|
|
775
|
-
const fromDir = currentRoutePath === "/" ? "" : currentRoutePath?.replace(/^\//, "").replace(/\/[^/]*$/, "") ?? "";
|
|
776
|
-
return VIRTUAL_PREFIX + resolveRelativePath(normalizedRoutePrefix && fromDir.startsWith(`${normalizedRoutePrefix}/`) ? fromDir.slice(normalizedRoutePrefix.length + 1) : fromDir, normalizedSpecPath);
|
|
777
|
-
}
|
|
778
|
-
function useOpenApiSpec(spec, specPath) {
|
|
779
|
-
const specs = useOpenApis();
|
|
780
|
-
const location = useLocation();
|
|
781
|
-
const config = useClarifyConfig();
|
|
782
|
-
if (spec) return spec;
|
|
783
|
-
if (!specPath) return null;
|
|
784
|
-
return specs[normalizeSpecPath(specPath, location.pathname, config.routePrefix)] ?? null;
|
|
785
|
-
}
|
|
786
1796
|
function WarningBox(arg0) {
|
|
787
1797
|
const { children, tone = "amber" } = arg0;
|
|
788
1798
|
return /* @__PURE__ */ jsx("div", {
|
|
@@ -792,27 +1802,24 @@ function WarningBox(arg0) {
|
|
|
792
1802
|
}
|
|
793
1803
|
function OpenApiPage(arg0) {
|
|
794
1804
|
const { spec, specPath } = arg0;
|
|
1805
|
+
const t = useBuiltInText();
|
|
795
1806
|
const resolved = useOpenApiSpec(spec, specPath);
|
|
796
|
-
if (!resolved) return /* @__PURE__ */
|
|
797
|
-
return /* @__PURE__ */
|
|
1807
|
+
if (!resolved) return /* @__PURE__ */ jsx(WarningBox, { children: t("openapi.specNotFound", { specPath: specPath ?? t("openapi.specPathMissing") }) });
|
|
1808
|
+
return /* @__PURE__ */ jsx("article", {
|
|
798
1809
|
className: "clarify-openapi-page flex h-full flex-col pt-16 pb-10",
|
|
799
|
-
children:
|
|
1810
|
+
children: /* @__PURE__ */ jsxs(Prose, {
|
|
800
1811
|
className: "flex-auto",
|
|
801
1812
|
children: [/* @__PURE__ */ jsx(OpenApiHeader, { spec: resolved }), /* @__PURE__ */ jsx(OpenApiPaths, { spec: resolved })]
|
|
802
|
-
})
|
|
1813
|
+
})
|
|
803
1814
|
});
|
|
804
1815
|
}
|
|
805
1816
|
function ApiEndpoint(arg0) {
|
|
806
1817
|
const { spec, path, method } = arg0;
|
|
1818
|
+
const t = useBuiltInText();
|
|
807
1819
|
const op = getOpenApiOperation(spec, path, method);
|
|
808
|
-
if (!op) return /* @__PURE__ */
|
|
1820
|
+
if (!op) return /* @__PURE__ */ jsx(WarningBox, {
|
|
809
1821
|
tone: "red",
|
|
810
|
-
children:
|
|
811
|
-
"Endpoint not found: ",
|
|
812
|
-
method.toUpperCase(),
|
|
813
|
-
" ",
|
|
814
|
-
path
|
|
815
|
-
]
|
|
1822
|
+
children: t("openapi.endpointNotFound", { endpoint: `${method.toUpperCase()} ${path}` })
|
|
816
1823
|
});
|
|
817
1824
|
return /* @__PURE__ */ jsx(OpenApiOperation, {
|
|
818
1825
|
spec,
|
|
@@ -823,8 +1830,9 @@ function ApiEndpoint(arg0) {
|
|
|
823
1830
|
}
|
|
824
1831
|
function OpenApiEndpoint(arg0) {
|
|
825
1832
|
const { specPath, path, method } = arg0;
|
|
1833
|
+
const t = useBuiltInText();
|
|
826
1834
|
const spec = useOpenApiSpec(void 0, specPath);
|
|
827
|
-
if (!spec) return /* @__PURE__ */
|
|
1835
|
+
if (!spec) return /* @__PURE__ */ jsx(WarningBox, { children: t("openapi.specNotFound", { specPath }) });
|
|
828
1836
|
return /* @__PURE__ */ jsx(ApiEndpoint, {
|
|
829
1837
|
spec,
|
|
830
1838
|
path,
|
|
@@ -845,6 +1853,6 @@ function useMDXComponents(components = {}) {
|
|
|
845
1853
|
};
|
|
846
1854
|
}
|
|
847
1855
|
//#endregion
|
|
848
|
-
export { ApiEndpoint, ApiEndpointCard, AppShell, BuiltWithClarify, Button, ClarifyConfigContext, Code, CodeGroup, DocShell, Feedback, GridPattern, Heading, HeroPattern, Logo, OpenApiEndpoint, OpenApiPage, OpenApisContext, PageFooter, Pre, Prose, SectionProvider, Tag, ThemeProvider, ThemeToggle, remToPx, render, useClarifyConfig, useMDXComponents, useOpenApis, useSectionStore, useTheme };
|
|
1856
|
+
export { ApiEndpoint, ApiEndpointCard, AppShell, BuiltWithClarify, Button, Callout, Card, CardGroup, ClarifyConfigContext, Code, CodeGroup, DocShell, Feedback, GridPattern, Heading, HeroPattern, Logo, OpenApiEndpoint, OpenApiPage, OpenApisContext, PageFooter, Pre, Prose, SectionProvider, Tag, ThemeProvider, ThemeToggle, remToPx, render, useClarifyConfig, useMDXComponents, useOpenApis, useSectionStore, useTheme };
|
|
849
1857
|
|
|
850
1858
|
//# sourceMappingURL=index.js.map
|