antonmedv/fx · error

<error from utils.Unquote(it.Key) unquoting the object key>

Error message

<error from utils.Unquote(it.Key) unquoting the object key> (panic(err))

What it means

When converting an Object node, ToValue unquotes each member key with utils.Unquote before setting it on the goja object. If a key is not a valid quoted string (bad escapes, missing quotes), Unquote's error is panicked. Keys in JSON must be valid string literals; this fires when a key node's raw text violates that.

Source

Thrown at internal/jsonx/to_value.go:58

			panic(err)
		}
		return vm.ToValue(unquoted)

	case Object:
		obj := vm.NewObject()

		if n.HasChildren() {
			it := n
			if it.IsCollapsed() {
				it = it.Collapsed
			} else {
				it = it.Next
			}

			for it != nil && it != n.End {
				unquotedKey, err := utils.Unquote(it.Key)
				if err != nil {
					panic(err)
				}

				err = obj.Set(unquotedKey, it.ToValue(vm))
				if err != nil {
					panic(err)
				}

				if it.HasChildren() {
					it = it.End.Next
				} else {
					it = it.Next
				}
			}
		}

		return obj

	case Array:

View on GitHub (pinned to 4f31cd3a0c)

Solutions

  1. Fix the offending key in the source: escape backslashes and quotes properly.
  2. Re-parse the original document so the parser normalizes keys.
  3. When generating JSON programmatically, always marshal keys through a JSON encoder.
  4. Recover the panic in the conversion wrapper and report which key failed.

Example fix

// before
{"C:\dir": 1}
// after
{"C:\\dir": 1}
Defensive patterns

Strategy: try-catch

Validate before calling

var dummy map[string]json.RawMessage
if err := json.Unmarshal(data, &dummy); err != nil {
    return fmt.Errorf("input has malformed keys: %w", err)
}

Type guard

func isValidObjectNode(n *jsonx.Node) bool {
    if n.Kind != jsonx.Object {
        return false
    }
    for it := n.Next; it != nil && it != n.End; it = it.Next {
        if it.Key != "" {
            var s string
            if json.Unmarshal([]byte(it.Key), &s) != nil {
                return false
            }
        }
    }
    return true
}

Try / catch

func safeObjectToValue(n *jsonx.Node, vm *goja.Runtime) (v goja.Value, err error) {
    defer func() {
        if r := recover(); r != nil {
            err = fmt.Errorf("object conversion failed (bad key?): %v", r)
        }
    }()
    return n.ToValue(vm), nil
}

Prevention

When it happens

Trigger: ToValue on an Object whose member Key fields contain invalid escapes (e.g. 'C:\dir' unescaped) or are not properly quoted string literals.

Common situations: Documents generated by string concatenation without escaping, keys copied from non-JSON sources, hand-assembled nodes in tests or tooling.

Related errors


AI-assisted analysis of antonmedv/fx@4f31cd3a0c (2026-09-02). Data as JSON: /api/errors/9a6c0eaa27422087. Report an issue: GitHub.