{"record":{"id":"a114d984d39ab014","repo":"louislam/dockge","slug":"event-name-must-be-a-string","errorCode":null,"errorMessage":"Event name must be a string","messagePattern":"Event name must be a string","errorType":"exception","errorClass":"Error","httpStatus":null,"severity":"error","filePath":"backend/socket-handlers/agent-proxy-socket-handler.ts","lineNumber":21,"sourceCode":"import { log } from \"../log\";\nimport { checkLogin, DockgeSocket } from \"../util-server\";\nimport { AgentSocket } from \"../../common/agent-socket\";\nimport { ALL_ENDPOINTS } from \"../../common/util-common\";\n\nexport class AgentProxySocketHandler extends SocketHandler {\n\n    create2(socket : DockgeSocket, server : DockgeServer, agentSocket : AgentSocket) {\n        // Agent - proxying requests if needed\n        socket.on(\"agent\", async (endpoint : unknown, eventName : unknown, ...args : unknown[]) => {\n            try {\n                checkLogin(socket);\n\n                // Check Type\n                if (typeof(endpoint) !== \"string\") {\n                    throw new Error(\"Endpoint must be a string: \" + endpoint);\n                }\n                if (typeof(eventName) !== \"string\") {\n                    throw new Error(\"Event name must be a string\");\n                }\n\n                if (endpoint === ALL_ENDPOINTS) {      // Send to all endpoints\n                    log.debug(\"agent\", \"Sending to all endpoints: \" + eventName);\n                    socket.instanceManager.emitToAllEndpoints(eventName, ...args);\n\n                } else if (!endpoint || endpoint === socket.endpoint) {      // Direct connection or matching endpoint\n                    log.debug(\"agent\", \"Matched endpoint: \" + eventName);\n                    agentSocket.call(eventName, ...args);\n\n                } else {\n                    log.debug(\"agent\", \"Proxying request to \" + endpoint + \" for \" + eventName);\n                    await socket.instanceManager.emitToEndpoint(endpoint, eventName, ...args);\n                }\n            } catch (e) {\n                if (e instanceof Error) {\n                    log.warn(\"agent\", e.message);\n                }","sourceCodeStart":3,"sourceCodeEnd":39,"githubUrl":"https://github.com/louislam/dockge/blob/f809ae192b571944ad773e9866d3e67064ae8043/backend/socket-handlers/agent-proxy-socket-handler.ts#L3-L39","documentation":"Second type check in the same `agent` event handler: `eventName` must be a string naming the agent event to forward. A non-string eventName throws 'Event name must be a string'. As with the endpoint check, the enclosing catch only logs the message server-side, so the client gets no explicit error callback.","triggerScenarios":"Emitting socket event `agent` with a non-string second argument, e.g. socket.emit('agent', 'endpoint', 42, payload) or omitting eventName entirely (undefined).","commonSituations":"Off-by-one in the argument list (payload passed where eventName belongs); programmatic emitters building the args array dynamically; typos swapping endpoint/eventName order.","solutions":["Pass eventName as a string in the second position: socket.emit('agent', endpoint, 'test', ...args)","Verify the argument order (endpoint, eventName, ...args) in the emitting code","Validate client-side: if (typeof eventName !== 'string') throw before emitting"],"exampleFix":"// before\nsocket.emit(\"agent\", endpoint, { name: \"test\" }, data);\n// after\nsocket.emit(\"agent\", endpoint, \"test\", data);","handlingStrategy":"type-guard","validationCode":"if (typeof eventName !== \"string\" || !eventName) { throw new TypeError(\"agent() requires a string eventName as 2nd arg\"); }\nsocket.emit(\"agent\", endpoint, eventName, ...args);","typeGuard":"const isEventName = (v: unknown): v is string => typeof v === \"string\" && v.length > 0;","tryCatchPattern":"// server catches and only logs; guard on the client\nif (!isEventName(ev)) { console.error(\"agent event skipped: eventName must be a string\"); return; }\nsocket.emit(\"agent\", endpoint, ev, ...args);","preventionTips":["Wrap the raw emit in a typed helper: function agentCall(endpoint: string, event: string, ...args: unknown[])","Never build the args array dynamically without re-checking positions","Note the server swallows this error into log.warn — client-side validation is the only reliable guard"],"tags":["validation","socket-io","agent","typescript"],"backgroundTag":"invalid-argument-type","analyzedSha":"f809ae192b571944ad773e9866d3e67064ae8043","analyzedAt":"2026-08-31T19:13:50.919Z","schemaVersion":2},"datasetVersion":"2026-08-31T19:17:28.585Z"}