wavetermdev/waveterm · error
terminput is required
Error message
terminput is required
What it means
Besides waveId, the event must contain a TermInput payload — that is what this endpoint dispatches via h.Client.Root.Event. If event.TermInput is nil after JSON parsing, the handler returns 400 'terminput is required'.
Source
Thrown at tsunami/engine/serverhandlers.go:428
}
body, err := io.ReadAll(r.Body)
if err != nil {
http.Error(w, fmt.Sprintf("failed to read request body: %v", err), http.StatusBadRequest)
return
}
var event vdom.VDomEvent
if err := json.Unmarshal(body, &event); err != nil {
http.Error(w, fmt.Sprintf("failed to parse JSON: %v", err), http.StatusBadRequest)
return
}
if strings.TrimSpace(event.WaveId) == "" {
http.Error(w, "waveid is required", http.StatusBadRequest)
return
}
if event.TermInput == nil {
http.Error(w, "terminput is required", http.StatusBadRequest)
return
}
h.renderLock.Lock()
h.Client.Root.Event(event, h.Client.GlobalEventHandler)
h.renderLock.Unlock()
w.WriteHeader(http.StatusNoContent)
}
func (h *httpHandlers) handleDynContent(w http.ResponseWriter, r *http.Request) {
defer func() {
panicErr := util.PanicHandler("handleDynContent", recover())
if panicErr != nil {
http.Error(w, fmt.Sprintf("internal server error: %v", panicErr), http.StatusInternalServerError)
}
}()
View on GitHub (pinned to a4447c1563)
Solutions
- Include a termInput object in the JSON body (e.g. {"inputData":"..."})
- Confirm you are calling the correct endpoint for your event type
- Inspect VDomEvent's TermInput struct shape and fill required sub-fields
- If building events in Go, ensure the *TermInput pointer is non-nil before marshaling
Example fix
// before
{"waveId":"wave-1234"}
// after
{"waveId":"wave-1234","termInput":{"inputData":"ls\n"}} Defensive patterns
Strategy: validation
Validate before calling
if (event.termInput == null) {
throw new Error('terminput is required: this endpoint only accepts terminal-input events')
} Type guard
function hasTermInput(e: unknown): e is { termInput: { inputData: string } } {
return (e as any)?.termInput != null && typeof (e as any).termInput === 'object'
} Try / catch
const res = await fetch(url, opts)
if (res.status === 400 && (await res.text()).includes('terminput is required')) {
// route the event to the correct endpoint instead
} Prevention
- Verify the event type matches the endpoint before POSTing
- Keep a typed event builder so TermInput cannot be omitted
- Add compile-time/type checks for required fields
When it happens
Trigger: POSTing an event with a valid waveId but no termInput object, termInput explicitly null, or posting an event type meant for a different endpoint (e.g. a vdom event that is not terminal input).
Common situations: Copy-pasted payload templates where the termInput block was deleted; sending UI events (clicks, keys from other blocks) to the term-input endpoint by mistake; serializers omitting nil fields and the field never being set.
Understand the failure class
Background: "missing required argument" and "the following required arguments were not provided": what required-argument errors mean and how to fix them — this error's family across 20 libraries.
Related errors
- waveid is required
- messageid must be set
- no content available
- Invalid UUID format
- failed to parse JSON: %v
AI-assisted analysis of wavetermdev/waveterm@a4447c1563 (2026-09-01).
Data as JSON: /api/errors/bcb8524e1422b9f0.
Report an issue: GitHub.