zudoku 0.1.1-dev.47 → 0.1.1-dev.48
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/lib/components/Select.js +1 -1
- package/dist/lib/components/Select.js.map +1 -1
- package/dist/lib/components/index.d.ts +0 -1
- package/dist/lib/components/index.js +0 -1
- package/dist/lib/components/index.js.map +1 -1
- package/dist/lib/components/navigation/SideNavigationItem.js +1 -2
- package/dist/lib/components/navigation/SideNavigationItem.js.map +1 -1
- package/dist/lib/core/DevPortalContext.d.ts +3 -5
- package/dist/lib/core/DevPortalContext.js.map +1 -1
- package/dist/lib/oas/graphql/index.js +1 -1
- package/dist/lib/oas/graphql/index.js.map +1 -1
- package/dist/lib/plugins/api-key/index.js +1 -1
- package/dist/lib/plugins/api-key/index.js.map +1 -1
- package/dist/lib/plugins/openapi/MakeRequest.js +1 -1
- package/dist/lib/plugins/openapi/MakeRequest.js.map +1 -1
- package/dist/lib/plugins/openapi/OperationList.js +7 -0
- package/dist/lib/plugins/openapi/OperationList.js.map +1 -1
- package/dist/lib/plugins/openapi/SchemaListView.js +3 -3
- package/dist/lib/plugins/openapi/SchemaListView.js.map +1 -1
- package/dist/lib/plugins/openapi/graphql/gql.d.ts +2 -2
- package/dist/lib/plugins/openapi/graphql/gql.js +1 -1
- package/dist/lib/plugins/openapi/graphql/gql.js.map +1 -1
- package/dist/lib/plugins/openapi/graphql/graphql.d.ts +8 -0
- package/dist/lib/plugins/openapi/graphql/graphql.js +46 -0
- package/dist/lib/plugins/openapi/graphql/graphql.js.map +1 -1
- package/dist/lib/plugins/openapi/playground/Playground.d.ts +1 -0
- package/dist/lib/plugins/openapi/playground/Playground.js +18 -8
- package/dist/lib/plugins/openapi/playground/Playground.js.map +1 -1
- package/dist/lib/plugins/openapi/playground/QueryParams.js +0 -2
- package/dist/lib/plugins/openapi/playground/QueryParams.js.map +1 -1
- package/lib/assets/{worker-W78u54MC.js → worker-BGlCY74N.js} +1 -1
- package/lib/zudoku.components.js +92 -97
- package/lib/zudoku.openapi-worker.js +6 -6
- package/lib/zudoku.plugins.js +4410 -4321
- package/package.json +2 -1
- package/src/lib/components/Select.tsx +3 -3
- package/src/lib/components/index.ts +0 -1
- package/src/lib/components/navigation/SideNavigationItem.tsx +1 -2
- package/src/lib/core/DevPortalContext.ts +3 -6
- package/src/lib/oas/graphql/index.ts +1 -1
- package/src/lib/plugins/api-key/index.tsx +1 -1
- package/src/lib/plugins/openapi/MakeRequest.tsx +1 -1
- package/src/lib/plugins/openapi/OperationList.tsx +7 -0
- package/src/lib/plugins/openapi/SchemaListView.tsx +4 -5
- package/src/lib/plugins/openapi/graphql/gql.ts +3 -3
- package/src/lib/plugins/openapi/graphql/graphql.ts +54 -0
- package/src/lib/plugins/openapi/playground/Playground.tsx +72 -25
- package/src/lib/plugins/openapi/playground/QueryParams.tsx +0 -3
- package/dist/lib/components/DynamicIcon.d.ts +0 -6
- package/dist/lib/components/DynamicIcon.js +0 -6
- package/dist/lib/components/DynamicIcon.js.map +0 -1
- package/src/lib/components/DynamicIcon.tsx +0 -60
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "zudoku",
|
|
3
|
-
"version": "0.1.1-dev.
|
|
3
|
+
"version": "0.1.1-dev.48",
|
|
4
4
|
"type": "module",
|
|
5
5
|
"files": [
|
|
6
6
|
"dist",
|
|
@@ -54,6 +54,7 @@
|
|
|
54
54
|
"@monaco-editor/react": "^4.6.0",
|
|
55
55
|
"@pothos/core": "3.41.0",
|
|
56
56
|
"@radix-ui/react-select": "2.1.1",
|
|
57
|
+
"@radix-ui/react-visually-hidden": "1.1.0",
|
|
57
58
|
"@sentry/node": "8.11.0",
|
|
58
59
|
"@stefanprobst/rehype-extract-toc": "2.2.0",
|
|
59
60
|
"@tailwindcss/typography": "0.5.13",
|
|
@@ -16,14 +16,14 @@ const SelectTrigger = React.forwardRef<
|
|
|
16
16
|
<SelectPrimitive.Trigger
|
|
17
17
|
ref={ref}
|
|
18
18
|
className={cn(
|
|
19
|
-
"flex h-10 w-full items-center justify-between rounded-md border border-input bg-background px-3 py-2 text-sm ring-offset-background placeholder:text-muted-foreground focus:outline-none focus:ring-2 focus:ring-ring focus:ring-offset-2 disabled:cursor-not-allowed disabled:opacity-50
|
|
19
|
+
"flex h-10 w-full items-center justify-between rounded-md border border-input bg-background px-3 py-2 text-sm ring-offset-background placeholder:text-muted-foreground focus:outline-none focus:ring-2 focus:ring-ring focus:ring-offset-2 disabled:cursor-not-allowed disabled:opacity-50",
|
|
20
20
|
className,
|
|
21
21
|
)}
|
|
22
22
|
{...props}
|
|
23
23
|
>
|
|
24
|
-
{children}
|
|
24
|
+
<span className="truncate">{children}</span>
|
|
25
25
|
<SelectPrimitive.Icon asChild>
|
|
26
|
-
<ChevronDown className="h-4 w-4 opacity-50" />
|
|
26
|
+
<ChevronDown className="flex-shrink-0 h-4 w-4 opacity-50" />
|
|
27
27
|
</SelectPrimitive.Icon>
|
|
28
28
|
</SelectPrimitive.Trigger>
|
|
29
29
|
));
|
|
@@ -11,7 +11,6 @@ import type {
|
|
|
11
11
|
import { cn } from "../../util/cn.js";
|
|
12
12
|
import { joinPath } from "../../util/joinPath.js";
|
|
13
13
|
import { AnchorLink } from "../AnchorLink.js";
|
|
14
|
-
import { DynamicIcon, isValidIcon } from "../DynamicIcon.js";
|
|
15
14
|
import { useNavigationCollapsibleState } from "./useNavigationCollapsibleState.js";
|
|
16
15
|
import { checkHasActiveItem, isLinkItem, isPathItem } from "./util.js";
|
|
17
16
|
|
|
@@ -82,7 +81,7 @@ export const SideNavigationItem = ({
|
|
|
82
81
|
const linkContent = (
|
|
83
82
|
<div className="flex justify-between w-full">
|
|
84
83
|
<div className="flex items-center gap-2 truncate w-full">
|
|
85
|
-
{
|
|
84
|
+
{item.icon}
|
|
86
85
|
{typeof item.label !== "string" ? (
|
|
87
86
|
item.label
|
|
88
87
|
) : (
|
|
@@ -14,12 +14,9 @@ import {
|
|
|
14
14
|
type NavigationPlugin,
|
|
15
15
|
} from "./plugins.js";
|
|
16
16
|
|
|
17
|
-
import type { LucideIcon } from "lucide-react";
|
|
18
|
-
import type { IconName } from "../components/DynamicIcon.js";
|
|
19
|
-
|
|
20
17
|
export interface ApiIdentity {
|
|
21
18
|
authorizeRequest: (request: Request) => Request;
|
|
22
|
-
|
|
19
|
+
label: string;
|
|
23
20
|
id: string;
|
|
24
21
|
}
|
|
25
22
|
|
|
@@ -27,7 +24,7 @@ type BaseNavigationCategoryItem = {
|
|
|
27
24
|
label: ReactNode;
|
|
28
25
|
title?: string;
|
|
29
26
|
muted?: boolean;
|
|
30
|
-
icon?: ReactNode
|
|
27
|
+
icon?: ReactNode;
|
|
31
28
|
};
|
|
32
29
|
|
|
33
30
|
export type PathNavigationCategoryItem = BaseNavigationCategoryItem & {
|
|
@@ -48,7 +45,7 @@ export type NavigationCategory = {
|
|
|
48
45
|
path?: string;
|
|
49
46
|
expanded?: boolean;
|
|
50
47
|
collapsible?: boolean;
|
|
51
|
-
icon?:
|
|
48
|
+
icon?: ReactNode;
|
|
52
49
|
children: NavigationCategoryItem[];
|
|
53
50
|
};
|
|
54
51
|
|
|
@@ -25,7 +25,7 @@ export const MakeRequest = ({
|
|
|
25
25
|
?.filter((p) => p.in === "header")
|
|
26
26
|
?.map((p) => ({
|
|
27
27
|
name: p.name,
|
|
28
|
-
value: "",
|
|
28
|
+
value: p.examples?.find((x) => x.value)?.value ?? "",
|
|
29
29
|
}));
|
|
30
30
|
const queryParams = operation.parameters
|
|
31
31
|
?.filter((p) => p.in === "query")
|
|
@@ -55,6 +55,7 @@ export const SchemaListView = ({
|
|
|
55
55
|
{Object.entries(groups).map(([group, properties]) => {
|
|
56
56
|
return (
|
|
57
57
|
<SchemaListViewItemGroup
|
|
58
|
+
key={group}
|
|
58
59
|
defaultOpen={defaultOpen}
|
|
59
60
|
group={group as any}
|
|
60
61
|
nestingLevel={level}
|
|
@@ -112,6 +113,7 @@ const SchemaListViewItemGroup = ({
|
|
|
112
113
|
<Collapsible.Content>
|
|
113
114
|
{properties.map(([propertyName, property]) => (
|
|
114
115
|
<SchemaListViewItem
|
|
116
|
+
key={propertyName}
|
|
115
117
|
property={property}
|
|
116
118
|
propertyName={propertyName}
|
|
117
119
|
nestingLevel={nestingLevel}
|
|
@@ -149,19 +151,16 @@ const SchemaListViewItem = ({
|
|
|
149
151
|
</code>
|
|
150
152
|
|
|
151
153
|
{property.type && (
|
|
152
|
-
<span className="text-muted-foreground">{property.type}</span>
|
|
154
|
+
<span className="text-xs text-muted-foreground">{property.type}</span>
|
|
153
155
|
)}
|
|
154
156
|
{property.deprecated && (
|
|
155
|
-
<span className="text-muted-foreground">Deprecated</span>
|
|
157
|
+
<span className="text-xs text-muted-foreground">Deprecated</span>
|
|
156
158
|
)}
|
|
157
159
|
{!isRequired && (
|
|
158
160
|
<span className="py-px px-1.5 font-medium text-xs border border-border rounded-lg">
|
|
159
161
|
optional {property.required}
|
|
160
162
|
</span>
|
|
161
163
|
)}
|
|
162
|
-
{/*{property.type === "object" && (*/}
|
|
163
|
-
{/* <div className="absolute right-3">+</div>*/}
|
|
164
|
-
{/*)}*/}
|
|
165
164
|
</div>
|
|
166
165
|
{property.description && (
|
|
167
166
|
<Markdown
|
|
@@ -15,7 +15,7 @@ import type { TypedDocumentNode as DocumentNode } from "@graphql-typed-document-
|
|
|
15
15
|
const documents = {
|
|
16
16
|
"\n query getServerQuery($input: JSON!, $type: SchemaType!) {\n schema(input: $input, type: $type) {\n url\n }\n }\n":
|
|
17
17
|
types.GetServerQueryDocument,
|
|
18
|
-
"\n fragment OperationsFragment on OperationItem {\n slug\n summary\n method\n description\n operationId\n contentTypes\n path\n parameters {\n name\n in\n description\n required\n schema\n style\n }\n requestBody {\n content {\n mediaType\n encoding {\n name\n }\n schema\n }\n description\n required\n }\n responses {\n statusCode\n links\n description\n content {\n mediaType\n encoding {\n name\n }\n schema\n }\n }\n }\n":
|
|
18
|
+
"\n fragment OperationsFragment on OperationItem {\n slug\n summary\n method\n description\n operationId\n contentTypes\n path\n parameters {\n name\n in\n description\n required\n schema\n style\n examples {\n name\n description\n externalValue\n value\n summary\n }\n }\n requestBody {\n content {\n mediaType\n encoding {\n name\n }\n schema\n }\n description\n required\n }\n responses {\n statusCode\n links\n description\n content {\n mediaType\n encoding {\n name\n }\n schema\n }\n }\n }\n":
|
|
19
19
|
types.OperationsFragmentFragmentDoc,
|
|
20
20
|
"\n query AllOperations($input: JSON!, $type: SchemaType!) {\n schema(input: $input, type: $type) {\n description\n title\n url\n version\n tags {\n name\n description\n operations {\n slug\n ...OperationsFragment\n }\n }\n }\n }\n":
|
|
21
21
|
types.AllOperationsDocument,
|
|
@@ -47,8 +47,8 @@ export function graphql(
|
|
|
47
47
|
* The graphql function is used to parse GraphQL queries into a document that can be used by GraphQL clients.
|
|
48
48
|
*/
|
|
49
49
|
export function graphql(
|
|
50
|
-
source: "\n fragment OperationsFragment on OperationItem {\n slug\n summary\n method\n description\n operationId\n contentTypes\n path\n parameters {\n name\n in\n description\n required\n schema\n style\n }\n requestBody {\n content {\n mediaType\n encoding {\n name\n }\n schema\n }\n description\n required\n }\n responses {\n statusCode\n links\n description\n content {\n mediaType\n encoding {\n name\n }\n schema\n }\n }\n }\n",
|
|
51
|
-
): (typeof documents)["\n fragment OperationsFragment on OperationItem {\n slug\n summary\n method\n description\n operationId\n contentTypes\n path\n parameters {\n name\n in\n description\n required\n schema\n style\n }\n requestBody {\n content {\n mediaType\n encoding {\n name\n }\n schema\n }\n description\n required\n }\n responses {\n statusCode\n links\n description\n content {\n mediaType\n encoding {\n name\n }\n schema\n }\n }\n }\n"];
|
|
50
|
+
source: "\n fragment OperationsFragment on OperationItem {\n slug\n summary\n method\n description\n operationId\n contentTypes\n path\n parameters {\n name\n in\n description\n required\n schema\n style\n examples {\n name\n description\n externalValue\n value\n summary\n }\n }\n requestBody {\n content {\n mediaType\n encoding {\n name\n }\n schema\n }\n description\n required\n }\n responses {\n statusCode\n links\n description\n content {\n mediaType\n encoding {\n name\n }\n schema\n }\n }\n }\n",
|
|
51
|
+
): (typeof documents)["\n fragment OperationsFragment on OperationItem {\n slug\n summary\n method\n description\n operationId\n contentTypes\n path\n parameters {\n name\n in\n description\n required\n schema\n style\n examples {\n name\n description\n externalValue\n value\n summary\n }\n }\n requestBody {\n content {\n mediaType\n encoding {\n name\n }\n schema\n }\n description\n required\n }\n responses {\n statusCode\n links\n description\n content {\n mediaType\n encoding {\n name\n }\n schema\n }\n }\n }\n"];
|
|
52
52
|
/**
|
|
53
53
|
* The graphql function is used to parse GraphQL queries into a document that can be used by GraphQL clients.
|
|
54
54
|
*/
|
|
@@ -190,6 +190,14 @@ export type OperationsFragmentFragment = {
|
|
|
190
190
|
required?: boolean | null;
|
|
191
191
|
schema?: any | null;
|
|
192
192
|
style?: string | null;
|
|
193
|
+
examples?: Array<{
|
|
194
|
+
__typename?: "ExampleItem";
|
|
195
|
+
name: string;
|
|
196
|
+
description?: string | null;
|
|
197
|
+
externalValue?: string | null;
|
|
198
|
+
value?: string | null;
|
|
199
|
+
summary?: string | null;
|
|
200
|
+
}> | null;
|
|
193
201
|
}> | null;
|
|
194
202
|
requestBody?: {
|
|
195
203
|
__typename?: "RequestBodyObject";
|
|
@@ -301,6 +309,29 @@ export const OperationsFragmentFragmentDoc = {
|
|
|
301
309
|
{ kind: "Field", name: { kind: "Name", value: "required" } },
|
|
302
310
|
{ kind: "Field", name: { kind: "Name", value: "schema" } },
|
|
303
311
|
{ kind: "Field", name: { kind: "Name", value: "style" } },
|
|
312
|
+
{
|
|
313
|
+
kind: "Field",
|
|
314
|
+
name: { kind: "Name", value: "examples" },
|
|
315
|
+
selectionSet: {
|
|
316
|
+
kind: "SelectionSet",
|
|
317
|
+
selections: [
|
|
318
|
+
{ kind: "Field", name: { kind: "Name", value: "name" } },
|
|
319
|
+
{
|
|
320
|
+
kind: "Field",
|
|
321
|
+
name: { kind: "Name", value: "description" },
|
|
322
|
+
},
|
|
323
|
+
{
|
|
324
|
+
kind: "Field",
|
|
325
|
+
name: { kind: "Name", value: "externalValue" },
|
|
326
|
+
},
|
|
327
|
+
{ kind: "Field", name: { kind: "Name", value: "value" } },
|
|
328
|
+
{
|
|
329
|
+
kind: "Field",
|
|
330
|
+
name: { kind: "Name", value: "summary" },
|
|
331
|
+
},
|
|
332
|
+
],
|
|
333
|
+
},
|
|
334
|
+
},
|
|
304
335
|
],
|
|
305
336
|
},
|
|
306
337
|
},
|
|
@@ -590,6 +621,29 @@ export const AllOperationsDocument = {
|
|
|
590
621
|
{ kind: "Field", name: { kind: "Name", value: "required" } },
|
|
591
622
|
{ kind: "Field", name: { kind: "Name", value: "schema" } },
|
|
592
623
|
{ kind: "Field", name: { kind: "Name", value: "style" } },
|
|
624
|
+
{
|
|
625
|
+
kind: "Field",
|
|
626
|
+
name: { kind: "Name", value: "examples" },
|
|
627
|
+
selectionSet: {
|
|
628
|
+
kind: "SelectionSet",
|
|
629
|
+
selections: [
|
|
630
|
+
{ kind: "Field", name: { kind: "Name", value: "name" } },
|
|
631
|
+
{
|
|
632
|
+
kind: "Field",
|
|
633
|
+
name: { kind: "Name", value: "description" },
|
|
634
|
+
},
|
|
635
|
+
{
|
|
636
|
+
kind: "Field",
|
|
637
|
+
name: { kind: "Name", value: "externalValue" },
|
|
638
|
+
},
|
|
639
|
+
{ kind: "Field", name: { kind: "Name", value: "value" } },
|
|
640
|
+
{
|
|
641
|
+
kind: "Field",
|
|
642
|
+
name: { kind: "Name", value: "summary" },
|
|
643
|
+
},
|
|
644
|
+
],
|
|
645
|
+
},
|
|
646
|
+
},
|
|
593
647
|
],
|
|
594
648
|
},
|
|
595
649
|
},
|
|
@@ -1,15 +1,13 @@
|
|
|
1
1
|
import {
|
|
2
2
|
Dialog,
|
|
3
3
|
DialogContent,
|
|
4
|
-
DialogDescription,
|
|
5
|
-
DialogHeader,
|
|
6
4
|
DialogTitle,
|
|
7
5
|
DialogTrigger,
|
|
8
6
|
} from "../../../components/Dialog.js";
|
|
9
|
-
import { Card
|
|
7
|
+
import { Card } from "../../../ui/Card.js";
|
|
10
8
|
import { Button } from "../../../ui/Button.js";
|
|
11
9
|
import { Tabs, TabsContent, TabsList, TabsTrigger } from "../../../ui/Tabs.js";
|
|
12
|
-
import { Fragment
|
|
10
|
+
import { Fragment } from "react";
|
|
13
11
|
import { SyntaxHighlight } from "../../../components/SyntaxHighlight.js";
|
|
14
12
|
import { ColorizedParam } from "../ColorizedParam.js";
|
|
15
13
|
import { useMutation } from "@tanstack/react-query";
|
|
@@ -17,11 +15,18 @@ import { FormProvider, useForm } from "react-hook-form";
|
|
|
17
15
|
import { Headers } from "./Headers.js";
|
|
18
16
|
import { QueryParams } from "./QueryParams.js";
|
|
19
17
|
import { PathParams } from "./PathParams.js";
|
|
20
|
-
import { CirclePlayIcon
|
|
18
|
+
import { CirclePlayIcon } from "lucide-react";
|
|
21
19
|
import { createUrl } from "./createUrl.js";
|
|
22
|
-
import { UrlDisplay } from "./UrlDisplay.js";
|
|
23
20
|
import { useApiIdentities } from "../../../components/context/DevPortalProvider.js";
|
|
24
21
|
import { Spinner } from "../../../components/Spinner.js";
|
|
22
|
+
import {
|
|
23
|
+
Select,
|
|
24
|
+
SelectContent,
|
|
25
|
+
SelectItem,
|
|
26
|
+
SelectTrigger,
|
|
27
|
+
SelectValue,
|
|
28
|
+
} from "../../../components/Select.js";
|
|
29
|
+
import { VisuallyHidden } from "@radix-ui/react-visually-hidden";
|
|
25
30
|
|
|
26
31
|
function mimeTypeToLanguage(mimeType: string) {
|
|
27
32
|
const mimeTypeMapping = {
|
|
@@ -72,8 +77,11 @@ export type PlaygroundForm = {
|
|
|
72
77
|
queryParams: QueryParam[];
|
|
73
78
|
pathParams: PathParam[];
|
|
74
79
|
headers: Header[];
|
|
80
|
+
identity?: string;
|
|
75
81
|
};
|
|
76
82
|
|
|
83
|
+
const NO_IDENTITY = "__none";
|
|
84
|
+
|
|
77
85
|
const Playground = ({
|
|
78
86
|
url,
|
|
79
87
|
host,
|
|
@@ -98,6 +106,7 @@ const Playground = ({
|
|
|
98
106
|
queryParams,
|
|
99
107
|
headers,
|
|
100
108
|
pathParams,
|
|
109
|
+
identity: NO_IDENTITY,
|
|
101
110
|
},
|
|
102
111
|
});
|
|
103
112
|
const formState = watch();
|
|
@@ -107,7 +116,8 @@ const Playground = ({
|
|
|
107
116
|
mutationFn: async (data: PlaygroundForm) => {
|
|
108
117
|
const requestUrl = createUrl(host, url, data);
|
|
109
118
|
const start = performance.now();
|
|
110
|
-
|
|
119
|
+
|
|
120
|
+
const request = new Request(requestUrl, {
|
|
111
121
|
method: method.toUpperCase(),
|
|
112
122
|
headers: Object.fromEntries(
|
|
113
123
|
data.pathParams
|
|
@@ -116,6 +126,14 @@ const Playground = ({
|
|
|
116
126
|
),
|
|
117
127
|
});
|
|
118
128
|
|
|
129
|
+
if (data.identity !== NO_IDENTITY) {
|
|
130
|
+
identities.data
|
|
131
|
+
?.find((i) => i.id === data.identity)
|
|
132
|
+
?.authorizeRequest(request);
|
|
133
|
+
}
|
|
134
|
+
|
|
135
|
+
const response = await fetch(request);
|
|
136
|
+
|
|
119
137
|
const body = await response.text();
|
|
120
138
|
|
|
121
139
|
return {
|
|
@@ -176,7 +194,13 @@ const Playground = ({
|
|
|
176
194
|
/>
|
|
177
195
|
</DialogTrigger>
|
|
178
196
|
|
|
179
|
-
<DialogContent
|
|
197
|
+
<DialogContent
|
|
198
|
+
className="max-w-screen-xl w-full h-5/6 overflow-auto p-0"
|
|
199
|
+
aria-describedby={undefined}
|
|
200
|
+
>
|
|
201
|
+
<VisuallyHidden>
|
|
202
|
+
<DialogTitle>Playground</DialogTitle>
|
|
203
|
+
</VisuallyHidden>
|
|
180
204
|
<FormProvider {...{ register, control, handleSubmit, watch, ...form }}>
|
|
181
205
|
<form
|
|
182
206
|
onSubmit={handleSubmit((data) => {
|
|
@@ -201,24 +225,47 @@ const Playground = ({
|
|
|
201
225
|
</Button>
|
|
202
226
|
</div>
|
|
203
227
|
<Tabs defaultValue={hasParams ? "parameters" : "headers"}>
|
|
204
|
-
<
|
|
205
|
-
|
|
206
|
-
|
|
207
|
-
|
|
208
|
-
<TabsTrigger value="headers">
|
|
209
|
-
Headers{" "}
|
|
210
|
-
{formState.headers.length > 0 &&
|
|
211
|
-
`(${formState.headers.length})`}
|
|
212
|
-
</TabsTrigger>
|
|
213
|
-
<TabsTrigger
|
|
214
|
-
value="body"
|
|
215
|
-
disabled={["POST", "PUT", "PATCH", "DELETE"].includes(
|
|
216
|
-
method.toUpperCase(),
|
|
228
|
+
<div className="flex justify-between">
|
|
229
|
+
<TabsList>
|
|
230
|
+
{hasParams && (
|
|
231
|
+
<TabsTrigger value="parameters">Parameters</TabsTrigger>
|
|
217
232
|
)}
|
|
218
|
-
|
|
219
|
-
|
|
220
|
-
|
|
221
|
-
|
|
233
|
+
<TabsTrigger value="headers">
|
|
234
|
+
Headers{" "}
|
|
235
|
+
{formState.headers.length > 0 &&
|
|
236
|
+
`(${formState.headers.length})`}
|
|
237
|
+
</TabsTrigger>
|
|
238
|
+
<TabsTrigger
|
|
239
|
+
value="body"
|
|
240
|
+
disabled={["POST", "PUT", "PATCH", "DELETE"].includes(
|
|
241
|
+
method.toUpperCase(),
|
|
242
|
+
)}
|
|
243
|
+
>
|
|
244
|
+
Body
|
|
245
|
+
</TabsTrigger>
|
|
246
|
+
</TabsList>
|
|
247
|
+
<div className="flex gap-2 items-center">
|
|
248
|
+
Auth:
|
|
249
|
+
<Select
|
|
250
|
+
onValueChange={(value) =>
|
|
251
|
+
form.setValue("identity", value)
|
|
252
|
+
}
|
|
253
|
+
defaultValue={formState.identity}
|
|
254
|
+
>
|
|
255
|
+
<SelectTrigger className="w-[180px]">
|
|
256
|
+
<SelectValue />
|
|
257
|
+
</SelectTrigger>
|
|
258
|
+
<SelectContent align="center">
|
|
259
|
+
<SelectItem value={NO_IDENTITY}>None</SelectItem>
|
|
260
|
+
{identities.data?.map((identity) => (
|
|
261
|
+
<SelectItem key={identity.id} value={identity.id}>
|
|
262
|
+
{identity.label}
|
|
263
|
+
</SelectItem>
|
|
264
|
+
))}
|
|
265
|
+
</SelectContent>
|
|
266
|
+
</Select>
|
|
267
|
+
</div>
|
|
268
|
+
</div>
|
|
222
269
|
<TabsContent value="headers">
|
|
223
270
|
<Headers
|
|
224
271
|
control={control}
|
|
@@ -20,9 +20,6 @@ const QueryParamActive = ({
|
|
|
20
20
|
const value = useWatch({ control, name: `queryParams.${i}.value` });
|
|
21
21
|
const active = useWatch({ control, name: `queryParams.${i}.active` });
|
|
22
22
|
const form = useFormContext<PlaygroundForm>();
|
|
23
|
-
const dirty = form.formState.dirtyFields;
|
|
24
|
-
|
|
25
|
-
console.log("dirty fields", dirty);
|
|
26
23
|
|
|
27
24
|
useEffect(() => {
|
|
28
25
|
if (value) {
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"DynamicIcon.js","sourceRoot":"","sources":["../../../src/lib/components/DynamicIcon.tsx"],"names":[],"mappings":";AAqDA,MAAM,UAAU,WAAW,CAAC,IAAa;IACvC,OAAO,IAAI,CAAC;AACd,CAAC;AAED,MAAM,CAAC,MAAM,WAAW,GAAG,CAAC,KAAsC,EAAE,EAAE,CAAC,CACrE,eAAW,CACZ,CAAC"}
|
|
@@ -1,60 +0,0 @@
|
|
|
1
|
-
// import { type LucideProps } from "lucide-react";
|
|
2
|
-
// import dynamicIconImports from "lucide-react/dynamicIconImports.js";
|
|
3
|
-
// import { Suspense, lazy, memo } from "react";
|
|
4
|
-
// import { cn } from "../util/cn.js";
|
|
5
|
-
|
|
6
|
-
// export type IconName = keyof typeof dynamicIconImports;
|
|
7
|
-
|
|
8
|
-
// const IconNames = Object.keys(dynamicIconImports) as IconName[];
|
|
9
|
-
|
|
10
|
-
// export const isValidIcon = (name: unknown): name is IconName =>
|
|
11
|
-
// typeof name === "string" && IconNames.includes(name as IconName);
|
|
12
|
-
|
|
13
|
-
// type IconProps = Omit<LucideProps, "ref"> & {
|
|
14
|
-
// name: IconName;
|
|
15
|
-
// inline?: boolean;
|
|
16
|
-
// };
|
|
17
|
-
|
|
18
|
-
// const Fallback = ({
|
|
19
|
-
// inline,
|
|
20
|
-
// size,
|
|
21
|
-
// }: {
|
|
22
|
-
// inline?: boolean;
|
|
23
|
-
// size?: string | number;
|
|
24
|
-
// }) => (
|
|
25
|
-
// <span
|
|
26
|
-
// className={cn(inline ? "inline-block" : "block", "bg-background")}
|
|
27
|
-
// style={{ height: size, width: size }}
|
|
28
|
-
// role="presentation"
|
|
29
|
-
// />
|
|
30
|
-
// );
|
|
31
|
-
|
|
32
|
-
// export const DynamicIcon = memo(function ({
|
|
33
|
-
// name,
|
|
34
|
-
// inline,
|
|
35
|
-
// className,
|
|
36
|
-
// size = 16,
|
|
37
|
-
// ...props
|
|
38
|
-
// }: IconProps) {
|
|
39
|
-
// const LucideIcon = lazy(dynamicIconImports[name]);
|
|
40
|
-
|
|
41
|
-
// return (
|
|
42
|
-
// <Suspense fallback={<Fallback inline={inline} size={size} />}>
|
|
43
|
-
// <LucideIcon
|
|
44
|
-
// {...props}
|
|
45
|
-
// size={size}
|
|
46
|
-
// className={cn(inline && "inline-block align-[-0.125em]", className)}
|
|
47
|
-
// />
|
|
48
|
-
// </Suspense>
|
|
49
|
-
// );
|
|
50
|
-
// });
|
|
51
|
-
|
|
52
|
-
export type IconName = string;
|
|
53
|
-
|
|
54
|
-
export function isValidIcon(name: unknown): name is IconName {
|
|
55
|
-
return true;
|
|
56
|
-
}
|
|
57
|
-
|
|
58
|
-
export const DynamicIcon = (props: { name: string; size?: number }) => (
|
|
59
|
-
<div></div>
|
|
60
|
-
);
|