From 4e26ab3bac3c0c16dbfc29b4947d4a9d0a1504c9 Mon Sep 17 00:00:00 2001 From: Andrew Melchor Date: Thu, 5 Mar 2026 16:26:28 -0800 Subject: [PATCH 1/4] feat(web)/request-workspace-panels --- .../src/components/request-workspace/index.ts | 23 + .../panels/body/file-editor.tsx | 59 ++ .../panels/body/form-data-editor.tsx | 135 +++++ .../request-workspace/panels/body/index.tsx | 85 +++ .../panels/body/inline-editor.tsx | 108 ++++ .../request-workspace/panels/body/types.ts | 71 +++ .../panels/headers/index.tsx | 42 ++ .../request-workspace/panels/params/index.tsx | 37 ++ .../panels/shared/draft-header.tsx | 48 ++ .../panels/shared/error-banner.tsx | 17 + .../request-workspace/panels/shared/index.ts | 3 + .../panels/shared/key-value-table.tsx | 96 ++++ .../request-workspace-tab-panels.tsx | 516 +----------------- 13 files changed, 730 insertions(+), 510 deletions(-) create mode 100644 packages/web/src/components/request-workspace/panels/body/file-editor.tsx create mode 100644 packages/web/src/components/request-workspace/panels/body/form-data-editor.tsx create mode 100644 packages/web/src/components/request-workspace/panels/body/index.tsx create mode 100644 packages/web/src/components/request-workspace/panels/body/inline-editor.tsx create mode 100644 packages/web/src/components/request-workspace/panels/body/types.ts create mode 100644 packages/web/src/components/request-workspace/panels/headers/index.tsx create mode 100644 packages/web/src/components/request-workspace/panels/params/index.tsx create mode 100644 packages/web/src/components/request-workspace/panels/shared/draft-header.tsx create mode 100644 packages/web/src/components/request-workspace/panels/shared/error-banner.tsx create mode 100644 packages/web/src/components/request-workspace/panels/shared/index.ts create mode 100644 packages/web/src/components/request-workspace/panels/shared/key-value-table.tsx diff --git a/packages/web/src/components/request-workspace/index.ts b/packages/web/src/components/request-workspace/index.ts index bd0b569..b767254 100644 --- a/packages/web/src/components/request-workspace/index.ts +++ b/packages/web/src/components/request-workspace/index.ts @@ -1,9 +1,32 @@ +// Model exports export { DEFAULT_REQUEST_WORKSPACE_TAB, isRequestWorkspaceTabId, REQUEST_WORKSPACE_TABS, type RequestWorkspaceTabId } from './model'; +export { BodyPanel } from './panels/body'; +export { HeadersPanel } from './panels/headers'; +// New panel component exports +export { ParamsPanel } from './panels/params'; +export { + DraftHeader as SharedDraftHeader, + ErrorBanner as SharedErrorBanner, + KeyValueRow as SharedKeyValueRow, + KeyValueTable as SharedKeyValueTable +} from './panels/shared'; + +// Legacy panel component exports (re-exported from new locations) +export { + DraftHeader, + ErrorBanner, + KeyValueRow, + KeyValueTable, + RequestWorkspaceBodyPanel, + RequestWorkspaceHeadersPanel, + RequestWorkspaceParamsPanel +} from './request-workspace-tab-panels'; +// Legacy exports (keep for backward compatibility) export { RequestWorkspaceTabs } from './request-workspace-tabs'; export { useRequestBodyDraftController } from './use-request-body-draft-controller'; export { useRequestHeaderDraftController } from './use-request-header-draft-controller'; diff --git a/packages/web/src/components/request-workspace/panels/body/file-editor.tsx b/packages/web/src/components/request-workspace/panels/body/file-editor.tsx new file mode 100644 index 0000000..2b94eb3 --- /dev/null +++ b/packages/web/src/components/request-workspace/panels/body/file-editor.tsx @@ -0,0 +1,59 @@ +import { Show } from 'solid-js'; +import type { FileBodyEditorProps } from './types'; + +export function FileBodyEditor(props: FileBodyEditorProps) { + return ( +
+
+ + +
+ + Unsaved + + + +
+
+ +
+ + props.onBodyFilePathChange(event.currentTarget.value)} + disabled={!props.hasRequest || props.bodyDraftSaving} + placeholder="./payload.json" + /> +
+
+ ); +} diff --git a/packages/web/src/components/request-workspace/panels/body/form-data-editor.tsx b/packages/web/src/components/request-workspace/panels/body/form-data-editor.tsx new file mode 100644 index 0000000..3e6cc94 --- /dev/null +++ b/packages/web/src/components/request-workspace/panels/body/form-data-editor.tsx @@ -0,0 +1,135 @@ +import { Index, Show } from 'solid-js'; +import type { FormDataEditorProps } from './types'; + +export function FormDataEditor(props: FormDataEditorProps) { + return ( +
+
+ + +
+ + Unsaved + + + +
+
+ +
+ + + + + + + + + + + + 0} + fallback={ + + + + } + > + + {(field, index) => ( + + + + + + + + )} + + + +
NameTypeValueFilenameActions
+ No form-data fields configured. +
+ + props.onBodyFormDataNameChange(index, event.currentTarget.value) + } + disabled={!props.hasRequest || props.bodyDraftSaving} + /> + + + + + props.onBodyFormDataValueChange(index, event.currentTarget.value) + } + placeholder={field().isFile ? './path/to/file' : 'value'} + disabled={!props.hasRequest || props.bodyDraftSaving} + /> + + + props.onBodyFormDataFilenameChange(index, event.currentTarget.value) + } + placeholder="optional" + disabled={!props.hasRequest || props.bodyDraftSaving || !field().isFile} + /> + + +
+
+
+ ); +} diff --git a/packages/web/src/components/request-workspace/panels/body/index.tsx b/packages/web/src/components/request-workspace/panels/body/index.tsx new file mode 100644 index 0000000..dca92b2 --- /dev/null +++ b/packages/web/src/components/request-workspace/panels/body/index.tsx @@ -0,0 +1,85 @@ +import { Match, Show, Switch } from 'solid-js'; +import { FileBodyEditor } from './file-editor'; +import { FormDataEditor } from './form-data-editor'; +import { InlineBodyEditor } from './inline-editor'; +import type { BodyPanelProps } from './types'; + +export function BodyPanel(props: BodyPanelProps) { + const shouldShowDescription = + props.requestBodySummary.description !== 'Request includes an inline body payload.'; + + return ( +
+ + {(message) => ( +
+ {message()} +
+ )} +
+ + +

{props.requestBodySummary.description}

+
+ + + + + + + + + + + + + + +
+ ); +} + +// Re-export types for backward compatibility +export type { + BodyPanelProps, + FileBodyEditorProps, + FormDataEditorProps, + InlineBodyEditorProps +} from './types'; diff --git a/packages/web/src/components/request-workspace/panels/body/inline-editor.tsx b/packages/web/src/components/request-workspace/panels/body/inline-editor.tsx new file mode 100644 index 0000000..9ee78da --- /dev/null +++ b/packages/web/src/components/request-workspace/panels/body/inline-editor.tsx @@ -0,0 +1,108 @@ +import { For, Show } from 'solid-js'; +import type { InlineBodyEditorProps } from './types'; + +export function InlineBodyEditor(props: InlineBodyEditorProps) { + return ( + +

Inline non-JSON body editing is not supported yet.

+ No inline body content was parsed.

} + > +
+              {props.requestBodySummary.text}
+            
+
+ + } + > +
+ 0}> +
+ {(warning) =>

{warning}

}
+
+
+ + + {(message) => ( + + )} + + +
+
+ + + +
+ +
+ + Unsaved + + + +
+
+ +