Object values rendering as [object Object] in settings UI

NousResearch/hermes-agent · cluster 9726 · gateway

Data as of

Nothing open on GitHub. Fix merged in #10949. Check it covers your case.

The short answer

0open issues
0open PRs
5items grouped
Known?
Yes. 5 related items grouped here, 3 issues already closed.
Fix event
A fix was merged to main in PR #10949. Check it covers your case. No release data is tracked.
Tracker
The maintainers' tracker marks this partially resolved, deciding PR #10949. That is separate from the fix event.
Still open
Nothing open on GitHub.

Multiple reports and corresponding fixes for a bug where object/list config values, particularly fallback_providers, are incorrectly rendered as '[object Object]' in the web UI settings pages.

Open issues0

No open issues.

Open PRs0

No open pull requests.

Fixes on record

Merged to main. A stamp counts the issues a fix is linked to.

  • #10949 fix(web): render object config values structurally

    merged to main

    files: web/src/components/AutoField.tsx

    Show the diff
    • web/src/components/AutoField.tsx
      @@ -17,6 +17,71 @@ function FieldHint({ schema, schemaKey }: { schema: Record<string, unknown>; sch
         );
       }
       
      +function isRecord(value: unknown): value is Record<string, unknown> {
      +  return typeof value === "object" && value !== null && !Array.isArray(value);
      +}
      +
      +function formatScalar(value: unknown): string {
      +  if (value === undefined || value === null) return "";
      +  if (typeof value === "string") return value;
      +  if (typeof value === "number" || typeof value === "boolean") return String(value);
      +  return JSON.stringify(value);
      +}
      +
      +function NestedValueEditor({
      +  fieldKey,
      +  value,
      +  onChange,
      +}: {
      +  fieldKey: string;
      +  value: unknown;
      +  onChange: (v: unknown) => void;
      +}) {
      +  if (isRecord(value)) {
      +    return (
      +      <div className="grid gap-2 border border-border p-2">
      +        {Object.entries(value).map(([subKey, subVal]) => (
      +          <div key={subKey} className="grid gap-1">
      +            <Label className="text-xs text-muted-foreground">{subKey}</Label>
      +            <NestedValueEditor
      +              fieldKey={`${fieldKey}.${subKey}`}
      +              value={subVal}
      +              onChange={(next) => onChange({ ...value, [subKey]: next })}
      +            />
      +          </div>
      +        ))}
      +      </div>
      +    );
      +  }
      +
      +  if (Array.isArray(value)) {
      +    return (
      +      <div className="grid gap-2">
      +        {value.map((item, index) => (
      +          <div key={`${fieldKey}.${index}`} className="grid gap-1">
      +            <Label className="text-xs text-muted-foreground">Item {index + 1}</Label>
      +            <NestedValueEditor
      +              fieldKey={`${fieldKey}.${index}`}
      +              value={item}
      +              onChange={(next) =>
      +                onChange(value.map((existing, i) => (i === index ? next : existing)))
      +              }
      +            />
      +          </div>
      +        ))}
      +      </div>
      +    );
      +  }
      +
      +  return (
      +    <Input
      +      value={formatScalar(value)}
      +      onChange={(e) => onChange(e.target.value)}
      +      className="text-xs"
      +    />
      +  );
      +}
      +
       export function AutoField({
         schemaKey,
         schema,
      @@ -26,6 +91,16 @@ export function AutoField({
         const rawLabel = schemaKey.split(".").pop() ?? schemaKey;
         const label = rawLabel.replace(/_/g, " ").replace(/\b\w/g, (c) => c.toUpperCase());
       
      +  if (isRecord(value) || (Array.isArray(value) && value.some((item) => isRecord(item)))) {
      +    return (
      +      <div className="grid gap-3 border border-border p-3">
      +        <Label className="text-xs font-medium">{label}</Label>
      +        <FieldHint schema={schema} schemaKey={schemaKey} />
      +        <NestedValueEditor fieldKey={schemaKey} value={value} onChange={onChange} />
      +      </div>
      +    );
      +  }
      +
         if (schema.type === "boolean") {
           return (
             <div className="flex items-center justify-between gap-4">
      @@ -114,26 +189,6 @@ export function AutoField({
           );
         }
       
      -  if (typeof value === "object" && value !== null && !Array.isArray(value)) {
      -    const obj = value as Record<string, unknown>;
      -    return (
      -      <div className="grid gap-3 border border-border p-3">
      -        <Label className="text-xs font-medium">{label}</Label>
      -        <FieldHint schema={schema} schemaKey={schemaKey} />
      -        {Object.entries(obj).map(([subKey, subVal]) => (
      -          <div key={subKey} className="grid gap-1">
      -            <Label className="text-xs text-muted-foreground">{subKey}</Label>
      -            <Input
      -              value={String(subVal ?? "")}
      -              onChange={(e) => onChange({ ...obj, [subKey]: e.target.value })}
      -              className="text-xs"
      -            />
      -          </div>
      -        ))}
      -      </div>
      -    );
      -  }
      -
         return (
           <div className="grid gap-1.5">
             <Label className="text-sm">{label}</Label>

1 PR closed without merging

From the close comments: stale or abandoned 1

  • #25376 fix(web): AutoField list type renders objects as [object Object] · stale or abandoned
Closed issues · 3
  • Closed#9726[Bug]: Dashboard Config page renders fallback_providers as "[object Object]"
  • Closed#11190[webUI] fallback_providers list renders as `[object Object]` in General settings
  • Closed#25352Settings UI: fallback_providers renders as "[object Object], [object Object]" in General settings
How this cluster was grouped
  • Link evidence (partly structural links): some members are connected by structural evidence (shared changed files, or a closing/superseded reference); the rest are joined by an automated relevance judgement over their text.
  • Members outside that structural core may belong to a different underlying problem.
  • Pairwise link density 0.31: the share of item pairs that carry a link, counting a structural link in full and a relevance-only link at 0.36. 1.00 means every pair is linked.

Pick up a Lab task

Check whether a fix covers the open issues here, with your own agent. Bring back evidence for maintainers.

Open the Lab

At a glance

Subsystem
gateway
Merged PRs
#10949
Closed issues
3
Attempts
1 PR closed without merging
Fix link checked
18 May 2026

For your agent

The same facts, typed.