@flanksource/clicky-ui 0.2.12 → 0.2.14
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/components/Combobox.cjs +47 -33
- package/dist/components/Combobox.cjs.map +1 -1
- package/dist/components/Combobox.d.ts +12 -0
- package/dist/components/Combobox.d.ts.map +1 -1
- package/dist/components/Combobox.js +48 -34
- package/dist/components/Combobox.js.map +1 -1
- package/dist/components/IconButton.cjs +26 -0
- package/dist/components/IconButton.cjs.map +1 -0
- package/dist/components/IconButton.d.ts +25 -0
- package/dist/components/IconButton.d.ts.map +1 -0
- package/dist/components/IconButton.js +26 -0
- package/dist/components/IconButton.js.map +1 -0
- package/dist/components/SecretKeySelector.cjs +151 -0
- package/dist/components/SecretKeySelector.cjs.map +1 -0
- package/dist/components/SecretKeySelector.d.ts +51 -0
- package/dist/components/SecretKeySelector.d.ts.map +1 -0
- package/dist/components/SecretKeySelector.js +151 -0
- package/dist/components/SecretKeySelector.js.map +1 -0
- package/dist/components/WorkloadPicker.cjs +144 -0
- package/dist/components/WorkloadPicker.cjs.map +1 -0
- package/dist/components/WorkloadPicker.d.ts +52 -0
- package/dist/components/WorkloadPicker.d.ts.map +1 -0
- package/dist/components/WorkloadPicker.js +144 -0
- package/dist/components/WorkloadPicker.js.map +1 -0
- package/dist/components/icon-menu-picker.cjs +83 -112
- package/dist/components/icon-menu-picker.cjs.map +1 -1
- package/dist/components/icon-menu-picker.d.ts.map +1 -1
- package/dist/components/icon-menu-picker.js +85 -114
- package/dist/components/icon-menu-picker.js.map +1 -1
- package/dist/components.cjs +10 -0
- package/dist/components.cjs.map +1 -1
- package/dist/components.d.ts +3 -0
- package/dist/components.d.ts.map +1 -1
- package/dist/components.js +11 -1
- package/dist/components.js.map +1 -1
- package/dist/data/Clicky.cjs +1 -1
- package/dist/data/Clicky.cjs.map +1 -1
- package/dist/data/Clicky.js +1 -1
- package/dist/data/Clicky.js.map +1 -1
- package/dist/data/TimeseriesCoreBars.cjs +8 -1
- package/dist/data/TimeseriesCoreBars.cjs.map +1 -1
- package/dist/data/TimeseriesCoreBars.d.ts.map +1 -1
- package/dist/data/TimeseriesCoreBars.js +8 -1
- package/dist/data/TimeseriesCoreBars.js.map +1 -1
- package/dist/data/Version.cjs +42 -0
- package/dist/data/Version.cjs.map +1 -0
- package/dist/data/Version.d.ts +36 -0
- package/dist/data/Version.d.ts.map +1 -0
- package/dist/data/Version.js +42 -0
- package/dist/data/Version.js.map +1 -0
- package/dist/data/test-runner/TestDetailPanel.cjs +165 -0
- package/dist/data/test-runner/TestDetailPanel.cjs.map +1 -0
- package/dist/data/test-runner/TestDetailPanel.d.ts +7 -0
- package/dist/data/test-runner/TestDetailPanel.d.ts.map +1 -0
- package/dist/data/test-runner/TestDetailPanel.js +165 -0
- package/dist/data/test-runner/TestDetailPanel.js.map +1 -0
- package/dist/data/test-runner/TestFailureDetail.cjs +78 -0
- package/dist/data/test-runner/TestFailureDetail.cjs.map +1 -0
- package/dist/data/test-runner/TestFailureDetail.d.ts +14 -0
- package/dist/data/test-runner/TestFailureDetail.d.ts.map +1 -0
- package/dist/data/test-runner/TestFailureDetail.js +78 -0
- package/dist/data/test-runner/TestFailureDetail.js.map +1 -0
- package/dist/data/test-runner/TestFilterBar.cjs +108 -0
- package/dist/data/test-runner/TestFilterBar.cjs.map +1 -0
- package/dist/data/test-runner/TestFilterBar.d.ts +15 -0
- package/dist/data/test-runner/TestFilterBar.d.ts.map +1 -0
- package/dist/data/test-runner/TestFilterBar.js +108 -0
- package/dist/data/test-runner/TestFilterBar.js.map +1 -0
- package/dist/data/test-runner/TestRunSummary.cjs +81 -0
- package/dist/data/test-runner/TestRunSummary.cjs.map +1 -0
- package/dist/data/test-runner/TestRunSummary.d.ts +19 -0
- package/dist/data/test-runner/TestRunSummary.d.ts.map +1 -0
- package/dist/data/test-runner/TestRunSummary.js +81 -0
- package/dist/data/test-runner/TestRunSummary.js.map +1 -0
- package/dist/data/test-runner/TestRunner.cjs +143 -0
- package/dist/data/test-runner/TestRunner.cjs.map +1 -0
- package/dist/data/test-runner/TestRunner.d.ts +42 -0
- package/dist/data/test-runner/TestRunner.d.ts.map +1 -0
- package/dist/data/test-runner/TestRunner.fixtures.d.ts +26 -0
- package/dist/data/test-runner/TestRunner.fixtures.d.ts.map +1 -0
- package/dist/data/test-runner/TestRunner.js +143 -0
- package/dist/data/test-runner/TestRunner.js.map +1 -0
- package/dist/data/test-runner/TestTree.cjs +42 -0
- package/dist/data/test-runner/TestTree.cjs.map +1 -0
- package/dist/data/test-runner/TestTree.d.ts +9 -0
- package/dist/data/test-runner/TestTree.d.ts.map +1 -0
- package/dist/data/test-runner/TestTree.js +42 -0
- package/dist/data/test-runner/TestTree.js.map +1 -0
- package/dist/data/test-runner/TestTreeNode.cjs +99 -0
- package/dist/data/test-runner/TestTreeNode.cjs.map +1 -0
- package/dist/data/test-runner/TestTreeNode.d.ts +12 -0
- package/dist/data/test-runner/TestTreeNode.d.ts.map +1 -0
- package/dist/data/test-runner/TestTreeNode.js +99 -0
- package/dist/data/test-runner/TestTreeNode.js.map +1 -0
- package/dist/data/test-runner/adapter.cjs +57 -0
- package/dist/data/test-runner/adapter.cjs.map +1 -0
- package/dist/data/test-runner/adapter.d.ts +60 -0
- package/dist/data/test-runner/adapter.d.ts.map +1 -0
- package/dist/data/test-runner/adapter.js +57 -0
- package/dist/data/test-runner/adapter.js.map +1 -0
- package/dist/data/test-runner/context.cjs +15 -0
- package/dist/data/test-runner/context.cjs.map +1 -0
- package/dist/data/test-runner/context.d.ts +40 -0
- package/dist/data/test-runner/context.d.ts.map +1 -0
- package/dist/data/test-runner/context.js +15 -0
- package/dist/data/test-runner/context.js.map +1 -0
- package/dist/data/test-runner/filterState.cjs +47 -0
- package/dist/data/test-runner/filterState.cjs.map +1 -0
- package/dist/data/test-runner/filterState.d.ts +14 -0
- package/dist/data/test-runner/filterState.d.ts.map +1 -0
- package/dist/data/test-runner/filterState.js +47 -0
- package/dist/data/test-runner/filterState.js.map +1 -0
- package/dist/data/test-runner/frameworkIcon.cjs +27 -0
- package/dist/data/test-runner/frameworkIcon.cjs.map +1 -0
- package/dist/data/test-runner/frameworkIcon.d.ts +3 -0
- package/dist/data/test-runner/frameworkIcon.d.ts.map +1 -0
- package/dist/data/test-runner/frameworkIcon.js +27 -0
- package/dist/data/test-runner/frameworkIcon.js.map +1 -0
- package/dist/data/test-runner/index.d.ts +14 -0
- package/dist/data/test-runner/index.d.ts.map +1 -0
- package/dist/data/test-runner/status.cjs +234 -0
- package/dist/data/test-runner/status.cjs.map +1 -0
- package/dist/data/test-runner/status.d.ts +52 -0
- package/dist/data/test-runner/status.d.ts.map +1 -0
- package/dist/data/test-runner/status.js +234 -0
- package/dist/data/test-runner/status.js.map +1 -0
- package/dist/data/test-runner/types.d.ts +148 -0
- package/dist/data/test-runner/types.d.ts.map +1 -0
- package/dist/data/version-info.cjs +26 -0
- package/dist/data/version-info.cjs.map +1 -0
- package/dist/data/version-info.d.ts +11 -0
- package/dist/data/version-info.d.ts.map +1 -0
- package/dist/data/version-info.js +26 -0
- package/dist/data/version-info.js.map +1 -0
- package/dist/data.cjs +49 -0
- package/dist/data.cjs.map +1 -1
- package/dist/data.d.ts +3 -0
- package/dist/data.d.ts.map +1 -1
- package/dist/data.js +50 -1
- package/dist/data.js.map +1 -1
- package/dist/index.cjs +59 -0
- package/dist/index.cjs.map +1 -1
- package/dist/index.js +60 -1
- package/dist/index.js.map +1 -1
- package/dist/overlay/DropdownMenu.cjs +57 -30
- package/dist/overlay/DropdownMenu.cjs.map +1 -1
- package/dist/overlay/DropdownMenu.d.ts.map +1 -1
- package/dist/overlay/DropdownMenu.js +57 -30
- package/dist/overlay/DropdownMenu.js.map +1 -1
- package/dist/overlay/Modal.cjs +62 -6
- package/dist/overlay/Modal.cjs.map +1 -1
- package/dist/overlay/Modal.d.ts +19 -1
- package/dist/overlay/Modal.d.ts.map +1 -1
- package/dist/overlay/Modal.js +62 -6
- package/dist/overlay/Modal.js.map +1 -1
- package/dist/rpc/CommandForm.cjs +2 -2
- package/dist/rpc/CommandForm.cjs.map +1 -1
- package/dist/rpc/CommandForm.d.ts.map +1 -1
- package/dist/rpc/CommandForm.js +3 -3
- package/dist/rpc/CommandForm.js.map +1 -1
- package/dist/rpc/formMetadata.cjs +5 -4
- package/dist/rpc/formMetadata.cjs.map +1 -1
- package/dist/rpc/formMetadata.d.ts.map +1 -1
- package/dist/rpc/formMetadata.js +6 -5
- package/dist/rpc/formMetadata.js.map +1 -1
- package/dist/rpc/types.cjs +4 -0
- package/dist/rpc/types.cjs.map +1 -1
- package/dist/rpc/types.d.ts +10 -0
- package/dist/rpc/types.d.ts.map +1 -1
- package/dist/rpc/types.js +5 -1
- package/dist/rpc/types.js.map +1 -1
- package/dist/styles.css +1 -1
- package/package.json +3 -1
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"CommandForm.js","sources":["../../src/rpc/CommandForm.tsx"],"sourcesContent":["import { useReducer, type FormEvent, type KeyboardEvent, type ReactNode } from \"react\";\nimport { Button } from \"../components/button\";\nimport { Icon } from \"../data/Icon\";\nimport { UiClose } from \"../icons\";\nimport { isPositionalParam, type OpenAPIParameter } from \"./types\";\n\nexport type CommandFormProps = {\n parameters: OpenAPIParameter[];\n onExecute: (params: Record<string, string>, headers: Record<string, string>) => void;\n isPending: boolean;\n method: string;\n path: string;\n accept: string;\n initialValues?: Record<string, string>;\n};\n\ntype FormState = Record<string, string>;\ntype FormAction = { name: string; value: string };\n\nfunction formReducer(state: FormState, action: FormAction): FormState {\n return { ...state, [action.name]: action.value };\n}\n\nexport function CommandForm({\n parameters,\n onExecute,\n isPending,\n method: _method,\n path,\n accept,\n initialValues,\n}: CommandFormProps) {\n const [values, dispatch] = useReducer(\n formReducer,\n { parameters, path, initialValues },\n ({ parameters: params, path: formPath, initialValues: overrides }) =>\n buildInitialState(normalizeParameters(params, formPath), formPath, overrides),\n );\n\n const formParameters = normalizeParameters(parameters, path);\n const visibleParams = formParameters.filter((p) => !(p.in === \"path\" && initialValues?.[p.name]));\n const positionalNames = new Set(formParameters.filter(isPositionalParam).map((p) => p.name));\n const inlineLayout = visibleParams.length >= INLINE_LAYOUT_THRESHOLD;\n\n function handleSubmit(event: FormEvent) {\n event.preventDefault();\n const params: Record<string, string> = {};\n const args: string[] = [];\n for (const param of formParameters) {\n const value = submitValue(param, values[param.name]);\n if (value == null) continue;\n if (positionalNames.has(param.name)) {\n args.push(...splitArgsValue(value));\n } else {\n params[param.name] = value;\n }\n }\n if (args.length > 0) params.args = args.join(\",\");\n onExecute(params, { Accept: accept });\n }\n\n return (\n <form onSubmit={handleSubmit} className=\"space-y-4\">\n {visibleParams.length > 0 && (\n <div className={inlineLayout ? \"grid gap-2\" : \"grid gap-4\"}>\n {visibleParams.map((param) => (\n <ParameterField\n key={param.name}\n param={param}\n value={values[param.name] || \"\"}\n inline={inlineLayout}\n onChange={(value) => dispatch({ name: param.name, value })}\n />\n ))}\n </div>\n )}\n\n <div\n className={\n inlineLayout\n ? \"sticky bottom-0 z-10 -mx-2 flex justify-end border-t border-border bg-background/95 px-2 py-3 backdrop-blur-sm\"\n : \"flex justify-end\"\n }\n >\n <Button type=\"submit\" disabled={isPending}>\n {isPending ? \"Executing...\" : \"Execute\"}\n </Button>\n </div>\n </form>\n );\n}\n\nconst INLINE_LAYOUT_THRESHOLD = 6;\n\nfunction ParameterField({\n param,\n value,\n inline,\n onChange,\n}: {\n param: OpenAPIParameter;\n value: string;\n inline: boolean;\n onChange: (value: string) => void;\n}) {\n const schema = param.schema;\n const fieldId = `param-${param.name}`;\n\n if (isMultiValueParam(param)) {\n return (\n <FieldWrapper param={param} fieldId={fieldId} inline={inline}>\n <TagInput\n id={fieldId}\n value={value}\n placeholder={param.description || param.name}\n onChange={onChange}\n />\n </FieldWrapper>\n );\n }\n\n if (schema?.enum) {\n return (\n <FieldWrapper param={param} fieldId={fieldId} inline={inline}>\n <select\n id={fieldId}\n value={value}\n className={inputClassName}\n onChange={(event) => onChange(event.target.value)}\n >\n <option value=\"\">Select {param.name}</option>\n {schema.enum.map((v) => (\n <option key={String(v)} value={String(v)}>\n {String(v)}\n </option>\n ))}\n </select>\n </FieldWrapper>\n );\n }\n\n if (schema?.type === \"boolean\") {\n const checkbox = (\n <input\n id={fieldId}\n type=\"checkbox\"\n className=\"h-4 w-4 accent-primary\"\n checked={value === \"true\"}\n onChange={(event) => onChange(event.target.checked ? \"true\" : \"false\")}\n />\n );\n if (inline) {\n return (\n <FieldWrapper param={param} fieldId={fieldId} inline>\n <div className=\"flex h-9 items-center\">{checkbox}</div>\n </FieldWrapper>\n );\n }\n return (\n <div className=\"flex items-center gap-2\">\n {checkbox}\n <label htmlFor={fieldId} className=\"text-sm font-medium\">\n {param.name}\n {param.required && <span className=\"text-destructive\"> *</span>}\n </label>\n {param.description && (\n <span className=\"text-xs text-muted-foreground\">{param.description}</span>\n )}\n </div>\n );\n }\n\n if (isDateParam(param)) {\n const dateTime = schema?.format === \"date-time\";\n return (\n <FieldWrapper param={param} fieldId={fieldId} inline={inline}>\n <div className=\"flex gap-2\">\n <input\n id={fieldId}\n type={dateTime ? \"datetime-local\" : \"date\"}\n value={dateInputValue(value, dateTime)}\n className={inputClassName}\n onChange={(event) => onChange(dateOutputValue(event.target.value, dateTime))}\n />\n {value && (\n <Button\n type=\"button\"\n variant=\"outline\"\n size=\"sm\"\n aria-label={`Clear ${param.name}`}\n onClick={() => onChange(\"\")}\n >\n <Icon icon={UiClose} />\n </Button>\n )}\n </div>\n </FieldWrapper>\n );\n }\n\n const inputType = schema?.type === \"integer\" || schema?.type === \"number\" ? \"number\" : \"text\";\n\n return (\n <FieldWrapper param={param} fieldId={fieldId} inline={inline}>\n <input\n id={fieldId}\n type={inputType}\n value={value}\n className={inputClassName}\n onChange={(event) => onChange(event.target.value)}\n placeholder={\n schema?.default != null ? String(schema.default) : param.description || param.name\n }\n />\n </FieldWrapper>\n );\n}\n\nfunction TagInput({\n id,\n value,\n placeholder,\n onChange,\n}: {\n id: string;\n value: string;\n placeholder: string;\n onChange: (value: string) => void;\n}) {\n const tags = parseTags(value);\n\n function commit(raw: string, input: HTMLInputElement) {\n const next = raw\n .split(\",\")\n .map((part) => part.trim())\n .filter(Boolean);\n if (next.length === 0) return;\n onChange(serializeTags([...tags, ...next]));\n input.value = \"\";\n }\n\n function remove(index: number) {\n onChange(serializeTags(tags.filter((_, i) => i !== index)));\n }\n\n function handleKeyDown(event: KeyboardEvent<HTMLInputElement>) {\n const input = event.currentTarget;\n if (event.key === \"Enter\" || event.key === \",\") {\n event.preventDefault();\n commit(input.value, input);\n return;\n }\n if (event.key === \"Backspace\" && input.value === \"\" && tags.length > 0) {\n remove(tags.length - 1);\n }\n }\n\n return (\n <div className=\"flex min-h-9 flex-wrap items-center gap-1.5 rounded-md border border-input bg-transparent px-2 py-1 shadow-sm\">\n {tags.map((tag, index) => (\n <span\n key={`${tag}-${index}`}\n className=\"inline-flex h-6 max-w-full items-center gap-1 rounded-md bg-muted px-2 text-xs\"\n >\n <span className=\"truncate\">{tag}</span>\n <button\n type=\"button\"\n className=\"text-muted-foreground hover:text-foreground\"\n aria-label={`Remove ${tag}`}\n onClick={() => remove(index)}\n >\n <Icon icon={UiClose} />\n </button>\n </span>\n ))}\n <input\n id={id}\n className=\"min-w-32 flex-1 bg-transparent px-1 py-1 text-sm outline-none\"\n placeholder={tags.length === 0 ? placeholder : \"\"}\n onKeyDown={handleKeyDown}\n onBlur={(event) => commit(event.currentTarget.value, event.currentTarget)}\n />\n </div>\n );\n}\n\nfunction FieldWrapper({\n param,\n fieldId,\n inline,\n children,\n}: {\n param: OpenAPIParameter;\n fieldId: string;\n inline?: boolean;\n children: ReactNode;\n}) {\n const label = (\n <label htmlFor={fieldId} className=\"text-sm font-medium\">\n {param.name}\n {param.required && <span className=\"text-destructive\"> *</span>}\n </label>\n );\n\n if (inline) {\n return (\n <div className=\"grid grid-cols-[10rem_1fr] items-start gap-x-3 gap-y-0.5\">\n <div className=\"flex h-9 items-center\">{label}</div>\n <div className=\"min-w-0\">{children}</div>\n {param.description && (\n <p className=\"col-start-2 text-xs text-muted-foreground\">{param.description}</p>\n )}\n </div>\n );\n }\n\n return (\n <div className=\"space-y-1.5\">\n {label}\n {children}\n {param.description && <p className=\"text-xs text-muted-foreground\">{param.description}</p>}\n </div>\n );\n}\n\nexport function normalizeParameters(\n parameters: OpenAPIParameter[],\n path: string,\n): OpenAPIParameter[] {\n const pathParams = pathParamNames(path);\n const firstPathParam = pathParams[0];\n const seen = new Set(parameters.map((param) => param.name));\n const normalized = parameters.filter(\n (param) => !(param.name === \"args\" && firstPathParam != null && !seen.has(firstPathParam)),\n );\n for (const name of pathParams) {\n if (seen.has(name)) continue;\n normalized.unshift({\n name,\n in: \"path\",\n required: true,\n description: \"Path parameter\",\n schema: { type: \"string\" },\n });\n }\n return normalized;\n}\n\nexport function pathParamNames(path: string): string[] {\n return [...path.matchAll(/\\{([^}]+)\\}/g)]\n .map((match) => match[1])\n .filter((name): name is string => Boolean(name));\n}\n\nfunction buildInitialState(\n parameters: OpenAPIParameter[],\n path: string,\n overrides?: Record<string, string>,\n): FormState {\n const state: FormState = {};\n for (const p of parameters) {\n state[p.name] = initialParamValue(p, overrides?.[p.name]);\n }\n for (const name of pathParamNames(path)) {\n if (state[name] == null) {\n state[name] = overrides?.[name] ?? \"\";\n }\n }\n return state;\n}\n\nfunction initialParamValue(param: OpenAPIParameter, override: string | undefined): string {\n if (override != null) return sanitizeInitialValue(param, override);\n const value = param.schema?.default;\n if (value == null) return \"\";\n return sanitizeInitialValue(param, String(value));\n}\n\nfunction sanitizeInitialValue(param: OpenAPIParameter, value: string): string {\n const trimmed = value.trim();\n if (trimmed === \"[]\" || trimmed === \"null\") return \"\";\n if (isDateParam(param) && isZeroDate(trimmed)) return \"\";\n return value;\n}\n\nexport function submitValue(param: OpenAPIParameter, value: string | undefined): string | null {\n const trimmed = (value ?? \"\").trim();\n if (!trimmed || trimmed === \"[]\" || trimmed === \"null\") return null;\n if (isDateParam(param) && isZeroDate(trimmed)) return null;\n return trimmed;\n}\n\nfunction splitArgsValue(value: string): string[] {\n try {\n const parsed = JSON.parse(value);\n if (Array.isArray(parsed)) return parsed.map(String).filter(Boolean);\n } catch {\n // Use comma splitting below.\n }\n return value\n .split(\",\")\n .map((part) => part.trim())\n .filter(Boolean);\n}\n\nfunction isMultiValueParam(param: OpenAPIParameter): boolean {\n const text = `${param.name} ${param.description ?? \"\"}`.toLowerCase();\n return (\n param.schema?.type === \"array\" ||\n String(param.schema?.default ?? \"\") === \"[]\" ||\n text.includes(\"repeatable\")\n );\n}\n\nfunction parseTags(value: string): string[] {\n const trimmed = value.trim();\n if (!trimmed || trimmed === \"[]\" || trimmed === \"null\") return [];\n try {\n const parsed = JSON.parse(trimmed);\n if (Array.isArray(parsed)) return parsed.map(String).filter(Boolean);\n } catch {\n // Fall back to comma-delimited tags below.\n }\n return trimmed\n .split(\",\")\n .map((part) => part.trim())\n .filter(Boolean);\n}\n\nfunction serializeTags(tags: string[]): string {\n return tags.join(\",\");\n}\n\nfunction isDateParam(param: OpenAPIParameter): boolean {\n const format = param.schema?.format?.toLowerCase();\n const text = `${param.name} ${param.description ?? \"\"}`.toLowerCase();\n return format === \"date\" || format === \"date-time\" || text.includes(\"date\");\n}\n\nfunction isZeroDate(value: string): boolean {\n return value.startsWith(\"0001-01-01\") || value === \"0001-01-01\";\n}\n\nfunction dateInputValue(value: string, dateTime: boolean): string {\n if (!value || value.startsWith(\"0001-01-01\")) return \"\";\n if (!dateTime) return value.slice(0, 10);\n const parsed = new Date(value);\n if (Number.isNaN(parsed.getTime())) return value.slice(0, 16);\n const offset = parsed.getTimezoneOffset() * 60_000;\n return new Date(parsed.getTime() - offset).toISOString().slice(0, 16);\n}\n\nfunction dateOutputValue(value: string, dateTime: boolean): string {\n if (!value) return \"\";\n if (!dateTime) return value;\n const parsed = new Date(value);\n if (Number.isNaN(parsed.getTime())) return value;\n return parsed.toISOString();\n}\n\nconst inputClassName =\n \"h-9 w-full min-w-0 rounded-md border border-input bg-background px-2 text-sm text-foreground outline-none placeholder:text-muted-foreground disabled:cursor-not-allowed disabled:bg-muted/40 focus-visible:ring-2 focus-visible:ring-ring\";\n"],"names":[],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"CommandForm.js","sources":["../../src/rpc/CommandForm.tsx"],"sourcesContent":["import { useReducer, type FormEvent, type KeyboardEvent, type ReactNode } from \"react\";\nimport { Button } from \"../components/button\";\nimport { Icon } from \"../data/Icon\";\nimport { UiClose } from \"../icons\";\nimport {\n isPositionalParam,\n parameterPlaceholder,\n type OpenAPIParameter,\n} from \"./types\";\n\nexport type CommandFormProps = {\n parameters: OpenAPIParameter[];\n onExecute: (params: Record<string, string>, headers: Record<string, string>) => void;\n isPending: boolean;\n method: string;\n path: string;\n accept: string;\n initialValues?: Record<string, string>;\n};\n\ntype FormState = Record<string, string>;\ntype FormAction = { name: string; value: string };\n\nfunction formReducer(state: FormState, action: FormAction): FormState {\n return { ...state, [action.name]: action.value };\n}\n\nexport function CommandForm({\n parameters,\n onExecute,\n isPending,\n method: _method,\n path,\n accept,\n initialValues,\n}: CommandFormProps) {\n const [values, dispatch] = useReducer(\n formReducer,\n { parameters, path, initialValues },\n ({ parameters: params, path: formPath, initialValues: overrides }) =>\n buildInitialState(normalizeParameters(params, formPath), formPath, overrides),\n );\n\n const formParameters = normalizeParameters(parameters, path);\n const visibleParams = formParameters.filter((p) => !(p.in === \"path\" && initialValues?.[p.name]));\n const positionalNames = new Set(formParameters.filter(isPositionalParam).map((p) => p.name));\n const inlineLayout = visibleParams.length >= INLINE_LAYOUT_THRESHOLD;\n\n function handleSubmit(event: FormEvent) {\n event.preventDefault();\n const params: Record<string, string> = {};\n const args: string[] = [];\n for (const param of formParameters) {\n const value = submitValue(param, values[param.name]);\n if (value == null) continue;\n if (positionalNames.has(param.name)) {\n args.push(...splitArgsValue(value));\n } else {\n params[param.name] = value;\n }\n }\n if (args.length > 0) params.args = args.join(\",\");\n onExecute(params, { Accept: accept });\n }\n\n return (\n <form onSubmit={handleSubmit} className=\"space-y-4\">\n {visibleParams.length > 0 && (\n <div className={inlineLayout ? \"grid gap-2\" : \"grid gap-4\"}>\n {visibleParams.map((param) => (\n <ParameterField\n key={param.name}\n param={param}\n value={values[param.name] || \"\"}\n inline={inlineLayout}\n onChange={(value) => dispatch({ name: param.name, value })}\n />\n ))}\n </div>\n )}\n\n <div\n className={\n inlineLayout\n ? \"sticky bottom-0 z-10 -mx-2 flex justify-end border-t border-border bg-background/95 px-2 py-3 backdrop-blur-sm\"\n : \"flex justify-end\"\n }\n >\n <Button type=\"submit\" disabled={isPending}>\n {isPending ? \"Executing...\" : \"Execute\"}\n </Button>\n </div>\n </form>\n );\n}\n\nconst INLINE_LAYOUT_THRESHOLD = 6;\n\nfunction ParameterField({\n param,\n value,\n inline,\n onChange,\n}: {\n param: OpenAPIParameter;\n value: string;\n inline: boolean;\n onChange: (value: string) => void;\n}) {\n const schema = param.schema;\n const fieldId = `param-${param.name}`;\n\n if (isMultiValueParam(param)) {\n return (\n <FieldWrapper param={param} fieldId={fieldId} inline={inline}>\n <TagInput\n id={fieldId}\n value={value}\n placeholder={parameterPlaceholder(param) || param.name}\n onChange={onChange}\n />\n </FieldWrapper>\n );\n }\n\n if (schema?.enum) {\n return (\n <FieldWrapper param={param} fieldId={fieldId} inline={inline}>\n <select\n id={fieldId}\n value={value}\n className={inputClassName}\n onChange={(event) => onChange(event.target.value)}\n >\n <option value=\"\">Select {param.name}</option>\n {schema.enum.map((v) => (\n <option key={String(v)} value={String(v)}>\n {String(v)}\n </option>\n ))}\n </select>\n </FieldWrapper>\n );\n }\n\n if (schema?.type === \"boolean\") {\n const checkbox = (\n <input\n id={fieldId}\n type=\"checkbox\"\n className=\"h-4 w-4 accent-primary\"\n checked={value === \"true\"}\n onChange={(event) => onChange(event.target.checked ? \"true\" : \"false\")}\n />\n );\n if (inline) {\n return (\n <FieldWrapper param={param} fieldId={fieldId} inline>\n <div className=\"flex h-9 items-center\">{checkbox}</div>\n </FieldWrapper>\n );\n }\n return (\n <div className=\"flex items-center gap-2\">\n {checkbox}\n <label htmlFor={fieldId} className=\"text-sm font-medium\">\n {param.name}\n {param.required && <span className=\"text-destructive\"> *</span>}\n </label>\n {param.description && (\n <span className=\"text-xs text-muted-foreground\">{param.description}</span>\n )}\n </div>\n );\n }\n\n if (isDateParam(param)) {\n const dateTime = schema?.format === \"date-time\";\n return (\n <FieldWrapper param={param} fieldId={fieldId} inline={inline}>\n <div className=\"flex gap-2\">\n <input\n id={fieldId}\n type={dateTime ? \"datetime-local\" : \"date\"}\n value={dateInputValue(value, dateTime)}\n className={inputClassName}\n onChange={(event) => onChange(dateOutputValue(event.target.value, dateTime))}\n />\n {value && (\n <Button\n type=\"button\"\n variant=\"outline\"\n size=\"sm\"\n aria-label={`Clear ${param.name}`}\n onClick={() => onChange(\"\")}\n >\n <Icon icon={UiClose} />\n </Button>\n )}\n </div>\n </FieldWrapper>\n );\n }\n\n const inputType = schema?.type === \"integer\" || schema?.type === \"number\" ? \"number\" : \"text\";\n\n return (\n <FieldWrapper param={param} fieldId={fieldId} inline={inline}>\n <input\n id={fieldId}\n type={inputType}\n value={value}\n className={inputClassName}\n onChange={(event) => onChange(event.target.value)}\n placeholder={\n schema?.default != null\n ? String(schema.default)\n : parameterPlaceholder(param) || param.name\n }\n />\n </FieldWrapper>\n );\n}\n\nfunction TagInput({\n id,\n value,\n placeholder,\n onChange,\n}: {\n id: string;\n value: string;\n placeholder: string;\n onChange: (value: string) => void;\n}) {\n const tags = parseTags(value);\n\n function commit(raw: string, input: HTMLInputElement) {\n const next = raw\n .split(\",\")\n .map((part) => part.trim())\n .filter(Boolean);\n if (next.length === 0) return;\n onChange(serializeTags([...tags, ...next]));\n input.value = \"\";\n }\n\n function remove(index: number) {\n onChange(serializeTags(tags.filter((_, i) => i !== index)));\n }\n\n function handleKeyDown(event: KeyboardEvent<HTMLInputElement>) {\n const input = event.currentTarget;\n if (event.key === \"Enter\" || event.key === \",\") {\n event.preventDefault();\n commit(input.value, input);\n return;\n }\n if (event.key === \"Backspace\" && input.value === \"\" && tags.length > 0) {\n remove(tags.length - 1);\n }\n }\n\n return (\n <div className=\"flex min-h-9 flex-wrap items-center gap-1.5 rounded-md border border-input bg-transparent px-2 py-1 shadow-sm\">\n {tags.map((tag, index) => (\n <span\n key={`${tag}-${index}`}\n className=\"inline-flex h-6 max-w-full items-center gap-1 rounded-md bg-muted px-2 text-xs\"\n >\n <span className=\"truncate\">{tag}</span>\n <button\n type=\"button\"\n className=\"text-muted-foreground hover:text-foreground\"\n aria-label={`Remove ${tag}`}\n onClick={() => remove(index)}\n >\n <Icon icon={UiClose} />\n </button>\n </span>\n ))}\n <input\n id={id}\n className=\"min-w-32 flex-1 bg-transparent px-1 py-1 text-sm outline-none\"\n placeholder={tags.length === 0 ? placeholder : \"\"}\n onKeyDown={handleKeyDown}\n onBlur={(event) => commit(event.currentTarget.value, event.currentTarget)}\n />\n </div>\n );\n}\n\nfunction FieldWrapper({\n param,\n fieldId,\n inline,\n children,\n}: {\n param: OpenAPIParameter;\n fieldId: string;\n inline?: boolean;\n children: ReactNode;\n}) {\n const label = (\n <label htmlFor={fieldId} className=\"text-sm font-medium\">\n {param.name}\n {param.required && <span className=\"text-destructive\"> *</span>}\n </label>\n );\n\n if (inline) {\n return (\n <div className=\"grid grid-cols-[10rem_1fr] items-start gap-x-3 gap-y-0.5\">\n <div className=\"flex h-9 items-center\">{label}</div>\n <div className=\"min-w-0\">{children}</div>\n {param.description && (\n <p className=\"col-start-2 text-xs text-muted-foreground\">{param.description}</p>\n )}\n </div>\n );\n }\n\n return (\n <div className=\"space-y-1.5\">\n {label}\n {children}\n {param.description && <p className=\"text-xs text-muted-foreground\">{param.description}</p>}\n </div>\n );\n}\n\nexport function normalizeParameters(\n parameters: OpenAPIParameter[],\n path: string,\n): OpenAPIParameter[] {\n const pathParams = pathParamNames(path);\n const firstPathParam = pathParams[0];\n const seen = new Set(parameters.map((param) => param.name));\n const normalized = parameters.filter(\n (param) => !(param.name === \"args\" && firstPathParam != null && !seen.has(firstPathParam)),\n );\n for (const name of pathParams) {\n if (seen.has(name)) continue;\n normalized.unshift({\n name,\n in: \"path\",\n required: true,\n description: \"Path parameter\",\n schema: { type: \"string\" },\n });\n }\n return normalized;\n}\n\nexport function pathParamNames(path: string): string[] {\n return [...path.matchAll(/\\{([^}]+)\\}/g)]\n .map((match) => match[1])\n .filter((name): name is string => Boolean(name));\n}\n\nfunction buildInitialState(\n parameters: OpenAPIParameter[],\n path: string,\n overrides?: Record<string, string>,\n): FormState {\n const state: FormState = {};\n for (const p of parameters) {\n state[p.name] = initialParamValue(p, overrides?.[p.name]);\n }\n for (const name of pathParamNames(path)) {\n if (state[name] == null) {\n state[name] = overrides?.[name] ?? \"\";\n }\n }\n return state;\n}\n\nfunction initialParamValue(param: OpenAPIParameter, override: string | undefined): string {\n if (override != null) return sanitizeInitialValue(param, override);\n const value = param.schema?.default;\n if (value == null) return \"\";\n return sanitizeInitialValue(param, String(value));\n}\n\nfunction sanitizeInitialValue(param: OpenAPIParameter, value: string): string {\n const trimmed = value.trim();\n if (trimmed === \"[]\" || trimmed === \"null\") return \"\";\n if (isDateParam(param) && isZeroDate(trimmed)) return \"\";\n return value;\n}\n\nexport function submitValue(param: OpenAPIParameter, value: string | undefined): string | null {\n const trimmed = (value ?? \"\").trim();\n if (!trimmed || trimmed === \"[]\" || trimmed === \"null\") return null;\n if (isDateParam(param) && isZeroDate(trimmed)) return null;\n return trimmed;\n}\n\nfunction splitArgsValue(value: string): string[] {\n try {\n const parsed = JSON.parse(value);\n if (Array.isArray(parsed)) return parsed.map(String).filter(Boolean);\n } catch {\n // Use comma splitting below.\n }\n return value\n .split(\",\")\n .map((part) => part.trim())\n .filter(Boolean);\n}\n\nfunction isMultiValueParam(param: OpenAPIParameter): boolean {\n const text = `${param.name} ${param.description ?? \"\"}`.toLowerCase();\n return (\n param.schema?.type === \"array\" ||\n String(param.schema?.default ?? \"\") === \"[]\" ||\n text.includes(\"repeatable\")\n );\n}\n\nfunction parseTags(value: string): string[] {\n const trimmed = value.trim();\n if (!trimmed || trimmed === \"[]\" || trimmed === \"null\") return [];\n try {\n const parsed = JSON.parse(trimmed);\n if (Array.isArray(parsed)) return parsed.map(String).filter(Boolean);\n } catch {\n // Fall back to comma-delimited tags below.\n }\n return trimmed\n .split(\",\")\n .map((part) => part.trim())\n .filter(Boolean);\n}\n\nfunction serializeTags(tags: string[]): string {\n return tags.join(\",\");\n}\n\nfunction isDateParam(param: OpenAPIParameter): boolean {\n const format = param.schema?.format?.toLowerCase();\n const text = `${param.name} ${param.description ?? \"\"}`.toLowerCase();\n return format === \"date\" || format === \"date-time\" || text.includes(\"date\");\n}\n\nfunction isZeroDate(value: string): boolean {\n return value.startsWith(\"0001-01-01\") || value === \"0001-01-01\";\n}\n\nfunction dateInputValue(value: string, dateTime: boolean): string {\n if (!value || value.startsWith(\"0001-01-01\")) return \"\";\n if (!dateTime) return value.slice(0, 10);\n const parsed = new Date(value);\n if (Number.isNaN(parsed.getTime())) return value.slice(0, 16);\n const offset = parsed.getTimezoneOffset() * 60_000;\n return new Date(parsed.getTime() - offset).toISOString().slice(0, 16);\n}\n\nfunction dateOutputValue(value: string, dateTime: boolean): string {\n if (!value) return \"\";\n if (!dateTime) return value;\n const parsed = new Date(value);\n if (Number.isNaN(parsed.getTime())) return value;\n return parsed.toISOString();\n}\n\nconst inputClassName =\n \"h-9 w-full min-w-0 rounded-md border border-input bg-background px-2 text-sm text-foreground outline-none placeholder:text-muted-foreground disabled:cursor-not-allowed disabled:bg-muted/40 focus-visible:ring-2 focus-visible:ring-ring\";\n"],"names":[],"mappings":"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"}
|
|
@@ -187,7 +187,7 @@ function parametersToFormConfig(parameters, values, setValues, options = {}) {
|
|
|
187
187
|
value: splitCommaValues(value),
|
|
188
188
|
disabled,
|
|
189
189
|
options: lookupOptionsToFieldOptions(lookupFilter),
|
|
190
|
-
placeholder: param
|
|
190
|
+
placeholder: types.parameterPlaceholder(param) ?? "value-1, value-2",
|
|
191
191
|
onChange: (next) => setValues((current) => ({ ...current, [param.name]: next.join(",") }))
|
|
192
192
|
});
|
|
193
193
|
continue;
|
|
@@ -199,7 +199,7 @@ function parametersToFormConfig(parameters, values, setValues, options = {}) {
|
|
|
199
199
|
value,
|
|
200
200
|
disabled,
|
|
201
201
|
options: lookupOptionsToFieldOptions(lookupFilter),
|
|
202
|
-
placeholder: param
|
|
202
|
+
placeholder: types.parameterPlaceholder(param) ?? label,
|
|
203
203
|
inputType: lookupFilter.type === "number" ? "number" : lookupFilter.type === "date" ? "date" : "text",
|
|
204
204
|
onChange: (next) => onChange(next)
|
|
205
205
|
});
|
|
@@ -211,7 +211,7 @@ function parametersToFormConfig(parameters, values, setValues, options = {}) {
|
|
|
211
211
|
label,
|
|
212
212
|
value,
|
|
213
213
|
disabled,
|
|
214
|
-
placeholder: param
|
|
214
|
+
placeholder: types.parameterPlaceholder(param) ?? label,
|
|
215
215
|
onChange: (next) => onChange(next)
|
|
216
216
|
});
|
|
217
217
|
}
|
|
@@ -219,13 +219,14 @@ function parametersToFormConfig(parameters, values, setValues, options = {}) {
|
|
|
219
219
|
if (searchParam) {
|
|
220
220
|
const searchDisabled = Object.prototype.hasOwnProperty.call(lockedValues, searchParam.name);
|
|
221
221
|
const searchValue = searchDisabled ? lockedValues[searchParam.name] ?? "" : values[searchParam.name] ?? "";
|
|
222
|
+
const searchPlaceholder = types.parameterPlaceholder(searchParam);
|
|
222
223
|
config.search = {
|
|
223
224
|
value: searchValue,
|
|
224
225
|
onChange: (next) => {
|
|
225
226
|
if (searchDisabled) return;
|
|
226
227
|
setValues((current) => ({ ...current, [searchParam.name]: next }));
|
|
227
228
|
},
|
|
228
|
-
...
|
|
229
|
+
...searchPlaceholder ? { placeholder: searchPlaceholder } : {},
|
|
229
230
|
ariaLabel: ((_c = lookupFilters[searchParam.name]) == null ? void 0 : _c.label) ?? titleCase(searchParam.name)
|
|
230
231
|
};
|
|
231
232
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"formMetadata.cjs","sources":["../../src/rpc/formMetadata.ts"],"sourcesContent":["import { useEffect, useState, type Dispatch, type SetStateAction } from \"react\";\nimport type {\n FilterBarFilter,\n FilterBarMultiFilterMode,\n FilterBarRangeProps,\n FilterBarSearchProps,\n} from \"../components/FilterBar\";\nimport type { DataTablePagination } from \"../data/DataTable\";\nimport type {\n ExecutionResponse,\n OpenAPIParameter,\n OperationLookupFilter,\n OperationLookupResponse,\n} from \"./types\";\nimport { isPositionalParam } from \"./types\";\n\nexport type ParameterValues = Record<string, string>;\nexport type ParameterValuesSetter = Dispatch<SetStateAction<ParameterValues>>;\n\n// ParameterPagination plumbs limit/offset query parameters into the\n// DataTable's pagination footer. The UI exposes both as the\n// {pageSize, pageIndex} tuple but here we keep raw string limit/offset\n// values so the executor sees exactly what the operation declared.\nexport type ParameterPagination = {\n limitParam: string; // parameter name on the operation, e.g. \"limit\"\n offsetParam: string;\n limitValue: string;\n offsetValue: string;\n setLimit: (next: string) => void;\n setOffset: (next: string) => void;\n};\n\nexport type ParameterFormConfig = {\n filters: FilterBarFilter[];\n search?: FilterBarSearchProps;\n timeRange?: FilterBarRangeProps;\n pagination?: ParameterPagination;\n};\nexport type ParameterFormOptions = {\n includeLocations?: OpenAPIParameter[\"in\"][];\n lookup?: OperationLookupResponse | undefined;\n lockedValues?: ParameterValues | undefined;\n hideLocked?: boolean;\n};\n\nexport function titleCase(value: string) {\n return value\n .split(/[-_]/)\n .filter(Boolean)\n .map((part) => part.charAt(0).toUpperCase() + part.slice(1))\n .join(\" \");\n}\n\nexport function defaultValueForParameter(param: OpenAPIParameter, method: string): string {\n if (method.toUpperCase() === \"GET\" && param.in === \"query\" && !param.required) {\n return \"\";\n }\n const fallback = param.in === \"path\" ? \"\" : undefined;\n const value = param.schema?.default ?? fallback;\n if (typeof value === \"boolean\") {\n return value ? \"true\" : \"false\";\n }\n if (Array.isArray(value) || (value != null && typeof value === \"object\")) {\n return \"\";\n }\n if (value == null) {\n return \"\";\n }\n return String(value);\n}\n\nexport function buildInitialParameterValues(\n parameters: OpenAPIParameter[],\n method: string,\n lockedValues: ParameterValues = {},\n initialValues: ParameterValues = {},\n): ParameterValues {\n const values = Object.fromEntries(\n parameters.map((param) => [param.name, defaultValueForParameter(param, method)]),\n );\n return { ...values, ...initialValues, ...lockedValues };\n}\n\nexport function dataTablePaginationFromForm(\n pagination: ParameterPagination | undefined,\n response: Pick<ExecutionResponse, \"pagination\"> | null | undefined,\n): DataTablePagination | undefined {\n if (!pagination) return undefined;\n\n const pageSize = positiveInt(pagination.limitValue) ?? response?.pagination?.limit ?? 25;\n const offset = nonNegativeInt(pagination.offsetValue) ?? response?.pagination?.offset ?? 0;\n const page = Math.floor(offset / pageSize);\n\n return {\n page,\n pageSize,\n ...(response?.pagination?.total !== undefined ? { total: response.pagination.total } : {}),\n onPageChange: (next: number) => {\n if (positiveInt(pagination.limitValue) == null) {\n pagination.setLimit(String(pageSize));\n }\n pagination.setOffset(String(Math.max(next, 0) * pageSize));\n },\n onPageSizeChange: (next: number) => {\n pagination.setLimit(String(next));\n pagination.setOffset(\"0\");\n },\n };\n}\n\nexport function pruneParameterValues(values: ParameterValues) {\n return Object.fromEntries(Object.entries(values).filter(([, value]) => value !== \"\"));\n}\n\nexport function packParameterValues(\n values: ParameterValues,\n parameters: OpenAPIParameter[],\n): ParameterValues {\n const positionalNames = new Set(\n parameters\n .filter((param) => param.in !== \"path\" && isPositionalParam(param))\n .map((p) => p.name),\n );\n const params: ParameterValues = {};\n const args: string[] = [];\n\n for (const [key, value] of Object.entries(values)) {\n if (!value) continue;\n if (positionalNames.has(key)) {\n args.push(value);\n } else {\n params[key] = value;\n }\n }\n\n if (args.length > 0) {\n params.args = args.join(\",\");\n }\n\n return params;\n}\n\nexport function parametersToFormConfig(\n parameters: OpenAPIParameter[],\n values: ParameterValues,\n setValues: ParameterValuesSetter,\n options: ParameterFormOptions = {},\n): ParameterFormConfig {\n const emitFilters: FilterBarFilter[] = [];\n const lookupFilters = options.lookup?.filters ?? {};\n const includeLocations = new Set(options.includeLocations ?? [\"path\", \"query\", \"header\"]);\n const lockedValues = options.lockedValues ?? {};\n const hideLocked = options.hideLocked ?? false;\n\n // Pull limit/offset out of the filter loop entirely — they drive pagination,\n // not filter pills. Roles come from server-side `paramRole` (see\n // clicky/rpc/openapi.go); the older \"named limit on a GET\" heuristic is\n // intentionally not duplicated here so the server stays the single source\n // of truth for parameter classification.\n const limitParam = parameters.find((p) => p[\"x-clicky\"]?.role === \"limit\");\n const offsetParam = parameters.find((p) => p[\"x-clicky\"]?.role === \"offset\");\n const paginationOmitNames = new Set<string>();\n if (limitParam) paginationOmitNames.add(limitParam.name);\n if (offsetParam) paginationOmitNames.add(offsetParam.name);\n\n // The search-role param drives the FilterBar's dedicated search input rather\n // than a filter chip; pull it out of the chip loop the same way pagination is.\n const searchParam = parameters.find(\n (p) => p[\"x-clicky\"]?.role === \"search\" && includeLocations.has(p.in),\n );\n const omitNames = new Set(paginationOmitNames);\n if (searchParam) omitNames.add(searchParam.name);\n\n // Time-range first looks for server-stamped roles, then falls back to the\n // existing lookup-driven \"from\"/\"to\" detection so older specs keep working.\n const roleRangeStart = parameters.find((p) => p[\"x-clicky\"]?.role === \"time-from\");\n const roleRangeEnd = parameters.find((p) => p[\"x-clicky\"]?.role === \"time-to\");\n const rangeStart =\n roleRangeStart ??\n parameters.find(\n (param) =>\n includeLocations.has(param.in) &&\n param.in === \"query\" &&\n lookupFilters[param.name]?.type === \"from\",\n );\n const rangeEnd =\n roleRangeEnd ??\n parameters.find(\n (param) =>\n includeLocations.has(param.in) &&\n param.in === \"query\" &&\n lookupFilters[param.name]?.type === \"to\",\n );\n const hasTimeRange = rangeStart != null && rangeEnd != null;\n\n for (const param of parameters) {\n if (!includeLocations.has(param.in)) continue;\n if (omitNames.has(param.name)) continue;\n if (hasTimeRange && (param.name === rangeStart?.name || param.name === rangeEnd?.name)) {\n continue;\n }\n\n const disabled = Object.prototype.hasOwnProperty.call(lockedValues, param.name);\n if (disabled && hideLocked) continue;\n const value = disabled ? (lockedValues[param.name] ?? \"\") : (values[param.name] ?? \"\");\n const label = lookupFilters[param.name]?.label ?? titleCase(param.name);\n const onChange = (next: string | boolean) => {\n if (disabled) return;\n const stringValue = typeof next === \"boolean\" ? (next ? \"true\" : \"false\") : next;\n setValues((current) => ({ ...current, [param.name]: stringValue }));\n };\n\n const schema = param.schema;\n const lookupFilter = lookupFilters[param.name];\n\n if (lookupFilter?.type === \"multi-filter\" && param.in === \"query\") {\n emitFilters.push({\n key: param.name,\n kind: \"multi\",\n label,\n value: parseMultiFilterValue(value),\n disabled,\n options: lookupOptionsToFieldOptions(lookupFilter),\n onChange: (next) =>\n setValues((current) => ({\n ...current,\n [param.name]: serializeMultiFilterValue(next),\n })),\n });\n continue;\n }\n\n if (schema?.enum) {\n emitFilters.push({\n key: param.name,\n kind: \"enum\",\n label,\n value,\n disabled,\n options: schema.enum.map((item) => ({\n value: String(item),\n label: String(item),\n })),\n onChange: (next) => onChange(next),\n });\n continue;\n }\n\n if (lookupFilter?.type === \"bool\" || schema?.type === \"boolean\") {\n emitFilters.push({\n key: param.name,\n kind: \"boolean\",\n label,\n value: value === \"true\",\n disabled,\n onChange: (next) => onChange(next),\n });\n continue;\n }\n\n if (lookupFilter != null && param.in === \"query\") {\n if (lookupFilter.multi) {\n emitFilters.push({\n key: param.name,\n kind: \"lookup-multi\",\n label,\n value: splitCommaValues(value),\n disabled,\n options: lookupOptionsToFieldOptions(lookupFilter),\n placeholder: param.description ?? \"value-1, value-2\",\n onChange: (next) =>\n setValues((current) => ({ ...current, [param.name]: next.join(\",\") })),\n });\n continue;\n }\n\n emitFilters.push({\n key: param.name,\n kind: \"lookup\",\n label,\n value,\n disabled,\n options: lookupOptionsToFieldOptions(lookupFilter),\n placeholder: param.description ?? label,\n inputType:\n lookupFilter.type === \"number\"\n ? \"number\"\n : lookupFilter.type === \"date\"\n ? \"date\"\n : \"text\",\n onChange: (next) => onChange(next),\n });\n continue;\n }\n\n emitFilters.push({\n key: param.name,\n kind: \"text\",\n label,\n value,\n disabled,\n placeholder: param.description ?? label,\n onChange: (next) => onChange(next),\n });\n }\n\n const config: ParameterFormConfig = { filters: emitFilters };\n if (searchParam) {\n const searchDisabled = Object.prototype.hasOwnProperty.call(lockedValues, searchParam.name);\n const searchValue = searchDisabled\n ? (lockedValues[searchParam.name] ?? \"\")\n : (values[searchParam.name] ?? \"\");\n config.search = {\n value: searchValue,\n onChange: (next) => {\n if (searchDisabled) return;\n setValues((current) => ({ ...current, [searchParam.name]: next }));\n },\n ...(searchParam.description ? { placeholder: searchParam.description } : {}),\n ariaLabel: lookupFilters[searchParam.name]?.label ?? titleCase(searchParam.name),\n };\n }\n if (limitParam && offsetParam) {\n config.pagination = {\n limitParam: limitParam.name,\n offsetParam: offsetParam.name,\n limitValue: values[limitParam.name] ?? \"\",\n offsetValue: values[offsetParam.name] ?? \"\",\n setLimit: (next) => setValues((current) => ({ ...current, [limitParam.name]: next })),\n setOffset: (next) => setValues((current) => ({ ...current, [offsetParam.name]: next })),\n };\n }\n if (hasTimeRange && rangeStart != null && rangeEnd != null) {\n const rangeStartMeta = lookupFilters[rangeStart.name];\n const rangeEndMeta = lookupFilters[rangeEnd.name];\n const rangeMeta = rangeStartMeta ?? rangeEndMeta;\n config.timeRange = {\n from: values[rangeStart.name] ?? \"\",\n to: values[rangeEnd.name] ?? \"\",\n onApply: (from, to) =>\n setValues((current) => ({\n ...current,\n [rangeStart.name]: from,\n [rangeEnd.name]: to,\n })),\n ...(rangeMeta?.presets ? { presets: rangeMeta.presets } : {}),\n ...(rangeMeta?.timeEnabled !== undefined ? { timeEnabled: rangeMeta.timeEnabled } : {}),\n ...(rangeMeta?.timeZone ? { timeZone: rangeMeta.timeZone } : {}),\n ...(rangeMeta?.timeZones ? { timeZones: rangeMeta.timeZones } : {}),\n ...(rangeStart.description ? { fromPlaceholder: rangeStart.description } : {}),\n ...(rangeEnd.description ? { toPlaceholder: rangeEnd.description } : {}),\n };\n }\n\n return config;\n}\n\nexport function useDebouncedRecord<T>(value: T, delayMs: number) {\n const [debounced, setDebounced] = useState(value);\n\n useEffect(() => {\n const timeoutId = window.setTimeout(() => setDebounced(value), delayMs);\n return () => window.clearTimeout(timeoutId);\n }, [delayMs, value]);\n\n return debounced;\n}\n\nexport function parseMultiFilterValue(value: string): Record<string, FilterBarMultiFilterMode> {\n const parsed: Record<string, FilterBarMultiFilterMode> = {};\n for (const item of splitCommaValues(value)) {\n if (item.startsWith(\"!\") && item.length > 1) {\n parsed[item.slice(1)] = \"exclude\";\n } else {\n parsed[item] = \"include\";\n }\n }\n return parsed;\n}\n\nexport function serializeMultiFilterValue(value: Record<string, FilterBarMultiFilterMode>): string {\n return Object.entries(value)\n .flatMap(([key, mode]) => {\n if (mode === \"include\") return [key];\n if (mode === \"exclude\") return [`!${key}`];\n return [];\n })\n .join(\",\");\n}\n\nfunction splitCommaValues(value: string) {\n return value\n .split(\",\")\n .map((item) => item.trim())\n .filter(Boolean);\n}\n\nfunction positiveInt(value: string | undefined): number | undefined {\n const parsed = parseInt(value ?? \"\", 10);\n return Number.isFinite(parsed) && parsed > 0 ? parsed : undefined;\n}\n\nfunction nonNegativeInt(value: string | undefined): number | undefined {\n const parsed = parseInt(value ?? \"\", 10);\n return Number.isFinite(parsed) && parsed >= 0 ? parsed : undefined;\n}\n\nfunction lookupOptionsToFieldOptions(filter: OperationLookupFilter) {\n const merged = new Map<string, { label?: string; title?: string }>();\n\n for (const [value, node] of Object.entries(filter.options ?? {})) {\n merged.set(value, {\n label: clickyNodeToPlainText(node) || value,\n title: clickyNodeToPlainText(node) || value,\n });\n }\n\n for (const [value, node] of Object.entries(filter.selected ?? {})) {\n if (!merged.has(value)) {\n merged.set(value, {\n label: clickyNodeToPlainText(node) || value,\n title: clickyNodeToPlainText(node) || value,\n });\n }\n }\n\n return Array.from(merged.entries()).map(([value, meta]) => ({\n value,\n label: meta.label ?? value,\n title: meta.title ?? value,\n }));\n}\n\ntype PlainTextClickyNode = {\n plain?: string;\n text?: string;\n children?: PlainTextClickyNode[];\n tooltip?: { plain?: string; text?: string };\n};\n\nfunction clickyNodeToPlainText(node: PlainTextClickyNode | null | undefined): string {\n if (node == null) return \"\";\n if (node.plain) return node.plain;\n if (node.text) return node.text;\n return (node.children ?? []).map((child) => clickyNodeToPlainText(child)).join(\"\");\n}\n"],"names":["isPositionalParam","_a","useState","useEffect"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"formMetadata.cjs","sources":["../../src/rpc/formMetadata.ts"],"sourcesContent":["import { useEffect, useState, type Dispatch, type SetStateAction } from \"react\";\nimport type {\n FilterBarFilter,\n FilterBarMultiFilterMode,\n FilterBarRangeProps,\n FilterBarSearchProps,\n} from \"../components/FilterBar\";\nimport type { DataTablePagination } from \"../data/DataTable\";\nimport type {\n ExecutionResponse,\n OpenAPIParameter,\n OperationLookupFilter,\n OperationLookupResponse,\n} from \"./types\";\nimport { isPositionalParam, parameterPlaceholder } from \"./types\";\n\nexport type ParameterValues = Record<string, string>;\nexport type ParameterValuesSetter = Dispatch<SetStateAction<ParameterValues>>;\n\n// ParameterPagination plumbs limit/offset query parameters into the\n// DataTable's pagination footer. The UI exposes both as the\n// {pageSize, pageIndex} tuple but here we keep raw string limit/offset\n// values so the executor sees exactly what the operation declared.\nexport type ParameterPagination = {\n limitParam: string; // parameter name on the operation, e.g. \"limit\"\n offsetParam: string;\n limitValue: string;\n offsetValue: string;\n setLimit: (next: string) => void;\n setOffset: (next: string) => void;\n};\n\nexport type ParameterFormConfig = {\n filters: FilterBarFilter[];\n search?: FilterBarSearchProps;\n timeRange?: FilterBarRangeProps;\n pagination?: ParameterPagination;\n};\nexport type ParameterFormOptions = {\n includeLocations?: OpenAPIParameter[\"in\"][];\n lookup?: OperationLookupResponse | undefined;\n lockedValues?: ParameterValues | undefined;\n hideLocked?: boolean;\n};\n\nexport function titleCase(value: string) {\n return value\n .split(/[-_]/)\n .filter(Boolean)\n .map((part) => part.charAt(0).toUpperCase() + part.slice(1))\n .join(\" \");\n}\n\nexport function defaultValueForParameter(param: OpenAPIParameter, method: string): string {\n if (method.toUpperCase() === \"GET\" && param.in === \"query\" && !param.required) {\n return \"\";\n }\n const fallback = param.in === \"path\" ? \"\" : undefined;\n const value = param.schema?.default ?? fallback;\n if (typeof value === \"boolean\") {\n return value ? \"true\" : \"false\";\n }\n if (Array.isArray(value) || (value != null && typeof value === \"object\")) {\n return \"\";\n }\n if (value == null) {\n return \"\";\n }\n return String(value);\n}\n\nexport function buildInitialParameterValues(\n parameters: OpenAPIParameter[],\n method: string,\n lockedValues: ParameterValues = {},\n initialValues: ParameterValues = {},\n): ParameterValues {\n const values = Object.fromEntries(\n parameters.map((param) => [param.name, defaultValueForParameter(param, method)]),\n );\n return { ...values, ...initialValues, ...lockedValues };\n}\n\nexport function dataTablePaginationFromForm(\n pagination: ParameterPagination | undefined,\n response: Pick<ExecutionResponse, \"pagination\"> | null | undefined,\n): DataTablePagination | undefined {\n if (!pagination) return undefined;\n\n const pageSize = positiveInt(pagination.limitValue) ?? response?.pagination?.limit ?? 25;\n const offset = nonNegativeInt(pagination.offsetValue) ?? response?.pagination?.offset ?? 0;\n const page = Math.floor(offset / pageSize);\n\n return {\n page,\n pageSize,\n ...(response?.pagination?.total !== undefined ? { total: response.pagination.total } : {}),\n onPageChange: (next: number) => {\n if (positiveInt(pagination.limitValue) == null) {\n pagination.setLimit(String(pageSize));\n }\n pagination.setOffset(String(Math.max(next, 0) * pageSize));\n },\n onPageSizeChange: (next: number) => {\n pagination.setLimit(String(next));\n pagination.setOffset(\"0\");\n },\n };\n}\n\nexport function pruneParameterValues(values: ParameterValues) {\n return Object.fromEntries(Object.entries(values).filter(([, value]) => value !== \"\"));\n}\n\nexport function packParameterValues(\n values: ParameterValues,\n parameters: OpenAPIParameter[],\n): ParameterValues {\n const positionalNames = new Set(\n parameters\n .filter((param) => param.in !== \"path\" && isPositionalParam(param))\n .map((p) => p.name),\n );\n const params: ParameterValues = {};\n const args: string[] = [];\n\n for (const [key, value] of Object.entries(values)) {\n if (!value) continue;\n if (positionalNames.has(key)) {\n args.push(value);\n } else {\n params[key] = value;\n }\n }\n\n if (args.length > 0) {\n params.args = args.join(\",\");\n }\n\n return params;\n}\n\nexport function parametersToFormConfig(\n parameters: OpenAPIParameter[],\n values: ParameterValues,\n setValues: ParameterValuesSetter,\n options: ParameterFormOptions = {},\n): ParameterFormConfig {\n const emitFilters: FilterBarFilter[] = [];\n const lookupFilters = options.lookup?.filters ?? {};\n const includeLocations = new Set(options.includeLocations ?? [\"path\", \"query\", \"header\"]);\n const lockedValues = options.lockedValues ?? {};\n const hideLocked = options.hideLocked ?? false;\n\n // Pull limit/offset out of the filter loop entirely — they drive pagination,\n // not filter pills. Roles come from server-side `paramRole` (see\n // clicky/rpc/openapi.go); the older \"named limit on a GET\" heuristic is\n // intentionally not duplicated here so the server stays the single source\n // of truth for parameter classification.\n const limitParam = parameters.find((p) => p[\"x-clicky\"]?.role === \"limit\");\n const offsetParam = parameters.find((p) => p[\"x-clicky\"]?.role === \"offset\");\n const paginationOmitNames = new Set<string>();\n if (limitParam) paginationOmitNames.add(limitParam.name);\n if (offsetParam) paginationOmitNames.add(offsetParam.name);\n\n // The search-role param drives the FilterBar's dedicated search input rather\n // than a filter chip; pull it out of the chip loop the same way pagination is.\n const searchParam = parameters.find(\n (p) => p[\"x-clicky\"]?.role === \"search\" && includeLocations.has(p.in),\n );\n const omitNames = new Set(paginationOmitNames);\n if (searchParam) omitNames.add(searchParam.name);\n\n // Time-range first looks for server-stamped roles, then falls back to the\n // existing lookup-driven \"from\"/\"to\" detection so older specs keep working.\n const roleRangeStart = parameters.find((p) => p[\"x-clicky\"]?.role === \"time-from\");\n const roleRangeEnd = parameters.find((p) => p[\"x-clicky\"]?.role === \"time-to\");\n const rangeStart =\n roleRangeStart ??\n parameters.find(\n (param) =>\n includeLocations.has(param.in) &&\n param.in === \"query\" &&\n lookupFilters[param.name]?.type === \"from\",\n );\n const rangeEnd =\n roleRangeEnd ??\n parameters.find(\n (param) =>\n includeLocations.has(param.in) &&\n param.in === \"query\" &&\n lookupFilters[param.name]?.type === \"to\",\n );\n const hasTimeRange = rangeStart != null && rangeEnd != null;\n\n for (const param of parameters) {\n if (!includeLocations.has(param.in)) continue;\n if (omitNames.has(param.name)) continue;\n if (hasTimeRange && (param.name === rangeStart?.name || param.name === rangeEnd?.name)) {\n continue;\n }\n\n const disabled = Object.prototype.hasOwnProperty.call(lockedValues, param.name);\n if (disabled && hideLocked) continue;\n const value = disabled ? (lockedValues[param.name] ?? \"\") : (values[param.name] ?? \"\");\n const label = lookupFilters[param.name]?.label ?? titleCase(param.name);\n const onChange = (next: string | boolean) => {\n if (disabled) return;\n const stringValue = typeof next === \"boolean\" ? (next ? \"true\" : \"false\") : next;\n setValues((current) => ({ ...current, [param.name]: stringValue }));\n };\n\n const schema = param.schema;\n const lookupFilter = lookupFilters[param.name];\n\n if (lookupFilter?.type === \"multi-filter\" && param.in === \"query\") {\n emitFilters.push({\n key: param.name,\n kind: \"multi\",\n label,\n value: parseMultiFilterValue(value),\n disabled,\n options: lookupOptionsToFieldOptions(lookupFilter),\n onChange: (next) =>\n setValues((current) => ({\n ...current,\n [param.name]: serializeMultiFilterValue(next),\n })),\n });\n continue;\n }\n\n if (schema?.enum) {\n emitFilters.push({\n key: param.name,\n kind: \"enum\",\n label,\n value,\n disabled,\n options: schema.enum.map((item) => ({\n value: String(item),\n label: String(item),\n })),\n onChange: (next) => onChange(next),\n });\n continue;\n }\n\n if (lookupFilter?.type === \"bool\" || schema?.type === \"boolean\") {\n emitFilters.push({\n key: param.name,\n kind: \"boolean\",\n label,\n value: value === \"true\",\n disabled,\n onChange: (next) => onChange(next),\n });\n continue;\n }\n\n if (lookupFilter != null && param.in === \"query\") {\n if (lookupFilter.multi) {\n emitFilters.push({\n key: param.name,\n kind: \"lookup-multi\",\n label,\n value: splitCommaValues(value),\n disabled,\n options: lookupOptionsToFieldOptions(lookupFilter),\n placeholder: parameterPlaceholder(param) ?? \"value-1, value-2\",\n onChange: (next) =>\n setValues((current) => ({ ...current, [param.name]: next.join(\",\") })),\n });\n continue;\n }\n\n emitFilters.push({\n key: param.name,\n kind: \"lookup\",\n label,\n value,\n disabled,\n options: lookupOptionsToFieldOptions(lookupFilter),\n placeholder: parameterPlaceholder(param) ?? label,\n inputType:\n lookupFilter.type === \"number\"\n ? \"number\"\n : lookupFilter.type === \"date\"\n ? \"date\"\n : \"text\",\n onChange: (next) => onChange(next),\n });\n continue;\n }\n\n emitFilters.push({\n key: param.name,\n kind: \"text\",\n label,\n value,\n disabled,\n placeholder: parameterPlaceholder(param) ?? label,\n onChange: (next) => onChange(next),\n });\n }\n\n const config: ParameterFormConfig = { filters: emitFilters };\n if (searchParam) {\n const searchDisabled = Object.prototype.hasOwnProperty.call(lockedValues, searchParam.name);\n const searchValue = searchDisabled\n ? (lockedValues[searchParam.name] ?? \"\")\n : (values[searchParam.name] ?? \"\");\n const searchPlaceholder = parameterPlaceholder(searchParam);\n config.search = {\n value: searchValue,\n onChange: (next) => {\n if (searchDisabled) return;\n setValues((current) => ({ ...current, [searchParam.name]: next }));\n },\n ...(searchPlaceholder ? { placeholder: searchPlaceholder } : {}),\n ariaLabel: lookupFilters[searchParam.name]?.label ?? titleCase(searchParam.name),\n };\n }\n if (limitParam && offsetParam) {\n config.pagination = {\n limitParam: limitParam.name,\n offsetParam: offsetParam.name,\n limitValue: values[limitParam.name] ?? \"\",\n offsetValue: values[offsetParam.name] ?? \"\",\n setLimit: (next) => setValues((current) => ({ ...current, [limitParam.name]: next })),\n setOffset: (next) => setValues((current) => ({ ...current, [offsetParam.name]: next })),\n };\n }\n if (hasTimeRange && rangeStart != null && rangeEnd != null) {\n const rangeStartMeta = lookupFilters[rangeStart.name];\n const rangeEndMeta = lookupFilters[rangeEnd.name];\n const rangeMeta = rangeStartMeta ?? rangeEndMeta;\n config.timeRange = {\n from: values[rangeStart.name] ?? \"\",\n to: values[rangeEnd.name] ?? \"\",\n onApply: (from, to) =>\n setValues((current) => ({\n ...current,\n [rangeStart.name]: from,\n [rangeEnd.name]: to,\n })),\n ...(rangeMeta?.presets ? { presets: rangeMeta.presets } : {}),\n ...(rangeMeta?.timeEnabled !== undefined ? { timeEnabled: rangeMeta.timeEnabled } : {}),\n ...(rangeMeta?.timeZone ? { timeZone: rangeMeta.timeZone } : {}),\n ...(rangeMeta?.timeZones ? { timeZones: rangeMeta.timeZones } : {}),\n ...(rangeStart.description ? { fromPlaceholder: rangeStart.description } : {}),\n ...(rangeEnd.description ? { toPlaceholder: rangeEnd.description } : {}),\n };\n }\n\n return config;\n}\n\nexport function useDebouncedRecord<T>(value: T, delayMs: number) {\n const [debounced, setDebounced] = useState(value);\n\n useEffect(() => {\n const timeoutId = window.setTimeout(() => setDebounced(value), delayMs);\n return () => window.clearTimeout(timeoutId);\n }, [delayMs, value]);\n\n return debounced;\n}\n\nexport function parseMultiFilterValue(value: string): Record<string, FilterBarMultiFilterMode> {\n const parsed: Record<string, FilterBarMultiFilterMode> = {};\n for (const item of splitCommaValues(value)) {\n if (item.startsWith(\"!\") && item.length > 1) {\n parsed[item.slice(1)] = \"exclude\";\n } else {\n parsed[item] = \"include\";\n }\n }\n return parsed;\n}\n\nexport function serializeMultiFilterValue(value: Record<string, FilterBarMultiFilterMode>): string {\n return Object.entries(value)\n .flatMap(([key, mode]) => {\n if (mode === \"include\") return [key];\n if (mode === \"exclude\") return [`!${key}`];\n return [];\n })\n .join(\",\");\n}\n\nfunction splitCommaValues(value: string) {\n return value\n .split(\",\")\n .map((item) => item.trim())\n .filter(Boolean);\n}\n\nfunction positiveInt(value: string | undefined): number | undefined {\n const parsed = parseInt(value ?? \"\", 10);\n return Number.isFinite(parsed) && parsed > 0 ? parsed : undefined;\n}\n\nfunction nonNegativeInt(value: string | undefined): number | undefined {\n const parsed = parseInt(value ?? \"\", 10);\n return Number.isFinite(parsed) && parsed >= 0 ? parsed : undefined;\n}\n\nfunction lookupOptionsToFieldOptions(filter: OperationLookupFilter) {\n const merged = new Map<string, { label?: string; title?: string }>();\n\n for (const [value, node] of Object.entries(filter.options ?? {})) {\n merged.set(value, {\n label: clickyNodeToPlainText(node) || value,\n title: clickyNodeToPlainText(node) || value,\n });\n }\n\n for (const [value, node] of Object.entries(filter.selected ?? {})) {\n if (!merged.has(value)) {\n merged.set(value, {\n label: clickyNodeToPlainText(node) || value,\n title: clickyNodeToPlainText(node) || value,\n });\n }\n }\n\n return Array.from(merged.entries()).map(([value, meta]) => ({\n value,\n label: meta.label ?? value,\n title: meta.title ?? value,\n }));\n}\n\ntype PlainTextClickyNode = {\n plain?: string;\n text?: string;\n children?: PlainTextClickyNode[];\n tooltip?: { plain?: string; text?: string };\n};\n\nfunction clickyNodeToPlainText(node: PlainTextClickyNode | null | undefined): string {\n if (node == null) return \"\";\n if (node.plain) return node.plain;\n if (node.text) return node.text;\n return (node.children ?? []).map((child) => clickyNodeToPlainText(child)).join(\"\");\n}\n"],"names":["isPositionalParam","_a","parameterPlaceholder","useState","useEffect"],"mappings":"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"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"formMetadata.d.ts","sourceRoot":"","sources":["../../src/rpc/formMetadata.ts"],"names":[],"mappings":"AAAA,OAAO,EAAuB,KAAK,QAAQ,EAAE,KAAK,cAAc,EAAE,MAAM,OAAO,CAAC;AAChF,OAAO,KAAK,EACV,eAAe,EACf,wBAAwB,EACxB,mBAAmB,EACnB,oBAAoB,EACrB,MAAM,yBAAyB,CAAC;AACjC,OAAO,KAAK,EAAE,mBAAmB,EAAE,MAAM,mBAAmB,CAAC;AAC7D,OAAO,KAAK,EACV,iBAAiB,EACjB,gBAAgB,EAEhB,uBAAuB,EACxB,MAAM,SAAS,CAAC;AAGjB,MAAM,MAAM,eAAe,GAAG,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;AACrD,MAAM,MAAM,qBAAqB,GAAG,QAAQ,CAAC,cAAc,CAAC,eAAe,CAAC,CAAC,CAAC;AAM9E,MAAM,MAAM,mBAAmB,GAAG;IAChC,UAAU,EAAE,MAAM,CAAC;IACnB,WAAW,EAAE,MAAM,CAAC;IACpB,UAAU,EAAE,MAAM,CAAC;IACnB,WAAW,EAAE,MAAM,CAAC;IACpB,QAAQ,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,IAAI,CAAC;IACjC,SAAS,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,IAAI,CAAC;CACnC,CAAC;AAEF,MAAM,MAAM,mBAAmB,GAAG;IAChC,OAAO,EAAE,eAAe,EAAE,CAAC;IAC3B,MAAM,CAAC,EAAE,oBAAoB,CAAC;IAC9B,SAAS,CAAC,EAAE,mBAAmB,CAAC;IAChC,UAAU,CAAC,EAAE,mBAAmB,CAAC;CAClC,CAAC;AACF,MAAM,MAAM,oBAAoB,GAAG;IACjC,gBAAgB,CAAC,EAAE,gBAAgB,CAAC,IAAI,CAAC,EAAE,CAAC;IAC5C,MAAM,CAAC,EAAE,uBAAuB,GAAG,SAAS,CAAC;IAC7C,YAAY,CAAC,EAAE,eAAe,GAAG,SAAS,CAAC;IAC3C,UAAU,CAAC,EAAE,OAAO,CAAC;CACtB,CAAC;AAEF,wBAAgB,SAAS,CAAC,KAAK,EAAE,MAAM,UAMtC;AAED,wBAAgB,wBAAwB,CAAC,KAAK,EAAE,gBAAgB,EAAE,MAAM,EAAE,MAAM,GAAG,MAAM,CAgBxF;AAED,wBAAgB,2BAA2B,CACzC,UAAU,EAAE,gBAAgB,EAAE,EAC9B,MAAM,EAAE,MAAM,EACd,YAAY,GAAE,eAAoB,EAClC,aAAa,GAAE,eAAoB,GAClC,eAAe,CAKjB;AAED,wBAAgB,2BAA2B,CACzC,UAAU,EAAE,mBAAmB,GAAG,SAAS,EAC3C,QAAQ,EAAE,IAAI,CAAC,iBAAiB,EAAE,YAAY,CAAC,GAAG,IAAI,GAAG,SAAS,GACjE,mBAAmB,GAAG,SAAS,CAsBjC;AAED,wBAAgB,oBAAoB,CAAC,MAAM,EAAE,eAAe;;EAE3D;AAED,wBAAgB,mBAAmB,CACjC,MAAM,EAAE,eAAe,EACvB,UAAU,EAAE,gBAAgB,EAAE,GAC7B,eAAe,CAuBjB;AAED,wBAAgB,sBAAsB,CACpC,UAAU,EAAE,gBAAgB,EAAE,EAC9B,MAAM,EAAE,eAAe,EACvB,SAAS,EAAE,qBAAqB,EAChC,OAAO,GAAE,oBAAyB,GACjC,mBAAmB,
|
|
1
|
+
{"version":3,"file":"formMetadata.d.ts","sourceRoot":"","sources":["../../src/rpc/formMetadata.ts"],"names":[],"mappings":"AAAA,OAAO,EAAuB,KAAK,QAAQ,EAAE,KAAK,cAAc,EAAE,MAAM,OAAO,CAAC;AAChF,OAAO,KAAK,EACV,eAAe,EACf,wBAAwB,EACxB,mBAAmB,EACnB,oBAAoB,EACrB,MAAM,yBAAyB,CAAC;AACjC,OAAO,KAAK,EAAE,mBAAmB,EAAE,MAAM,mBAAmB,CAAC;AAC7D,OAAO,KAAK,EACV,iBAAiB,EACjB,gBAAgB,EAEhB,uBAAuB,EACxB,MAAM,SAAS,CAAC;AAGjB,MAAM,MAAM,eAAe,GAAG,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;AACrD,MAAM,MAAM,qBAAqB,GAAG,QAAQ,CAAC,cAAc,CAAC,eAAe,CAAC,CAAC,CAAC;AAM9E,MAAM,MAAM,mBAAmB,GAAG;IAChC,UAAU,EAAE,MAAM,CAAC;IACnB,WAAW,EAAE,MAAM,CAAC;IACpB,UAAU,EAAE,MAAM,CAAC;IACnB,WAAW,EAAE,MAAM,CAAC;IACpB,QAAQ,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,IAAI,CAAC;IACjC,SAAS,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,IAAI,CAAC;CACnC,CAAC;AAEF,MAAM,MAAM,mBAAmB,GAAG;IAChC,OAAO,EAAE,eAAe,EAAE,CAAC;IAC3B,MAAM,CAAC,EAAE,oBAAoB,CAAC;IAC9B,SAAS,CAAC,EAAE,mBAAmB,CAAC;IAChC,UAAU,CAAC,EAAE,mBAAmB,CAAC;CAClC,CAAC;AACF,MAAM,MAAM,oBAAoB,GAAG;IACjC,gBAAgB,CAAC,EAAE,gBAAgB,CAAC,IAAI,CAAC,EAAE,CAAC;IAC5C,MAAM,CAAC,EAAE,uBAAuB,GAAG,SAAS,CAAC;IAC7C,YAAY,CAAC,EAAE,eAAe,GAAG,SAAS,CAAC;IAC3C,UAAU,CAAC,EAAE,OAAO,CAAC;CACtB,CAAC;AAEF,wBAAgB,SAAS,CAAC,KAAK,EAAE,MAAM,UAMtC;AAED,wBAAgB,wBAAwB,CAAC,KAAK,EAAE,gBAAgB,EAAE,MAAM,EAAE,MAAM,GAAG,MAAM,CAgBxF;AAED,wBAAgB,2BAA2B,CACzC,UAAU,EAAE,gBAAgB,EAAE,EAC9B,MAAM,EAAE,MAAM,EACd,YAAY,GAAE,eAAoB,EAClC,aAAa,GAAE,eAAoB,GAClC,eAAe,CAKjB;AAED,wBAAgB,2BAA2B,CACzC,UAAU,EAAE,mBAAmB,GAAG,SAAS,EAC3C,QAAQ,EAAE,IAAI,CAAC,iBAAiB,EAAE,YAAY,CAAC,GAAG,IAAI,GAAG,SAAS,GACjE,mBAAmB,GAAG,SAAS,CAsBjC;AAED,wBAAgB,oBAAoB,CAAC,MAAM,EAAE,eAAe;;EAE3D;AAED,wBAAgB,mBAAmB,CACjC,MAAM,EAAE,eAAe,EACvB,UAAU,EAAE,gBAAgB,EAAE,GAC7B,eAAe,CAuBjB;AAED,wBAAgB,sBAAsB,CACpC,UAAU,EAAE,gBAAgB,EAAE,EAC9B,MAAM,EAAE,eAAe,EACvB,SAAS,EAAE,qBAAqB,EAChC,OAAO,GAAE,oBAAyB,GACjC,mBAAmB,CAiNrB;AAED,wBAAgB,kBAAkB,CAAC,CAAC,EAAE,KAAK,EAAE,CAAC,EAAE,OAAO,EAAE,MAAM,KAS9D;AAED,wBAAgB,qBAAqB,CAAC,KAAK,EAAE,MAAM,GAAG,MAAM,CAAC,MAAM,EAAE,wBAAwB,CAAC,CAU7F;AAED,wBAAgB,yBAAyB,CAAC,KAAK,EAAE,MAAM,CAAC,MAAM,EAAE,wBAAwB,CAAC,GAAG,MAAM,CAQjG"}
|
package/dist/rpc/formMetadata.js
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { useState, useEffect } from "react";
|
|
2
|
-
import { isPositionalParam } from "./types.js";
|
|
2
|
+
import { isPositionalParam, parameterPlaceholder } from "./types.js";
|
|
3
3
|
function titleCase(value) {
|
|
4
4
|
return value.split(/[-_]/).filter(Boolean).map((part) => part.charAt(0).toUpperCase() + part.slice(1)).join(" ");
|
|
5
5
|
}
|
|
@@ -185,7 +185,7 @@ function parametersToFormConfig(parameters, values, setValues, options = {}) {
|
|
|
185
185
|
value: splitCommaValues(value),
|
|
186
186
|
disabled,
|
|
187
187
|
options: lookupOptionsToFieldOptions(lookupFilter),
|
|
188
|
-
placeholder: param
|
|
188
|
+
placeholder: parameterPlaceholder(param) ?? "value-1, value-2",
|
|
189
189
|
onChange: (next) => setValues((current) => ({ ...current, [param.name]: next.join(",") }))
|
|
190
190
|
});
|
|
191
191
|
continue;
|
|
@@ -197,7 +197,7 @@ function parametersToFormConfig(parameters, values, setValues, options = {}) {
|
|
|
197
197
|
value,
|
|
198
198
|
disabled,
|
|
199
199
|
options: lookupOptionsToFieldOptions(lookupFilter),
|
|
200
|
-
placeholder: param
|
|
200
|
+
placeholder: parameterPlaceholder(param) ?? label,
|
|
201
201
|
inputType: lookupFilter.type === "number" ? "number" : lookupFilter.type === "date" ? "date" : "text",
|
|
202
202
|
onChange: (next) => onChange(next)
|
|
203
203
|
});
|
|
@@ -209,7 +209,7 @@ function parametersToFormConfig(parameters, values, setValues, options = {}) {
|
|
|
209
209
|
label,
|
|
210
210
|
value,
|
|
211
211
|
disabled,
|
|
212
|
-
placeholder: param
|
|
212
|
+
placeholder: parameterPlaceholder(param) ?? label,
|
|
213
213
|
onChange: (next) => onChange(next)
|
|
214
214
|
});
|
|
215
215
|
}
|
|
@@ -217,13 +217,14 @@ function parametersToFormConfig(parameters, values, setValues, options = {}) {
|
|
|
217
217
|
if (searchParam) {
|
|
218
218
|
const searchDisabled = Object.prototype.hasOwnProperty.call(lockedValues, searchParam.name);
|
|
219
219
|
const searchValue = searchDisabled ? lockedValues[searchParam.name] ?? "" : values[searchParam.name] ?? "";
|
|
220
|
+
const searchPlaceholder = parameterPlaceholder(searchParam);
|
|
220
221
|
config.search = {
|
|
221
222
|
value: searchValue,
|
|
222
223
|
onChange: (next) => {
|
|
223
224
|
if (searchDisabled) return;
|
|
224
225
|
setValues((current) => ({ ...current, [searchParam.name]: next }));
|
|
225
226
|
},
|
|
226
|
-
...
|
|
227
|
+
...searchPlaceholder ? { placeholder: searchPlaceholder } : {},
|
|
227
228
|
ariaLabel: ((_c = lookupFilters[searchParam.name]) == null ? void 0 : _c.label) ?? titleCase(searchParam.name)
|
|
228
229
|
};
|
|
229
230
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"formMetadata.js","sources":["../../src/rpc/formMetadata.ts"],"sourcesContent":["import { useEffect, useState, type Dispatch, type SetStateAction } from \"react\";\nimport type {\n FilterBarFilter,\n FilterBarMultiFilterMode,\n FilterBarRangeProps,\n FilterBarSearchProps,\n} from \"../components/FilterBar\";\nimport type { DataTablePagination } from \"../data/DataTable\";\nimport type {\n ExecutionResponse,\n OpenAPIParameter,\n OperationLookupFilter,\n OperationLookupResponse,\n} from \"./types\";\nimport { isPositionalParam } from \"./types\";\n\nexport type ParameterValues = Record<string, string>;\nexport type ParameterValuesSetter = Dispatch<SetStateAction<ParameterValues>>;\n\n// ParameterPagination plumbs limit/offset query parameters into the\n// DataTable's pagination footer. The UI exposes both as the\n// {pageSize, pageIndex} tuple but here we keep raw string limit/offset\n// values so the executor sees exactly what the operation declared.\nexport type ParameterPagination = {\n limitParam: string; // parameter name on the operation, e.g. \"limit\"\n offsetParam: string;\n limitValue: string;\n offsetValue: string;\n setLimit: (next: string) => void;\n setOffset: (next: string) => void;\n};\n\nexport type ParameterFormConfig = {\n filters: FilterBarFilter[];\n search?: FilterBarSearchProps;\n timeRange?: FilterBarRangeProps;\n pagination?: ParameterPagination;\n};\nexport type ParameterFormOptions = {\n includeLocations?: OpenAPIParameter[\"in\"][];\n lookup?: OperationLookupResponse | undefined;\n lockedValues?: ParameterValues | undefined;\n hideLocked?: boolean;\n};\n\nexport function titleCase(value: string) {\n return value\n .split(/[-_]/)\n .filter(Boolean)\n .map((part) => part.charAt(0).toUpperCase() + part.slice(1))\n .join(\" \");\n}\n\nexport function defaultValueForParameter(param: OpenAPIParameter, method: string): string {\n if (method.toUpperCase() === \"GET\" && param.in === \"query\" && !param.required) {\n return \"\";\n }\n const fallback = param.in === \"path\" ? \"\" : undefined;\n const value = param.schema?.default ?? fallback;\n if (typeof value === \"boolean\") {\n return value ? \"true\" : \"false\";\n }\n if (Array.isArray(value) || (value != null && typeof value === \"object\")) {\n return \"\";\n }\n if (value == null) {\n return \"\";\n }\n return String(value);\n}\n\nexport function buildInitialParameterValues(\n parameters: OpenAPIParameter[],\n method: string,\n lockedValues: ParameterValues = {},\n initialValues: ParameterValues = {},\n): ParameterValues {\n const values = Object.fromEntries(\n parameters.map((param) => [param.name, defaultValueForParameter(param, method)]),\n );\n return { ...values, ...initialValues, ...lockedValues };\n}\n\nexport function dataTablePaginationFromForm(\n pagination: ParameterPagination | undefined,\n response: Pick<ExecutionResponse, \"pagination\"> | null | undefined,\n): DataTablePagination | undefined {\n if (!pagination) return undefined;\n\n const pageSize = positiveInt(pagination.limitValue) ?? response?.pagination?.limit ?? 25;\n const offset = nonNegativeInt(pagination.offsetValue) ?? response?.pagination?.offset ?? 0;\n const page = Math.floor(offset / pageSize);\n\n return {\n page,\n pageSize,\n ...(response?.pagination?.total !== undefined ? { total: response.pagination.total } : {}),\n onPageChange: (next: number) => {\n if (positiveInt(pagination.limitValue) == null) {\n pagination.setLimit(String(pageSize));\n }\n pagination.setOffset(String(Math.max(next, 0) * pageSize));\n },\n onPageSizeChange: (next: number) => {\n pagination.setLimit(String(next));\n pagination.setOffset(\"0\");\n },\n };\n}\n\nexport function pruneParameterValues(values: ParameterValues) {\n return Object.fromEntries(Object.entries(values).filter(([, value]) => value !== \"\"));\n}\n\nexport function packParameterValues(\n values: ParameterValues,\n parameters: OpenAPIParameter[],\n): ParameterValues {\n const positionalNames = new Set(\n parameters\n .filter((param) => param.in !== \"path\" && isPositionalParam(param))\n .map((p) => p.name),\n );\n const params: ParameterValues = {};\n const args: string[] = [];\n\n for (const [key, value] of Object.entries(values)) {\n if (!value) continue;\n if (positionalNames.has(key)) {\n args.push(value);\n } else {\n params[key] = value;\n }\n }\n\n if (args.length > 0) {\n params.args = args.join(\",\");\n }\n\n return params;\n}\n\nexport function parametersToFormConfig(\n parameters: OpenAPIParameter[],\n values: ParameterValues,\n setValues: ParameterValuesSetter,\n options: ParameterFormOptions = {},\n): ParameterFormConfig {\n const emitFilters: FilterBarFilter[] = [];\n const lookupFilters = options.lookup?.filters ?? {};\n const includeLocations = new Set(options.includeLocations ?? [\"path\", \"query\", \"header\"]);\n const lockedValues = options.lockedValues ?? {};\n const hideLocked = options.hideLocked ?? false;\n\n // Pull limit/offset out of the filter loop entirely — they drive pagination,\n // not filter pills. Roles come from server-side `paramRole` (see\n // clicky/rpc/openapi.go); the older \"named limit on a GET\" heuristic is\n // intentionally not duplicated here so the server stays the single source\n // of truth for parameter classification.\n const limitParam = parameters.find((p) => p[\"x-clicky\"]?.role === \"limit\");\n const offsetParam = parameters.find((p) => p[\"x-clicky\"]?.role === \"offset\");\n const paginationOmitNames = new Set<string>();\n if (limitParam) paginationOmitNames.add(limitParam.name);\n if (offsetParam) paginationOmitNames.add(offsetParam.name);\n\n // The search-role param drives the FilterBar's dedicated search input rather\n // than a filter chip; pull it out of the chip loop the same way pagination is.\n const searchParam = parameters.find(\n (p) => p[\"x-clicky\"]?.role === \"search\" && includeLocations.has(p.in),\n );\n const omitNames = new Set(paginationOmitNames);\n if (searchParam) omitNames.add(searchParam.name);\n\n // Time-range first looks for server-stamped roles, then falls back to the\n // existing lookup-driven \"from\"/\"to\" detection so older specs keep working.\n const roleRangeStart = parameters.find((p) => p[\"x-clicky\"]?.role === \"time-from\");\n const roleRangeEnd = parameters.find((p) => p[\"x-clicky\"]?.role === \"time-to\");\n const rangeStart =\n roleRangeStart ??\n parameters.find(\n (param) =>\n includeLocations.has(param.in) &&\n param.in === \"query\" &&\n lookupFilters[param.name]?.type === \"from\",\n );\n const rangeEnd =\n roleRangeEnd ??\n parameters.find(\n (param) =>\n includeLocations.has(param.in) &&\n param.in === \"query\" &&\n lookupFilters[param.name]?.type === \"to\",\n );\n const hasTimeRange = rangeStart != null && rangeEnd != null;\n\n for (const param of parameters) {\n if (!includeLocations.has(param.in)) continue;\n if (omitNames.has(param.name)) continue;\n if (hasTimeRange && (param.name === rangeStart?.name || param.name === rangeEnd?.name)) {\n continue;\n }\n\n const disabled = Object.prototype.hasOwnProperty.call(lockedValues, param.name);\n if (disabled && hideLocked) continue;\n const value = disabled ? (lockedValues[param.name] ?? \"\") : (values[param.name] ?? \"\");\n const label = lookupFilters[param.name]?.label ?? titleCase(param.name);\n const onChange = (next: string | boolean) => {\n if (disabled) return;\n const stringValue = typeof next === \"boolean\" ? (next ? \"true\" : \"false\") : next;\n setValues((current) => ({ ...current, [param.name]: stringValue }));\n };\n\n const schema = param.schema;\n const lookupFilter = lookupFilters[param.name];\n\n if (lookupFilter?.type === \"multi-filter\" && param.in === \"query\") {\n emitFilters.push({\n key: param.name,\n kind: \"multi\",\n label,\n value: parseMultiFilterValue(value),\n disabled,\n options: lookupOptionsToFieldOptions(lookupFilter),\n onChange: (next) =>\n setValues((current) => ({\n ...current,\n [param.name]: serializeMultiFilterValue(next),\n })),\n });\n continue;\n }\n\n if (schema?.enum) {\n emitFilters.push({\n key: param.name,\n kind: \"enum\",\n label,\n value,\n disabled,\n options: schema.enum.map((item) => ({\n value: String(item),\n label: String(item),\n })),\n onChange: (next) => onChange(next),\n });\n continue;\n }\n\n if (lookupFilter?.type === \"bool\" || schema?.type === \"boolean\") {\n emitFilters.push({\n key: param.name,\n kind: \"boolean\",\n label,\n value: value === \"true\",\n disabled,\n onChange: (next) => onChange(next),\n });\n continue;\n }\n\n if (lookupFilter != null && param.in === \"query\") {\n if (lookupFilter.multi) {\n emitFilters.push({\n key: param.name,\n kind: \"lookup-multi\",\n label,\n value: splitCommaValues(value),\n disabled,\n options: lookupOptionsToFieldOptions(lookupFilter),\n placeholder: param.description ?? \"value-1, value-2\",\n onChange: (next) =>\n setValues((current) => ({ ...current, [param.name]: next.join(\",\") })),\n });\n continue;\n }\n\n emitFilters.push({\n key: param.name,\n kind: \"lookup\",\n label,\n value,\n disabled,\n options: lookupOptionsToFieldOptions(lookupFilter),\n placeholder: param.description ?? label,\n inputType:\n lookupFilter.type === \"number\"\n ? \"number\"\n : lookupFilter.type === \"date\"\n ? \"date\"\n : \"text\",\n onChange: (next) => onChange(next),\n });\n continue;\n }\n\n emitFilters.push({\n key: param.name,\n kind: \"text\",\n label,\n value,\n disabled,\n placeholder: param.description ?? label,\n onChange: (next) => onChange(next),\n });\n }\n\n const config: ParameterFormConfig = { filters: emitFilters };\n if (searchParam) {\n const searchDisabled = Object.prototype.hasOwnProperty.call(lockedValues, searchParam.name);\n const searchValue = searchDisabled\n ? (lockedValues[searchParam.name] ?? \"\")\n : (values[searchParam.name] ?? \"\");\n config.search = {\n value: searchValue,\n onChange: (next) => {\n if (searchDisabled) return;\n setValues((current) => ({ ...current, [searchParam.name]: next }));\n },\n ...(searchParam.description ? { placeholder: searchParam.description } : {}),\n ariaLabel: lookupFilters[searchParam.name]?.label ?? titleCase(searchParam.name),\n };\n }\n if (limitParam && offsetParam) {\n config.pagination = {\n limitParam: limitParam.name,\n offsetParam: offsetParam.name,\n limitValue: values[limitParam.name] ?? \"\",\n offsetValue: values[offsetParam.name] ?? \"\",\n setLimit: (next) => setValues((current) => ({ ...current, [limitParam.name]: next })),\n setOffset: (next) => setValues((current) => ({ ...current, [offsetParam.name]: next })),\n };\n }\n if (hasTimeRange && rangeStart != null && rangeEnd != null) {\n const rangeStartMeta = lookupFilters[rangeStart.name];\n const rangeEndMeta = lookupFilters[rangeEnd.name];\n const rangeMeta = rangeStartMeta ?? rangeEndMeta;\n config.timeRange = {\n from: values[rangeStart.name] ?? \"\",\n to: values[rangeEnd.name] ?? \"\",\n onApply: (from, to) =>\n setValues((current) => ({\n ...current,\n [rangeStart.name]: from,\n [rangeEnd.name]: to,\n })),\n ...(rangeMeta?.presets ? { presets: rangeMeta.presets } : {}),\n ...(rangeMeta?.timeEnabled !== undefined ? { timeEnabled: rangeMeta.timeEnabled } : {}),\n ...(rangeMeta?.timeZone ? { timeZone: rangeMeta.timeZone } : {}),\n ...(rangeMeta?.timeZones ? { timeZones: rangeMeta.timeZones } : {}),\n ...(rangeStart.description ? { fromPlaceholder: rangeStart.description } : {}),\n ...(rangeEnd.description ? { toPlaceholder: rangeEnd.description } : {}),\n };\n }\n\n return config;\n}\n\nexport function useDebouncedRecord<T>(value: T, delayMs: number) {\n const [debounced, setDebounced] = useState(value);\n\n useEffect(() => {\n const timeoutId = window.setTimeout(() => setDebounced(value), delayMs);\n return () => window.clearTimeout(timeoutId);\n }, [delayMs, value]);\n\n return debounced;\n}\n\nexport function parseMultiFilterValue(value: string): Record<string, FilterBarMultiFilterMode> {\n const parsed: Record<string, FilterBarMultiFilterMode> = {};\n for (const item of splitCommaValues(value)) {\n if (item.startsWith(\"!\") && item.length > 1) {\n parsed[item.slice(1)] = \"exclude\";\n } else {\n parsed[item] = \"include\";\n }\n }\n return parsed;\n}\n\nexport function serializeMultiFilterValue(value: Record<string, FilterBarMultiFilterMode>): string {\n return Object.entries(value)\n .flatMap(([key, mode]) => {\n if (mode === \"include\") return [key];\n if (mode === \"exclude\") return [`!${key}`];\n return [];\n })\n .join(\",\");\n}\n\nfunction splitCommaValues(value: string) {\n return value\n .split(\",\")\n .map((item) => item.trim())\n .filter(Boolean);\n}\n\nfunction positiveInt(value: string | undefined): number | undefined {\n const parsed = parseInt(value ?? \"\", 10);\n return Number.isFinite(parsed) && parsed > 0 ? parsed : undefined;\n}\n\nfunction nonNegativeInt(value: string | undefined): number | undefined {\n const parsed = parseInt(value ?? \"\", 10);\n return Number.isFinite(parsed) && parsed >= 0 ? parsed : undefined;\n}\n\nfunction lookupOptionsToFieldOptions(filter: OperationLookupFilter) {\n const merged = new Map<string, { label?: string; title?: string }>();\n\n for (const [value, node] of Object.entries(filter.options ?? {})) {\n merged.set(value, {\n label: clickyNodeToPlainText(node) || value,\n title: clickyNodeToPlainText(node) || value,\n });\n }\n\n for (const [value, node] of Object.entries(filter.selected ?? {})) {\n if (!merged.has(value)) {\n merged.set(value, {\n label: clickyNodeToPlainText(node) || value,\n title: clickyNodeToPlainText(node) || value,\n });\n }\n }\n\n return Array.from(merged.entries()).map(([value, meta]) => ({\n value,\n label: meta.label ?? value,\n title: meta.title ?? value,\n }));\n}\n\ntype PlainTextClickyNode = {\n plain?: string;\n text?: string;\n children?: PlainTextClickyNode[];\n tooltip?: { plain?: string; text?: string };\n};\n\nfunction clickyNodeToPlainText(node: PlainTextClickyNode | null | undefined): string {\n if (node == null) return \"\";\n if (node.plain) return node.plain;\n if (node.text) return node.text;\n return (node.children ?? []).map((child) => clickyNodeToPlainText(child)).join(\"\");\n}\n"],"names":["_a"],"mappings":";;AA6CO,SAAS,UAAU,OAAe;AACvC,SAAO,MACJ,MAAM,MAAM,EACZ,OAAO,OAAO,EACd,IAAI,CAAC,SAAS,KAAK,OAAO,CAAC,EAAE,gBAAgB,KAAK,MAAM,CAAC,CAAC,EAC1D,KAAK,GAAG;AACb;AAEO,SAAS,yBAAyB,OAAyB,QAAwB;;AACxF,MAAI,OAAO,kBAAkB,SAAS,MAAM,OAAO,WAAW,CAAC,MAAM,UAAU;AAC7E,WAAO;AAAA,EACT;AACA,QAAM,WAAW,MAAM,OAAO,SAAS,KAAK;AAC5C,QAAM,UAAQ,WAAM,WAAN,mBAAc,YAAW;AACvC,MAAI,OAAO,UAAU,WAAW;AAC9B,WAAO,QAAQ,SAAS;AAAA,EAC1B;AACA,MAAI,MAAM,QAAQ,KAAK,KAAM,SAAS,QAAQ,OAAO,UAAU,UAAW;AACxE,WAAO;AAAA,EACT;AACA,MAAI,SAAS,MAAM;AACjB,WAAO;AAAA,EACT;AACA,SAAO,OAAO,KAAK;AACrB;AAEO,SAAS,4BACd,YACA,QACA,eAAgC,CAAA,GAChC,gBAAiC,IAChB;AACjB,QAAM,SAAS,OAAO;AAAA,IACpB,WAAW,IAAI,CAAC,UAAU,CAAC,MAAM,MAAM,yBAAyB,OAAO,MAAM,CAAC,CAAC;AAAA,EAAA;AAEjF,SAAO,EAAE,GAAG,QAAQ,GAAG,eAAe,GAAG,aAAA;AAC3C;AAEO,SAAS,4BACd,YACA,UACiC;;AACjC,MAAI,CAAC,WAAY,QAAO;AAExB,QAAM,WAAW,YAAY,WAAW,UAAU,OAAK,0CAAU,eAAV,mBAAsB,UAAS;AACtF,QAAM,SAAS,eAAe,WAAW,WAAW,OAAK,0CAAU,eAAV,mBAAsB,WAAU;AACzF,QAAM,OAAO,KAAK,MAAM,SAAS,QAAQ;AAEzC,SAAO;AAAA,IACL;AAAA,IACA;AAAA,IACA,KAAI,0CAAU,eAAV,mBAAsB,WAAU,SAAY,EAAE,OAAO,SAAS,WAAW,MAAA,IAAU,CAAA;AAAA,IACvF,cAAc,CAAC,SAAiB;AAC9B,UAAI,YAAY,WAAW,UAAU,KAAK,MAAM;AAC9C,mBAAW,SAAS,OAAO,QAAQ,CAAC;AAAA,MACtC;AACA,iBAAW,UAAU,OAAO,KAAK,IAAI,MAAM,CAAC,IAAI,QAAQ,CAAC;AAAA,IAC3D;AAAA,IACA,kBAAkB,CAAC,SAAiB;AAClC,iBAAW,SAAS,OAAO,IAAI,CAAC;AAChC,iBAAW,UAAU,GAAG;AAAA,IAC1B;AAAA,EAAA;AAEJ;AAEO,SAAS,qBAAqB,QAAyB;AAC5D,SAAO,OAAO,YAAY,OAAO,QAAQ,MAAM,EAAE,OAAO,CAAC,CAAA,EAAG,KAAK,MAAM,UAAU,EAAE,CAAC;AACtF;AAEO,SAAS,oBACd,QACA,YACiB;AACjB,QAAM,kBAAkB,IAAI;AAAA,IAC1B,WACG,OAAO,CAAC,UAAU,MAAM,OAAO,UAAU,kBAAkB,KAAK,CAAC,EACjE,IAAI,CAAC,MAAM,EAAE,IAAI;AAAA,EAAA;AAEtB,QAAM,SAA0B,CAAA;AAChC,QAAM,OAAiB,CAAA;AAEvB,aAAW,CAAC,KAAK,KAAK,KAAK,OAAO,QAAQ,MAAM,GAAG;AACjD,QAAI,CAAC,MAAO;AACZ,QAAI,gBAAgB,IAAI,GAAG,GAAG;AAC5B,WAAK,KAAK,KAAK;AAAA,IACjB,OAAO;AACL,aAAO,GAAG,IAAI;AAAA,IAChB;AAAA,EACF;AAEA,MAAI,KAAK,SAAS,GAAG;AACnB,WAAO,OAAO,KAAK,KAAK,GAAG;AAAA,EAC7B;AAEA,SAAO;AACT;AAEO,SAAS,uBACd,YACA,QACA,WACA,UAAgC,CAAA,GACX;;AACrB,QAAM,cAAiC,CAAA;AACvC,QAAM,kBAAgB,aAAQ,WAAR,mBAAgB,YAAW,CAAA;AACjD,QAAM,mBAAmB,IAAI,IAAI,QAAQ,oBAAoB,CAAC,QAAQ,SAAS,QAAQ,CAAC;AACxF,QAAM,eAAe,QAAQ,gBAAgB,CAAA;AAC7C,QAAM,aAAa,QAAQ,cAAc;AAOzC,QAAM,aAAa,WAAW,KAAK,CAAC;;AAAM,aAAAA,MAAA,EAAE,UAAU,MAAZ,gBAAAA,IAAe,UAAS;AAAA,GAAO;AACzE,QAAM,cAAc,WAAW,KAAK,CAAC;;AAAM,aAAAA,MAAA,EAAE,UAAU,MAAZ,gBAAAA,IAAe,UAAS;AAAA,GAAQ;AAC3E,QAAM,0CAA0B,IAAA;AAChC,MAAI,WAAY,qBAAoB,IAAI,WAAW,IAAI;AACvD,MAAI,YAAa,qBAAoB,IAAI,YAAY,IAAI;AAIzD,QAAM,cAAc,WAAW;AAAA,IAC7B,CAAC,MAAA;;AAAM,eAAAA,MAAA,EAAE,UAAU,MAAZ,gBAAAA,IAAe,UAAS,YAAY,iBAAiB,IAAI,EAAE,EAAE;AAAA;AAAA,EAAA;AAEtE,QAAM,YAAY,IAAI,IAAI,mBAAmB;AAC7C,MAAI,YAAa,WAAU,IAAI,YAAY,IAAI;AAI/C,QAAM,iBAAiB,WAAW,KAAK,CAAC;;AAAM,aAAAA,MAAA,EAAE,UAAU,MAAZ,gBAAAA,IAAe,UAAS;AAAA,GAAW;AACjF,QAAM,eAAe,WAAW,KAAK,CAAC;;AAAM,aAAAA,MAAA,EAAE,UAAU,MAAZ,gBAAAA,IAAe,UAAS;AAAA,GAAS;AAC7E,QAAM,aACJ,kBACA,WAAW;AAAA,IACT,CAAC,UAAA;;AACC,8BAAiB,IAAI,MAAM,EAAE,KAC7B,MAAM,OAAO,aACbA,MAAA,cAAc,MAAM,IAAI,MAAxB,gBAAAA,IAA2B,UAAS;AAAA;AAAA,EAAA;AAE1C,QAAM,WACJ,gBACA,WAAW;AAAA,IACT,CAAC,UAAA;;AACC,8BAAiB,IAAI,MAAM,EAAE,KAC7B,MAAM,OAAO,aACbA,MAAA,cAAc,MAAM,IAAI,MAAxB,gBAAAA,IAA2B,UAAS;AAAA;AAAA,EAAA;AAE1C,QAAM,eAAe,cAAc,QAAQ,YAAY;AAEvD,aAAW,SAAS,YAAY;AAC9B,QAAI,CAAC,iBAAiB,IAAI,MAAM,EAAE,EAAG;AACrC,QAAI,UAAU,IAAI,MAAM,IAAI,EAAG;AAC/B,QAAI,iBAAiB,MAAM,UAAS,yCAAY,SAAQ,MAAM,UAAS,qCAAU,QAAO;AACtF;AAAA,IACF;AAEA,UAAM,WAAW,OAAO,UAAU,eAAe,KAAK,cAAc,MAAM,IAAI;AAC9E,QAAI,YAAY,WAAY;AAC5B,UAAM,QAAQ,WAAY,aAAa,MAAM,IAAI,KAAK,KAAO,OAAO,MAAM,IAAI,KAAK;AACnF,UAAM,UAAQ,mBAAc,MAAM,IAAI,MAAxB,mBAA2B,UAAS,UAAU,MAAM,IAAI;AACtE,UAAM,WAAW,CAAC,SAA2B;AAC3C,UAAI,SAAU;AACd,YAAM,cAAc,OAAO,SAAS,YAAa,OAAO,SAAS,UAAW;AAC5E,gBAAU,CAAC,aAAa,EAAE,GAAG,SAAS,CAAC,MAAM,IAAI,GAAG,YAAA,EAAc;AAAA,IACpE;AAEA,UAAM,SAAS,MAAM;AACrB,UAAM,eAAe,cAAc,MAAM,IAAI;AAE7C,SAAI,6CAAc,UAAS,kBAAkB,MAAM,OAAO,SAAS;AACjE,kBAAY,KAAK;AAAA,QACf,KAAK,MAAM;AAAA,QACX,MAAM;AAAA,QACN;AAAA,QACA,OAAO,sBAAsB,KAAK;AAAA,QAClC;AAAA,QACA,SAAS,4BAA4B,YAAY;AAAA,QACjD,UAAU,CAAC,SACT,UAAU,CAAC,aAAa;AAAA,UACtB,GAAG;AAAA,UACH,CAAC,MAAM,IAAI,GAAG,0BAA0B,IAAI;AAAA,QAAA,EAC5C;AAAA,MAAA,CACL;AACD;AAAA,IACF;AAEA,QAAI,iCAAQ,MAAM;AAChB,kBAAY,KAAK;AAAA,QACf,KAAK,MAAM;AAAA,QACX,MAAM;AAAA,QACN;AAAA,QACA;AAAA,QACA;AAAA,QACA,SAAS,OAAO,KAAK,IAAI,CAAC,UAAU;AAAA,UAClC,OAAO,OAAO,IAAI;AAAA,UAClB,OAAO,OAAO,IAAI;AAAA,QAAA,EAClB;AAAA,QACF,UAAU,CAAC,SAAS,SAAS,IAAI;AAAA,MAAA,CAClC;AACD;AAAA,IACF;AAEA,SAAI,6CAAc,UAAS,WAAU,iCAAQ,UAAS,WAAW;AAC/D,kBAAY,KAAK;AAAA,QACf,KAAK,MAAM;AAAA,QACX,MAAM;AAAA,QACN;AAAA,QACA,OAAO,UAAU;AAAA,QACjB;AAAA,QACA,UAAU,CAAC,SAAS,SAAS,IAAI;AAAA,MAAA,CAClC;AACD;AAAA,IACF;AAEA,QAAI,gBAAgB,QAAQ,MAAM,OAAO,SAAS;AAChD,UAAI,aAAa,OAAO;AACtB,oBAAY,KAAK;AAAA,UACf,KAAK,MAAM;AAAA,UACX,MAAM;AAAA,UACN;AAAA,UACA,OAAO,iBAAiB,KAAK;AAAA,UAC7B;AAAA,UACA,SAAS,4BAA4B,YAAY;AAAA,UACjD,aAAa,MAAM,eAAe;AAAA,UAClC,UAAU,CAAC,SACT,UAAU,CAAC,aAAa,EAAE,GAAG,SAAS,CAAC,MAAM,IAAI,GAAG,KAAK,KAAK,GAAG,IAAI;AAAA,QAAA,CACxE;AACD;AAAA,MACF;AAEA,kBAAY,KAAK;AAAA,QACf,KAAK,MAAM;AAAA,QACX,MAAM;AAAA,QACN;AAAA,QACA;AAAA,QACA;AAAA,QACA,SAAS,4BAA4B,YAAY;AAAA,QACjD,aAAa,MAAM,eAAe;AAAA,QAClC,WACE,aAAa,SAAS,WAClB,WACA,aAAa,SAAS,SACpB,SACA;AAAA,QACR,UAAU,CAAC,SAAS,SAAS,IAAI;AAAA,MAAA,CAClC;AACD;AAAA,IACF;AAEA,gBAAY,KAAK;AAAA,MACf,KAAK,MAAM;AAAA,MACX,MAAM;AAAA,MACN;AAAA,MACA;AAAA,MACA;AAAA,MACA,aAAa,MAAM,eAAe;AAAA,MAClC,UAAU,CAAC,SAAS,SAAS,IAAI;AAAA,IAAA,CAClC;AAAA,EACH;AAEA,QAAM,SAA8B,EAAE,SAAS,YAAA;AAC/C,MAAI,aAAa;AACf,UAAM,iBAAiB,OAAO,UAAU,eAAe,KAAK,cAAc,YAAY,IAAI;AAC1F,UAAM,cAAc,iBACf,aAAa,YAAY,IAAI,KAAK,KAClC,OAAO,YAAY,IAAI,KAAK;AACjC,WAAO,SAAS;AAAA,MACd,OAAO;AAAA,MACP,UAAU,CAAC,SAAS;AAClB,YAAI,eAAgB;AACpB,kBAAU,CAAC,aAAa,EAAE,GAAG,SAAS,CAAC,YAAY,IAAI,GAAG,KAAA,EAAO;AAAA,MACnE;AAAA,MACA,GAAI,YAAY,cAAc,EAAE,aAAa,YAAY,YAAA,IAAgB,CAAA;AAAA,MACzE,aAAW,mBAAc,YAAY,IAAI,MAA9B,mBAAiC,UAAS,UAAU,YAAY,IAAI;AAAA,IAAA;AAAA,EAEnF;AACA,MAAI,cAAc,aAAa;AAC7B,WAAO,aAAa;AAAA,MAClB,YAAY,WAAW;AAAA,MACvB,aAAa,YAAY;AAAA,MACzB,YAAY,OAAO,WAAW,IAAI,KAAK;AAAA,MACvC,aAAa,OAAO,YAAY,IAAI,KAAK;AAAA,MACzC,UAAU,CAAC,SAAS,UAAU,CAAC,aAAa,EAAE,GAAG,SAAS,CAAC,WAAW,IAAI,GAAG,OAAO;AAAA,MACpF,WAAW,CAAC,SAAS,UAAU,CAAC,aAAa,EAAE,GAAG,SAAS,CAAC,YAAY,IAAI,GAAG,OAAO;AAAA,IAAA;AAAA,EAE1F;AACA,MAAI,gBAAgB,cAAc,QAAQ,YAAY,MAAM;AAC1D,UAAM,iBAAiB,cAAc,WAAW,IAAI;AACpD,UAAM,eAAe,cAAc,SAAS,IAAI;AAChD,UAAM,YAAY,kBAAkB;AACpC,WAAO,YAAY;AAAA,MACjB,MAAM,OAAO,WAAW,IAAI,KAAK;AAAA,MACjC,IAAI,OAAO,SAAS,IAAI,KAAK;AAAA,MAC7B,SAAS,CAAC,MAAM,OACd,UAAU,CAAC,aAAa;AAAA,QACtB,GAAG;AAAA,QACH,CAAC,WAAW,IAAI,GAAG;AAAA,QACnB,CAAC,SAAS,IAAI,GAAG;AAAA,MAAA,EACjB;AAAA,MACJ,IAAI,uCAAW,WAAU,EAAE,SAAS,UAAU,QAAA,IAAY,CAAA;AAAA,MAC1D,IAAI,uCAAW,iBAAgB,SAAY,EAAE,aAAa,UAAU,YAAA,IAAgB,CAAA;AAAA,MACpF,IAAI,uCAAW,YAAW,EAAE,UAAU,UAAU,SAAA,IAAa,CAAA;AAAA,MAC7D,IAAI,uCAAW,aAAY,EAAE,WAAW,UAAU,UAAA,IAAc,CAAA;AAAA,MAChE,GAAI,WAAW,cAAc,EAAE,iBAAiB,WAAW,YAAA,IAAgB,CAAA;AAAA,MAC3E,GAAI,SAAS,cAAc,EAAE,eAAe,SAAS,YAAA,IAAgB,CAAA;AAAA,IAAC;AAAA,EAE1E;AAEA,SAAO;AACT;AAEO,SAAS,mBAAsB,OAAU,SAAiB;AAC/D,QAAM,CAAC,WAAW,YAAY,IAAI,SAAS,KAAK;AAEhD,YAAU,MAAM;AACd,UAAM,YAAY,OAAO,WAAW,MAAM,aAAa,KAAK,GAAG,OAAO;AACtE,WAAO,MAAM,OAAO,aAAa,SAAS;AAAA,EAC5C,GAAG,CAAC,SAAS,KAAK,CAAC;AAEnB,SAAO;AACT;AAEO,SAAS,sBAAsB,OAAyD;AAC7F,QAAM,SAAmD,CAAA;AACzD,aAAW,QAAQ,iBAAiB,KAAK,GAAG;AAC1C,QAAI,KAAK,WAAW,GAAG,KAAK,KAAK,SAAS,GAAG;AAC3C,aAAO,KAAK,MAAM,CAAC,CAAC,IAAI;AAAA,IAC1B,OAAO;AACL,aAAO,IAAI,IAAI;AAAA,IACjB;AAAA,EACF;AACA,SAAO;AACT;AAEO,SAAS,0BAA0B,OAAyD;AACjG,SAAO,OAAO,QAAQ,KAAK,EACxB,QAAQ,CAAC,CAAC,KAAK,IAAI,MAAM;AACxB,QAAI,SAAS,UAAW,QAAO,CAAC,GAAG;AACnC,QAAI,SAAS,UAAW,QAAO,CAAC,IAAI,GAAG,EAAE;AACzC,WAAO,CAAA;AAAA,EACT,CAAC,EACA,KAAK,GAAG;AACb;AAEA,SAAS,iBAAiB,OAAe;AACvC,SAAO,MACJ,MAAM,GAAG,EACT,IAAI,CAAC,SAAS,KAAK,KAAA,CAAM,EACzB,OAAO,OAAO;AACnB;AAEA,SAAS,YAAY,OAA+C;AAClE,QAAM,SAAS,SAAS,SAAS,IAAI,EAAE;AACvC,SAAO,OAAO,SAAS,MAAM,KAAK,SAAS,IAAI,SAAS;AAC1D;AAEA,SAAS,eAAe,OAA+C;AACrE,QAAM,SAAS,SAAS,SAAS,IAAI,EAAE;AACvC,SAAO,OAAO,SAAS,MAAM,KAAK,UAAU,IAAI,SAAS;AAC3D;AAEA,SAAS,4BAA4B,QAA+B;AAClE,QAAM,6BAAa,IAAA;AAEnB,aAAW,CAAC,OAAO,IAAI,KAAK,OAAO,QAAQ,OAAO,WAAW,CAAA,CAAE,GAAG;AAChE,WAAO,IAAI,OAAO;AAAA,MAChB,OAAO,sBAAsB,IAAI,KAAK;AAAA,MACtC,OAAO,sBAAsB,IAAI,KAAK;AAAA,IAAA,CACvC;AAAA,EACH;AAEA,aAAW,CAAC,OAAO,IAAI,KAAK,OAAO,QAAQ,OAAO,YAAY,CAAA,CAAE,GAAG;AACjE,QAAI,CAAC,OAAO,IAAI,KAAK,GAAG;AACtB,aAAO,IAAI,OAAO;AAAA,QAChB,OAAO,sBAAsB,IAAI,KAAK;AAAA,QACtC,OAAO,sBAAsB,IAAI,KAAK;AAAA,MAAA,CACvC;AAAA,IACH;AAAA,EACF;AAEA,SAAO,MAAM,KAAK,OAAO,QAAA,CAAS,EAAE,IAAI,CAAC,CAAC,OAAO,IAAI,OAAO;AAAA,IAC1D;AAAA,IACA,OAAO,KAAK,SAAS;AAAA,IACrB,OAAO,KAAK,SAAS;AAAA,EAAA,EACrB;AACJ;AASA,SAAS,sBAAsB,MAAsD;AACnF,MAAI,QAAQ,KAAM,QAAO;AACzB,MAAI,KAAK,MAAO,QAAO,KAAK;AAC5B,MAAI,KAAK,KAAM,QAAO,KAAK;AAC3B,UAAQ,KAAK,YAAY,CAAA,GAAI,IAAI,CAAC,UAAU,sBAAsB,KAAK,CAAC,EAAE,KAAK,EAAE;AACnF;"}
|
|
1
|
+
{"version":3,"file":"formMetadata.js","sources":["../../src/rpc/formMetadata.ts"],"sourcesContent":["import { useEffect, useState, type Dispatch, type SetStateAction } from \"react\";\nimport type {\n FilterBarFilter,\n FilterBarMultiFilterMode,\n FilterBarRangeProps,\n FilterBarSearchProps,\n} from \"../components/FilterBar\";\nimport type { DataTablePagination } from \"../data/DataTable\";\nimport type {\n ExecutionResponse,\n OpenAPIParameter,\n OperationLookupFilter,\n OperationLookupResponse,\n} from \"./types\";\nimport { isPositionalParam, parameterPlaceholder } from \"./types\";\n\nexport type ParameterValues = Record<string, string>;\nexport type ParameterValuesSetter = Dispatch<SetStateAction<ParameterValues>>;\n\n// ParameterPagination plumbs limit/offset query parameters into the\n// DataTable's pagination footer. The UI exposes both as the\n// {pageSize, pageIndex} tuple but here we keep raw string limit/offset\n// values so the executor sees exactly what the operation declared.\nexport type ParameterPagination = {\n limitParam: string; // parameter name on the operation, e.g. \"limit\"\n offsetParam: string;\n limitValue: string;\n offsetValue: string;\n setLimit: (next: string) => void;\n setOffset: (next: string) => void;\n};\n\nexport type ParameterFormConfig = {\n filters: FilterBarFilter[];\n search?: FilterBarSearchProps;\n timeRange?: FilterBarRangeProps;\n pagination?: ParameterPagination;\n};\nexport type ParameterFormOptions = {\n includeLocations?: OpenAPIParameter[\"in\"][];\n lookup?: OperationLookupResponse | undefined;\n lockedValues?: ParameterValues | undefined;\n hideLocked?: boolean;\n};\n\nexport function titleCase(value: string) {\n return value\n .split(/[-_]/)\n .filter(Boolean)\n .map((part) => part.charAt(0).toUpperCase() + part.slice(1))\n .join(\" \");\n}\n\nexport function defaultValueForParameter(param: OpenAPIParameter, method: string): string {\n if (method.toUpperCase() === \"GET\" && param.in === \"query\" && !param.required) {\n return \"\";\n }\n const fallback = param.in === \"path\" ? \"\" : undefined;\n const value = param.schema?.default ?? fallback;\n if (typeof value === \"boolean\") {\n return value ? \"true\" : \"false\";\n }\n if (Array.isArray(value) || (value != null && typeof value === \"object\")) {\n return \"\";\n }\n if (value == null) {\n return \"\";\n }\n return String(value);\n}\n\nexport function buildInitialParameterValues(\n parameters: OpenAPIParameter[],\n method: string,\n lockedValues: ParameterValues = {},\n initialValues: ParameterValues = {},\n): ParameterValues {\n const values = Object.fromEntries(\n parameters.map((param) => [param.name, defaultValueForParameter(param, method)]),\n );\n return { ...values, ...initialValues, ...lockedValues };\n}\n\nexport function dataTablePaginationFromForm(\n pagination: ParameterPagination | undefined,\n response: Pick<ExecutionResponse, \"pagination\"> | null | undefined,\n): DataTablePagination | undefined {\n if (!pagination) return undefined;\n\n const pageSize = positiveInt(pagination.limitValue) ?? response?.pagination?.limit ?? 25;\n const offset = nonNegativeInt(pagination.offsetValue) ?? response?.pagination?.offset ?? 0;\n const page = Math.floor(offset / pageSize);\n\n return {\n page,\n pageSize,\n ...(response?.pagination?.total !== undefined ? { total: response.pagination.total } : {}),\n onPageChange: (next: number) => {\n if (positiveInt(pagination.limitValue) == null) {\n pagination.setLimit(String(pageSize));\n }\n pagination.setOffset(String(Math.max(next, 0) * pageSize));\n },\n onPageSizeChange: (next: number) => {\n pagination.setLimit(String(next));\n pagination.setOffset(\"0\");\n },\n };\n}\n\nexport function pruneParameterValues(values: ParameterValues) {\n return Object.fromEntries(Object.entries(values).filter(([, value]) => value !== \"\"));\n}\n\nexport function packParameterValues(\n values: ParameterValues,\n parameters: OpenAPIParameter[],\n): ParameterValues {\n const positionalNames = new Set(\n parameters\n .filter((param) => param.in !== \"path\" && isPositionalParam(param))\n .map((p) => p.name),\n );\n const params: ParameterValues = {};\n const args: string[] = [];\n\n for (const [key, value] of Object.entries(values)) {\n if (!value) continue;\n if (positionalNames.has(key)) {\n args.push(value);\n } else {\n params[key] = value;\n }\n }\n\n if (args.length > 0) {\n params.args = args.join(\",\");\n }\n\n return params;\n}\n\nexport function parametersToFormConfig(\n parameters: OpenAPIParameter[],\n values: ParameterValues,\n setValues: ParameterValuesSetter,\n options: ParameterFormOptions = {},\n): ParameterFormConfig {\n const emitFilters: FilterBarFilter[] = [];\n const lookupFilters = options.lookup?.filters ?? {};\n const includeLocations = new Set(options.includeLocations ?? [\"path\", \"query\", \"header\"]);\n const lockedValues = options.lockedValues ?? {};\n const hideLocked = options.hideLocked ?? false;\n\n // Pull limit/offset out of the filter loop entirely — they drive pagination,\n // not filter pills. Roles come from server-side `paramRole` (see\n // clicky/rpc/openapi.go); the older \"named limit on a GET\" heuristic is\n // intentionally not duplicated here so the server stays the single source\n // of truth for parameter classification.\n const limitParam = parameters.find((p) => p[\"x-clicky\"]?.role === \"limit\");\n const offsetParam = parameters.find((p) => p[\"x-clicky\"]?.role === \"offset\");\n const paginationOmitNames = new Set<string>();\n if (limitParam) paginationOmitNames.add(limitParam.name);\n if (offsetParam) paginationOmitNames.add(offsetParam.name);\n\n // The search-role param drives the FilterBar's dedicated search input rather\n // than a filter chip; pull it out of the chip loop the same way pagination is.\n const searchParam = parameters.find(\n (p) => p[\"x-clicky\"]?.role === \"search\" && includeLocations.has(p.in),\n );\n const omitNames = new Set(paginationOmitNames);\n if (searchParam) omitNames.add(searchParam.name);\n\n // Time-range first looks for server-stamped roles, then falls back to the\n // existing lookup-driven \"from\"/\"to\" detection so older specs keep working.\n const roleRangeStart = parameters.find((p) => p[\"x-clicky\"]?.role === \"time-from\");\n const roleRangeEnd = parameters.find((p) => p[\"x-clicky\"]?.role === \"time-to\");\n const rangeStart =\n roleRangeStart ??\n parameters.find(\n (param) =>\n includeLocations.has(param.in) &&\n param.in === \"query\" &&\n lookupFilters[param.name]?.type === \"from\",\n );\n const rangeEnd =\n roleRangeEnd ??\n parameters.find(\n (param) =>\n includeLocations.has(param.in) &&\n param.in === \"query\" &&\n lookupFilters[param.name]?.type === \"to\",\n );\n const hasTimeRange = rangeStart != null && rangeEnd != null;\n\n for (const param of parameters) {\n if (!includeLocations.has(param.in)) continue;\n if (omitNames.has(param.name)) continue;\n if (hasTimeRange && (param.name === rangeStart?.name || param.name === rangeEnd?.name)) {\n continue;\n }\n\n const disabled = Object.prototype.hasOwnProperty.call(lockedValues, param.name);\n if (disabled && hideLocked) continue;\n const value = disabled ? (lockedValues[param.name] ?? \"\") : (values[param.name] ?? \"\");\n const label = lookupFilters[param.name]?.label ?? titleCase(param.name);\n const onChange = (next: string | boolean) => {\n if (disabled) return;\n const stringValue = typeof next === \"boolean\" ? (next ? \"true\" : \"false\") : next;\n setValues((current) => ({ ...current, [param.name]: stringValue }));\n };\n\n const schema = param.schema;\n const lookupFilter = lookupFilters[param.name];\n\n if (lookupFilter?.type === \"multi-filter\" && param.in === \"query\") {\n emitFilters.push({\n key: param.name,\n kind: \"multi\",\n label,\n value: parseMultiFilterValue(value),\n disabled,\n options: lookupOptionsToFieldOptions(lookupFilter),\n onChange: (next) =>\n setValues((current) => ({\n ...current,\n [param.name]: serializeMultiFilterValue(next),\n })),\n });\n continue;\n }\n\n if (schema?.enum) {\n emitFilters.push({\n key: param.name,\n kind: \"enum\",\n label,\n value,\n disabled,\n options: schema.enum.map((item) => ({\n value: String(item),\n label: String(item),\n })),\n onChange: (next) => onChange(next),\n });\n continue;\n }\n\n if (lookupFilter?.type === \"bool\" || schema?.type === \"boolean\") {\n emitFilters.push({\n key: param.name,\n kind: \"boolean\",\n label,\n value: value === \"true\",\n disabled,\n onChange: (next) => onChange(next),\n });\n continue;\n }\n\n if (lookupFilter != null && param.in === \"query\") {\n if (lookupFilter.multi) {\n emitFilters.push({\n key: param.name,\n kind: \"lookup-multi\",\n label,\n value: splitCommaValues(value),\n disabled,\n options: lookupOptionsToFieldOptions(lookupFilter),\n placeholder: parameterPlaceholder(param) ?? \"value-1, value-2\",\n onChange: (next) =>\n setValues((current) => ({ ...current, [param.name]: next.join(\",\") })),\n });\n continue;\n }\n\n emitFilters.push({\n key: param.name,\n kind: \"lookup\",\n label,\n value,\n disabled,\n options: lookupOptionsToFieldOptions(lookupFilter),\n placeholder: parameterPlaceholder(param) ?? label,\n inputType:\n lookupFilter.type === \"number\"\n ? \"number\"\n : lookupFilter.type === \"date\"\n ? \"date\"\n : \"text\",\n onChange: (next) => onChange(next),\n });\n continue;\n }\n\n emitFilters.push({\n key: param.name,\n kind: \"text\",\n label,\n value,\n disabled,\n placeholder: parameterPlaceholder(param) ?? label,\n onChange: (next) => onChange(next),\n });\n }\n\n const config: ParameterFormConfig = { filters: emitFilters };\n if (searchParam) {\n const searchDisabled = Object.prototype.hasOwnProperty.call(lockedValues, searchParam.name);\n const searchValue = searchDisabled\n ? (lockedValues[searchParam.name] ?? \"\")\n : (values[searchParam.name] ?? \"\");\n const searchPlaceholder = parameterPlaceholder(searchParam);\n config.search = {\n value: searchValue,\n onChange: (next) => {\n if (searchDisabled) return;\n setValues((current) => ({ ...current, [searchParam.name]: next }));\n },\n ...(searchPlaceholder ? { placeholder: searchPlaceholder } : {}),\n ariaLabel: lookupFilters[searchParam.name]?.label ?? titleCase(searchParam.name),\n };\n }\n if (limitParam && offsetParam) {\n config.pagination = {\n limitParam: limitParam.name,\n offsetParam: offsetParam.name,\n limitValue: values[limitParam.name] ?? \"\",\n offsetValue: values[offsetParam.name] ?? \"\",\n setLimit: (next) => setValues((current) => ({ ...current, [limitParam.name]: next })),\n setOffset: (next) => setValues((current) => ({ ...current, [offsetParam.name]: next })),\n };\n }\n if (hasTimeRange && rangeStart != null && rangeEnd != null) {\n const rangeStartMeta = lookupFilters[rangeStart.name];\n const rangeEndMeta = lookupFilters[rangeEnd.name];\n const rangeMeta = rangeStartMeta ?? rangeEndMeta;\n config.timeRange = {\n from: values[rangeStart.name] ?? \"\",\n to: values[rangeEnd.name] ?? \"\",\n onApply: (from, to) =>\n setValues((current) => ({\n ...current,\n [rangeStart.name]: from,\n [rangeEnd.name]: to,\n })),\n ...(rangeMeta?.presets ? { presets: rangeMeta.presets } : {}),\n ...(rangeMeta?.timeEnabled !== undefined ? { timeEnabled: rangeMeta.timeEnabled } : {}),\n ...(rangeMeta?.timeZone ? { timeZone: rangeMeta.timeZone } : {}),\n ...(rangeMeta?.timeZones ? { timeZones: rangeMeta.timeZones } : {}),\n ...(rangeStart.description ? { fromPlaceholder: rangeStart.description } : {}),\n ...(rangeEnd.description ? { toPlaceholder: rangeEnd.description } : {}),\n };\n }\n\n return config;\n}\n\nexport function useDebouncedRecord<T>(value: T, delayMs: number) {\n const [debounced, setDebounced] = useState(value);\n\n useEffect(() => {\n const timeoutId = window.setTimeout(() => setDebounced(value), delayMs);\n return () => window.clearTimeout(timeoutId);\n }, [delayMs, value]);\n\n return debounced;\n}\n\nexport function parseMultiFilterValue(value: string): Record<string, FilterBarMultiFilterMode> {\n const parsed: Record<string, FilterBarMultiFilterMode> = {};\n for (const item of splitCommaValues(value)) {\n if (item.startsWith(\"!\") && item.length > 1) {\n parsed[item.slice(1)] = \"exclude\";\n } else {\n parsed[item] = \"include\";\n }\n }\n return parsed;\n}\n\nexport function serializeMultiFilterValue(value: Record<string, FilterBarMultiFilterMode>): string {\n return Object.entries(value)\n .flatMap(([key, mode]) => {\n if (mode === \"include\") return [key];\n if (mode === \"exclude\") return [`!${key}`];\n return [];\n })\n .join(\",\");\n}\n\nfunction splitCommaValues(value: string) {\n return value\n .split(\",\")\n .map((item) => item.trim())\n .filter(Boolean);\n}\n\nfunction positiveInt(value: string | undefined): number | undefined {\n const parsed = parseInt(value ?? \"\", 10);\n return Number.isFinite(parsed) && parsed > 0 ? parsed : undefined;\n}\n\nfunction nonNegativeInt(value: string | undefined): number | undefined {\n const parsed = parseInt(value ?? \"\", 10);\n return Number.isFinite(parsed) && parsed >= 0 ? parsed : undefined;\n}\n\nfunction lookupOptionsToFieldOptions(filter: OperationLookupFilter) {\n const merged = new Map<string, { label?: string; title?: string }>();\n\n for (const [value, node] of Object.entries(filter.options ?? {})) {\n merged.set(value, {\n label: clickyNodeToPlainText(node) || value,\n title: clickyNodeToPlainText(node) || value,\n });\n }\n\n for (const [value, node] of Object.entries(filter.selected ?? {})) {\n if (!merged.has(value)) {\n merged.set(value, {\n label: clickyNodeToPlainText(node) || value,\n title: clickyNodeToPlainText(node) || value,\n });\n }\n }\n\n return Array.from(merged.entries()).map(([value, meta]) => ({\n value,\n label: meta.label ?? value,\n title: meta.title ?? value,\n }));\n}\n\ntype PlainTextClickyNode = {\n plain?: string;\n text?: string;\n children?: PlainTextClickyNode[];\n tooltip?: { plain?: string; text?: string };\n};\n\nfunction clickyNodeToPlainText(node: PlainTextClickyNode | null | undefined): string {\n if (node == null) return \"\";\n if (node.plain) return node.plain;\n if (node.text) return node.text;\n return (node.children ?? []).map((child) => clickyNodeToPlainText(child)).join(\"\");\n}\n"],"names":["_a"],"mappings":"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"}
|
package/dist/rpc/types.cjs
CHANGED
|
@@ -1,8 +1,12 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, Symbol.toStringTag, { value: "Module" });
|
|
3
|
+
function parameterPlaceholder(param) {
|
|
4
|
+
return param["x-clicky-placeholder"] ?? param.placeholder;
|
|
5
|
+
}
|
|
3
6
|
function isPositionalParam(p) {
|
|
4
7
|
var _a;
|
|
5
8
|
return p.name === "args" || ((_a = p.description) == null ? void 0 : _a.toLowerCase().includes("positional argument")) === true;
|
|
6
9
|
}
|
|
7
10
|
exports.isPositionalParam = isPositionalParam;
|
|
11
|
+
exports.parameterPlaceholder = parameterPlaceholder;
|
|
8
12
|
//# sourceMappingURL=types.cjs.map
|
package/dist/rpc/types.cjs.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"types.cjs","sources":["../../src/rpc/types.ts"],"sourcesContent":["import type { ClickyNode } from \"../data/Clicky\";\nimport type { TimeRangePresetGroup } from \"../components/TimeRange\";\n\nexport interface ExecutionRequest {\n args?: string[];\n flags?: Record<string, string>;\n}\n\nexport interface ExecutionPagination {\n total?: number;\n limit?: number;\n offset?: number;\n}\n\nexport interface ExecutionResponse {\n success: boolean;\n message?: string;\n output?: string;\n stdout?: string;\n stderr?: string;\n exit_code: number;\n error?: string;\n cli?: string;\n input?: ExecutionRequest;\n contentType?: string;\n requestUrl?: string;\n responseHeaders?: Record<string, string>;\n pagination?: ExecutionPagination;\n blob?: Blob;\n parsed?: unknown;\n}\n\nexport interface OpenAPISchema {\n type?: string;\n format?: string;\n default?: unknown;\n enum?: unknown[];\n description?: string;\n properties?: Record<string, OpenAPISchema>;\n}\n\n// ClickyParameterRole tells the UI which widget owns a parameter:\n// \"search\" — render as the FilterBar's dedicated search input\n// \"filter\" — render as a FilterBar chip on the DataTable\n// \"limit\" — feed into DataTable pagination's pageSize\n// \"offset\" — feed into DataTable pagination's page (or skip)\n// \"time-from\" — left edge of a time-range picker\n// \"time-to\" — right edge of a time-range picker\n// Set server-side by clicky's converter (see paramRole in clicky/rpc/openapi.go).\nexport type ClickyParameterRole =\n | \"search\"\n | \"filter\"\n | \"limit\"\n | \"offset\"\n | \"time-from\"\n | \"time-to\";\n\nexport interface ClickyParameterMeta {\n role?: ClickyParameterRole;\n}\n\nexport interface OpenAPIParameter {\n name: string;\n in: \"query\" | \"path\" | \"header\";\n description?: string;\n required?: boolean;\n schema?: OpenAPISchema;\n \"x-clicky\"?: ClickyParameterMeta;\n}\n\nexport interface OpenAPIOperation {\n tags?: string[];\n summary?: string;\n description?: string;\n operationId?: string;\n parameters?: OpenAPIParameter[];\n requestBody?: {\n content?: Record<string, { schema?: OpenAPISchema }>;\n };\n responses: Record<string, unknown>;\n \"x-clicky\"?: ClickyOperationMeta;\n}\n\nexport interface OpenAPISpec {\n openapi: string;\n info: { title: string; description?: string; version: string };\n paths: Record<string, Record<string, OpenAPIOperation>>;\n tags?: Array<{ name: string; description?: string }>;\n \"x-clicky\"?: ClickySpecMeta;\n}\n\nexport interface ResolvedOperation {\n path: string;\n method: string;\n operation: OpenAPIOperation;\n}\n\nexport interface DomainDefinition {\n key: string;\n title: string;\n description: string;\n emptyTitle?: string;\n emptyDescription?: string;\n}\n\nexport interface ClickySpecMeta {\n surfaces?: ClickySurface[];\n}\n\nexport interface ClickySurface {\n key: string;\n entity: string;\n title: string;\n parent?: string;\n admin?: boolean;\n description?: string;\n}\n\nexport interface ClickyOperationMeta {\n command?: string;\n surface?: string;\n verb: \"list\" | \"get\" | \"create\" | \"update\" | \"delete\" | \"action\";\n scope: \"collection\" | \"entity\";\n actionName?: string;\n idParam?: string;\n supportsLookup?: boolean;\n supportsFilterMode?: boolean;\n}\n\nexport type OperationLookupFilterType = \"bool\" | \"number\" | \"date\" | \"from\" | \"to\" | \"multi-filter\";\n\nexport interface OperationLookupFilter {\n label?: string;\n options?: Record<string, ClickyNode>;\n selected?: Record<string, ClickyNode>;\n multi?: boolean;\n type?: OperationLookupFilterType;\n /** True when `options` is only the head of a larger set (server-side capped). */\n truncated?: boolean;\n /** True distinct count behind a truncated option set; drives \"… and N more\". */\n total?: number;\n presets?: Array<{ label: string; from: string; to: string } | TimeRangePresetGroup>;\n timeEnabled?: boolean;\n timeZone?: string;\n timeZones?: string[];\n}\n\nexport interface OperationLookupResponse {\n filters: Record<string, OperationLookupFilter>;\n}\n\nexport function isPositionalParam(p: OpenAPIParameter): boolean {\n return p.name === \"args\" || p.description?.toLowerCase().includes(\"positional argument\") === true;\n}\n"],"names":[],"mappings":";;
|
|
1
|
+
{"version":3,"file":"types.cjs","sources":["../../src/rpc/types.ts"],"sourcesContent":["import type { ClickyNode } from \"../data/Clicky\";\nimport type { TimeRangePresetGroup } from \"../components/TimeRange\";\n\nexport interface ExecutionRequest {\n args?: string[];\n flags?: Record<string, string>;\n}\n\nexport interface ExecutionPagination {\n total?: number;\n limit?: number;\n offset?: number;\n}\n\nexport interface ExecutionResponse {\n success: boolean;\n message?: string;\n output?: string;\n stdout?: string;\n stderr?: string;\n exit_code: number;\n error?: string;\n cli?: string;\n input?: ExecutionRequest;\n contentType?: string;\n requestUrl?: string;\n responseHeaders?: Record<string, string>;\n pagination?: ExecutionPagination;\n blob?: Blob;\n parsed?: unknown;\n}\n\nexport interface OpenAPISchema {\n type?: string;\n format?: string;\n default?: unknown;\n enum?: unknown[];\n description?: string;\n properties?: Record<string, OpenAPISchema>;\n}\n\n// ClickyParameterRole tells the UI which widget owns a parameter:\n// \"search\" — render as the FilterBar's dedicated search input\n// \"filter\" — render as a FilterBar chip on the DataTable\n// \"limit\" — feed into DataTable pagination's pageSize\n// \"offset\" — feed into DataTable pagination's page (or skip)\n// \"time-from\" — left edge of a time-range picker\n// \"time-to\" — right edge of a time-range picker\n// Set server-side by clicky's converter (see paramRole in clicky/rpc/openapi.go).\nexport type ClickyParameterRole =\n | \"search\"\n | \"filter\"\n | \"limit\"\n | \"offset\"\n | \"time-from\"\n | \"time-to\";\n\nexport interface ClickyParameterMeta {\n role?: ClickyParameterRole;\n}\n\nexport interface OpenAPIParameter {\n name: string;\n in: \"query\" | \"path\" | \"header\";\n description?: string;\n required?: boolean;\n schema?: OpenAPISchema;\n /** Hint text shown inside the empty input. Distinct from `description`,\n * which is help text and must NOT be used as a placeholder. */\n placeholder?: string;\n \"x-clicky\"?: ClickyParameterMeta;\n /** Vendor-extension placeholder, set server-side by clicky's converter.\n * Takes precedence over `placeholder` when both are present. */\n \"x-clicky-placeholder\"?: string;\n}\n\n/** Resolves the input placeholder for a parameter, drawing ONLY from explicit\n * placeholder fields — never from `description` (help text). Returns undefined\n * when no placeholder is declared so callers can apply their own fallback. */\nexport function parameterPlaceholder(param: OpenAPIParameter): string | undefined {\n return param[\"x-clicky-placeholder\"] ?? param.placeholder;\n}\n\nexport interface OpenAPIOperation {\n tags?: string[];\n summary?: string;\n description?: string;\n operationId?: string;\n parameters?: OpenAPIParameter[];\n requestBody?: {\n content?: Record<string, { schema?: OpenAPISchema }>;\n };\n responses: Record<string, unknown>;\n \"x-clicky\"?: ClickyOperationMeta;\n}\n\nexport interface OpenAPISpec {\n openapi: string;\n info: { title: string; description?: string; version: string };\n paths: Record<string, Record<string, OpenAPIOperation>>;\n tags?: Array<{ name: string; description?: string }>;\n \"x-clicky\"?: ClickySpecMeta;\n}\n\nexport interface ResolvedOperation {\n path: string;\n method: string;\n operation: OpenAPIOperation;\n}\n\nexport interface DomainDefinition {\n key: string;\n title: string;\n description: string;\n emptyTitle?: string;\n emptyDescription?: string;\n}\n\nexport interface ClickySpecMeta {\n surfaces?: ClickySurface[];\n}\n\nexport interface ClickySurface {\n key: string;\n entity: string;\n title: string;\n parent?: string;\n admin?: boolean;\n description?: string;\n}\n\nexport interface ClickyOperationMeta {\n command?: string;\n surface?: string;\n verb: \"list\" | \"get\" | \"create\" | \"update\" | \"delete\" | \"action\";\n scope: \"collection\" | \"entity\";\n actionName?: string;\n idParam?: string;\n supportsLookup?: boolean;\n supportsFilterMode?: boolean;\n}\n\nexport type OperationLookupFilterType = \"bool\" | \"number\" | \"date\" | \"from\" | \"to\" | \"multi-filter\";\n\nexport interface OperationLookupFilter {\n label?: string;\n options?: Record<string, ClickyNode>;\n selected?: Record<string, ClickyNode>;\n multi?: boolean;\n type?: OperationLookupFilterType;\n /** True when `options` is only the head of a larger set (server-side capped). */\n truncated?: boolean;\n /** True distinct count behind a truncated option set; drives \"… and N more\". */\n total?: number;\n presets?: Array<{ label: string; from: string; to: string } | TimeRangePresetGroup>;\n timeEnabled?: boolean;\n timeZone?: string;\n timeZones?: string[];\n}\n\nexport interface OperationLookupResponse {\n filters: Record<string, OperationLookupFilter>;\n}\n\nexport function isPositionalParam(p: OpenAPIParameter): boolean {\n return p.name === \"args\" || p.description?.toLowerCase().includes(\"positional argument\") === true;\n}\n"],"names":[],"mappings":";;AA+EO,SAAS,qBAAqB,OAA6C;AAChF,SAAO,MAAM,sBAAsB,KAAK,MAAM;AAChD;AAmFO,SAAS,kBAAkB,GAA8B;;AAC9D,SAAO,EAAE,SAAS,YAAU,OAAE,gBAAF,mBAAe,cAAc,SAAS,4BAA2B;AAC/F;;;"}
|
package/dist/rpc/types.d.ts
CHANGED
|
@@ -44,8 +44,18 @@ export interface OpenAPIParameter {
|
|
|
44
44
|
description?: string;
|
|
45
45
|
required?: boolean;
|
|
46
46
|
schema?: OpenAPISchema;
|
|
47
|
+
/** Hint text shown inside the empty input. Distinct from `description`,
|
|
48
|
+
* which is help text and must NOT be used as a placeholder. */
|
|
49
|
+
placeholder?: string;
|
|
47
50
|
"x-clicky"?: ClickyParameterMeta;
|
|
51
|
+
/** Vendor-extension placeholder, set server-side by clicky's converter.
|
|
52
|
+
* Takes precedence over `placeholder` when both are present. */
|
|
53
|
+
"x-clicky-placeholder"?: string;
|
|
48
54
|
}
|
|
55
|
+
/** Resolves the input placeholder for a parameter, drawing ONLY from explicit
|
|
56
|
+
* placeholder fields — never from `description` (help text). Returns undefined
|
|
57
|
+
* when no placeholder is declared so callers can apply their own fallback. */
|
|
58
|
+
export declare function parameterPlaceholder(param: OpenAPIParameter): string | undefined;
|
|
49
59
|
export interface OpenAPIOperation {
|
|
50
60
|
tags?: string[];
|
|
51
61
|
summary?: string;
|
package/dist/rpc/types.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../src/rpc/types.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,gBAAgB,CAAC;AACjD,OAAO,KAAK,EAAE,oBAAoB,EAAE,MAAM,yBAAyB,CAAC;AAEpE,MAAM,WAAW,gBAAgB;IAC/B,IAAI,CAAC,EAAE,MAAM,EAAE,CAAC;IAChB,KAAK,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;CAChC;AAED,MAAM,WAAW,mBAAmB;IAClC,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,MAAM,CAAC,EAAE,MAAM,CAAC;CACjB;AAED,MAAM,WAAW,iBAAiB;IAChC,OAAO,EAAE,OAAO,CAAC;IACjB,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,SAAS,EAAE,MAAM,CAAC;IAClB,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,GAAG,CAAC,EAAE,MAAM,CAAC;IACb,KAAK,CAAC,EAAE,gBAAgB,CAAC;IACzB,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,eAAe,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;IACzC,UAAU,CAAC,EAAE,mBAAmB,CAAC;IACjC,IAAI,CAAC,EAAE,IAAI,CAAC;IACZ,MAAM,CAAC,EAAE,OAAO,CAAC;CAClB;AAED,MAAM,WAAW,aAAa;IAC5B,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,OAAO,CAAC,EAAE,OAAO,CAAC;IAClB,IAAI,CAAC,EAAE,OAAO,EAAE,CAAC;IACjB,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,UAAU,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,aAAa,CAAC,CAAC;CAC5C;AAUD,MAAM,MAAM,mBAAmB,GAC3B,QAAQ,GACR,QAAQ,GACR,OAAO,GACP,QAAQ,GACR,WAAW,GACX,SAAS,CAAC;AAEd,MAAM,WAAW,mBAAmB;IAClC,IAAI,CAAC,EAAE,mBAAmB,CAAC;CAC5B;AAED,MAAM,WAAW,gBAAgB;IAC/B,IAAI,EAAE,MAAM,CAAC;IACb,EAAE,EAAE,OAAO,GAAG,MAAM,GAAG,QAAQ,CAAC;IAChC,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,QAAQ,CAAC,EAAE,OAAO,CAAC;IACnB,MAAM,CAAC,EAAE,aAAa,CAAC;IACvB,UAAU,CAAC,EAAE,mBAAmB,CAAC;
|
|
1
|
+
{"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../src/rpc/types.ts"],"names":[],"mappings":"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"}
|
package/dist/rpc/types.js
CHANGED
|
@@ -1,8 +1,12 @@
|
|
|
1
|
+
function parameterPlaceholder(param) {
|
|
2
|
+
return param["x-clicky-placeholder"] ?? param.placeholder;
|
|
3
|
+
}
|
|
1
4
|
function isPositionalParam(p) {
|
|
2
5
|
var _a;
|
|
3
6
|
return p.name === "args" || ((_a = p.description) == null ? void 0 : _a.toLowerCase().includes("positional argument")) === true;
|
|
4
7
|
}
|
|
5
8
|
export {
|
|
6
|
-
isPositionalParam
|
|
9
|
+
isPositionalParam,
|
|
10
|
+
parameterPlaceholder
|
|
7
11
|
};
|
|
8
12
|
//# sourceMappingURL=types.js.map
|
package/dist/rpc/types.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"types.js","sources":["../../src/rpc/types.ts"],"sourcesContent":["import type { ClickyNode } from \"../data/Clicky\";\nimport type { TimeRangePresetGroup } from \"../components/TimeRange\";\n\nexport interface ExecutionRequest {\n args?: string[];\n flags?: Record<string, string>;\n}\n\nexport interface ExecutionPagination {\n total?: number;\n limit?: number;\n offset?: number;\n}\n\nexport interface ExecutionResponse {\n success: boolean;\n message?: string;\n output?: string;\n stdout?: string;\n stderr?: string;\n exit_code: number;\n error?: string;\n cli?: string;\n input?: ExecutionRequest;\n contentType?: string;\n requestUrl?: string;\n responseHeaders?: Record<string, string>;\n pagination?: ExecutionPagination;\n blob?: Blob;\n parsed?: unknown;\n}\n\nexport interface OpenAPISchema {\n type?: string;\n format?: string;\n default?: unknown;\n enum?: unknown[];\n description?: string;\n properties?: Record<string, OpenAPISchema>;\n}\n\n// ClickyParameterRole tells the UI which widget owns a parameter:\n// \"search\" — render as the FilterBar's dedicated search input\n// \"filter\" — render as a FilterBar chip on the DataTable\n// \"limit\" — feed into DataTable pagination's pageSize\n// \"offset\" — feed into DataTable pagination's page (or skip)\n// \"time-from\" — left edge of a time-range picker\n// \"time-to\" — right edge of a time-range picker\n// Set server-side by clicky's converter (see paramRole in clicky/rpc/openapi.go).\nexport type ClickyParameterRole =\n | \"search\"\n | \"filter\"\n | \"limit\"\n | \"offset\"\n | \"time-from\"\n | \"time-to\";\n\nexport interface ClickyParameterMeta {\n role?: ClickyParameterRole;\n}\n\nexport interface OpenAPIParameter {\n name: string;\n in: \"query\" | \"path\" | \"header\";\n description?: string;\n required?: boolean;\n schema?: OpenAPISchema;\n \"x-clicky\"?: ClickyParameterMeta;\n}\n\nexport interface OpenAPIOperation {\n tags?: string[];\n summary?: string;\n description?: string;\n operationId?: string;\n parameters?: OpenAPIParameter[];\n requestBody?: {\n content?: Record<string, { schema?: OpenAPISchema }>;\n };\n responses: Record<string, unknown>;\n \"x-clicky\"?: ClickyOperationMeta;\n}\n\nexport interface OpenAPISpec {\n openapi: string;\n info: { title: string; description?: string; version: string };\n paths: Record<string, Record<string, OpenAPIOperation>>;\n tags?: Array<{ name: string; description?: string }>;\n \"x-clicky\"?: ClickySpecMeta;\n}\n\nexport interface ResolvedOperation {\n path: string;\n method: string;\n operation: OpenAPIOperation;\n}\n\nexport interface DomainDefinition {\n key: string;\n title: string;\n description: string;\n emptyTitle?: string;\n emptyDescription?: string;\n}\n\nexport interface ClickySpecMeta {\n surfaces?: ClickySurface[];\n}\n\nexport interface ClickySurface {\n key: string;\n entity: string;\n title: string;\n parent?: string;\n admin?: boolean;\n description?: string;\n}\n\nexport interface ClickyOperationMeta {\n command?: string;\n surface?: string;\n verb: \"list\" | \"get\" | \"create\" | \"update\" | \"delete\" | \"action\";\n scope: \"collection\" | \"entity\";\n actionName?: string;\n idParam?: string;\n supportsLookup?: boolean;\n supportsFilterMode?: boolean;\n}\n\nexport type OperationLookupFilterType = \"bool\" | \"number\" | \"date\" | \"from\" | \"to\" | \"multi-filter\";\n\nexport interface OperationLookupFilter {\n label?: string;\n options?: Record<string, ClickyNode>;\n selected?: Record<string, ClickyNode>;\n multi?: boolean;\n type?: OperationLookupFilterType;\n /** True when `options` is only the head of a larger set (server-side capped). */\n truncated?: boolean;\n /** True distinct count behind a truncated option set; drives \"… and N more\". */\n total?: number;\n presets?: Array<{ label: string; from: string; to: string } | TimeRangePresetGroup>;\n timeEnabled?: boolean;\n timeZone?: string;\n timeZones?: string[];\n}\n\nexport interface OperationLookupResponse {\n filters: Record<string, OperationLookupFilter>;\n}\n\nexport function isPositionalParam(p: OpenAPIParameter): boolean {\n return p.name === \"args\" || p.description?.toLowerCase().includes(\"positional argument\") === true;\n}\n"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"types.js","sources":["../../src/rpc/types.ts"],"sourcesContent":["import type { ClickyNode } from \"../data/Clicky\";\nimport type { TimeRangePresetGroup } from \"../components/TimeRange\";\n\nexport interface ExecutionRequest {\n args?: string[];\n flags?: Record<string, string>;\n}\n\nexport interface ExecutionPagination {\n total?: number;\n limit?: number;\n offset?: number;\n}\n\nexport interface ExecutionResponse {\n success: boolean;\n message?: string;\n output?: string;\n stdout?: string;\n stderr?: string;\n exit_code: number;\n error?: string;\n cli?: string;\n input?: ExecutionRequest;\n contentType?: string;\n requestUrl?: string;\n responseHeaders?: Record<string, string>;\n pagination?: ExecutionPagination;\n blob?: Blob;\n parsed?: unknown;\n}\n\nexport interface OpenAPISchema {\n type?: string;\n format?: string;\n default?: unknown;\n enum?: unknown[];\n description?: string;\n properties?: Record<string, OpenAPISchema>;\n}\n\n// ClickyParameterRole tells the UI which widget owns a parameter:\n// \"search\" — render as the FilterBar's dedicated search input\n// \"filter\" — render as a FilterBar chip on the DataTable\n// \"limit\" — feed into DataTable pagination's pageSize\n// \"offset\" — feed into DataTable pagination's page (or skip)\n// \"time-from\" — left edge of a time-range picker\n// \"time-to\" — right edge of a time-range picker\n// Set server-side by clicky's converter (see paramRole in clicky/rpc/openapi.go).\nexport type ClickyParameterRole =\n | \"search\"\n | \"filter\"\n | \"limit\"\n | \"offset\"\n | \"time-from\"\n | \"time-to\";\n\nexport interface ClickyParameterMeta {\n role?: ClickyParameterRole;\n}\n\nexport interface OpenAPIParameter {\n name: string;\n in: \"query\" | \"path\" | \"header\";\n description?: string;\n required?: boolean;\n schema?: OpenAPISchema;\n /** Hint text shown inside the empty input. Distinct from `description`,\n * which is help text and must NOT be used as a placeholder. */\n placeholder?: string;\n \"x-clicky\"?: ClickyParameterMeta;\n /** Vendor-extension placeholder, set server-side by clicky's converter.\n * Takes precedence over `placeholder` when both are present. */\n \"x-clicky-placeholder\"?: string;\n}\n\n/** Resolves the input placeholder for a parameter, drawing ONLY from explicit\n * placeholder fields — never from `description` (help text). Returns undefined\n * when no placeholder is declared so callers can apply their own fallback. */\nexport function parameterPlaceholder(param: OpenAPIParameter): string | undefined {\n return param[\"x-clicky-placeholder\"] ?? param.placeholder;\n}\n\nexport interface OpenAPIOperation {\n tags?: string[];\n summary?: string;\n description?: string;\n operationId?: string;\n parameters?: OpenAPIParameter[];\n requestBody?: {\n content?: Record<string, { schema?: OpenAPISchema }>;\n };\n responses: Record<string, unknown>;\n \"x-clicky\"?: ClickyOperationMeta;\n}\n\nexport interface OpenAPISpec {\n openapi: string;\n info: { title: string; description?: string; version: string };\n paths: Record<string, Record<string, OpenAPIOperation>>;\n tags?: Array<{ name: string; description?: string }>;\n \"x-clicky\"?: ClickySpecMeta;\n}\n\nexport interface ResolvedOperation {\n path: string;\n method: string;\n operation: OpenAPIOperation;\n}\n\nexport interface DomainDefinition {\n key: string;\n title: string;\n description: string;\n emptyTitle?: string;\n emptyDescription?: string;\n}\n\nexport interface ClickySpecMeta {\n surfaces?: ClickySurface[];\n}\n\nexport interface ClickySurface {\n key: string;\n entity: string;\n title: string;\n parent?: string;\n admin?: boolean;\n description?: string;\n}\n\nexport interface ClickyOperationMeta {\n command?: string;\n surface?: string;\n verb: \"list\" | \"get\" | \"create\" | \"update\" | \"delete\" | \"action\";\n scope: \"collection\" | \"entity\";\n actionName?: string;\n idParam?: string;\n supportsLookup?: boolean;\n supportsFilterMode?: boolean;\n}\n\nexport type OperationLookupFilterType = \"bool\" | \"number\" | \"date\" | \"from\" | \"to\" | \"multi-filter\";\n\nexport interface OperationLookupFilter {\n label?: string;\n options?: Record<string, ClickyNode>;\n selected?: Record<string, ClickyNode>;\n multi?: boolean;\n type?: OperationLookupFilterType;\n /** True when `options` is only the head of a larger set (server-side capped). */\n truncated?: boolean;\n /** True distinct count behind a truncated option set; drives \"… and N more\". */\n total?: number;\n presets?: Array<{ label: string; from: string; to: string } | TimeRangePresetGroup>;\n timeEnabled?: boolean;\n timeZone?: string;\n timeZones?: string[];\n}\n\nexport interface OperationLookupResponse {\n filters: Record<string, OperationLookupFilter>;\n}\n\nexport function isPositionalParam(p: OpenAPIParameter): boolean {\n return p.name === \"args\" || p.description?.toLowerCase().includes(\"positional argument\") === true;\n}\n"],"names":[],"mappings":"AA+EO,SAAS,qBAAqB,OAA6C;AAChF,SAAO,MAAM,sBAAsB,KAAK,MAAM;AAChD;AAmFO,SAAS,kBAAkB,GAA8B;AArFzD;AAsFL,SAAO,EAAE,SAAS,YAAU,OAAE,gBAAF,mBAAe,cAAc,SAAS,4BAA2B;AAC/F;"}
|