{"record":{"id":"65a63d917efd0a08","repo":"wavetermdev/waveterm","slug":"nil-message","errorCode":null,"errorMessage":"nil message","messagePattern":"nil message","errorType":"validation","errorClass":null,"httpStatus":null,"severity":"error","filePath":"pkg/wshutil/wshutil.go","lineNumber":117,"sourceCode":"\tvar buf bytes.Buffer\n\tbuf.Write(makeOscPrefix(oscNum))\n\tescSeq := [6]byte{'\\\\', 'u', '0', '0', '0', '0'}\n\tfor _, b := range barr {\n\t\tif b < 0x20 || b == 0x7f {\n\t\t\tescSeq[4] = HexChars[b>>4]\n\t\t\tescSeq[5] = HexChars[b&0x0f]\n\t\t\tbuf.Write(escSeq[:])\n\t\t} else {\n\t\t\tbuf.WriteByte(b)\n\t\t}\n\t}\n\tbuf.WriteByte(BEL)\n\treturn buf.Bytes(), nil\n}\n\nfunc EncodeWaveOSCMessageEx(oscNum string, msg *RpcMessage) ([]byte, error) {\n\tif msg == nil {\n\t\treturn nil, fmt.Errorf(\"nil message\")\n\t}\n\tbarr, err := json.Marshal(msg)\n\tif err != nil {\n\t\treturn nil, fmt.Errorf(\"error marshalling message to json: %w\", err)\n\t}\n\treturn EncodeWaveOSCBytes(oscNum, barr)\n}\n\nvar shutdownOnce sync.Once\n\nfunc DoShutdown(reason string, exitCode int, quiet bool) {\n\tshutdownOnce.Do(func() {\n\t\tdefer os.Exit(exitCode)\n\t\tif !quiet && reason != \"\" {\n\t\t\tlog.Printf(\"shutting down: %s\\n\", reason)\n\t\t}\n\t})\n}","sourceCodeStart":99,"sourceCodeEnd":135,"githubUrl":"https://github.com/wavetermdev/waveterm/blob/a4447c1563b2df285ab89e76c82f91e1a1a49c1e/pkg/wshutil/wshutil.go#L99-L135","documentation":"EncodeWaveOSCMessageEx serializes an *RpcMessage to JSON and wraps it in an OSC sequence. A nil message pointer cannot be marshalled meaningfully, so the function rejects it explicitly with this sentinel error before touching json.Marshal.","triggerScenarios":"Calling EncodeWaveOSCMessageEx with msg == nil — e.g. a channel or variable holding a typed-nil *RpcMessage, or an upstream function returning nil on a path the caller didn't check.","commonSituations":"Uninitialized message variable; an RPC builder that returns (nil, nil) on an edge case; passing a nil pointer through a message queue unchecked.","solutions":["Construct a valid RpcMessage before calling; never pass a nil pointer.","Check the upstream producer for paths that return a nil message.","If an empty message is intended, pass &RpcMessage{} with appropriate fields instead."],"exampleFix":"// before\nvar msg *RpcMessage\nbarr, err := EncodeWaveOSCMessageEx(\"1337;\", msg) // panics into error\n// after\nmsg := &RpcMessage{Command: \"waveclient:getdata\", Data: basePayload}\nbarr, err := EncodeWaveOSCMessageEx(\"1337;\", msg)","handlingStrategy":"validation","validationCode":"if msg == nil {\n    return errors.New(\"cannot encode nil RpcMessage\")\n}","typeGuard":"func hasMessage(m *wshutil.RpcMessage) bool { return m != nil }","tryCatchPattern":"if msg == nil { return errors.New(\"no message to send\") }\nif _, err := EncodeWaveOSCMessageEx(oscNum, msg); err != nil {\n    return fmt.Errorf(\"encode failed: %w\", err)\n}","preventionTips":["Check producers for code paths returning nil messages","Initialize messages with &RpcMessage{} rather than var msg *RpcMessage","Validate messages at API boundaries before queuing"],"tags":["go","nil-pointer","validation"],"backgroundTag":"nil-pointer-argument","analyzedSha":"a4447c1563b2df285ab89e76c82f91e1a1a49c1e","analyzedAt":"2026-09-01T15:26:23.972Z","contentChangedAt":null,"schemaVersion":2},"datasetVersion":"2026-09-08T10:18:20.063Z"}