{"record":{"id":"d1672c9f52ce203c","repo":"paperclipai/paperclip","slug":"handler-function-is-required-when-a-filter-is-prov","errorCode":null,"errorMessage":"Handler function is required when a filter is provided","messagePattern":"Handler function is required when a filter is provided","errorType":"exception","errorClass":"Error","httpStatus":null,"severity":"error","filePath":"server/src/services/plugin-event-bus.ts","lineNumber":234,"sourceCode":"       * For wildcard subscriptions use a trailing `.*` pattern, e.g.\n       * `\"plugin.acme.linear.*\"`.\n       *\n       * Requires the `events.subscribe` capability (capability enforcement is\n       * done by the host layer before calling this method).\n       */\n      subscribe(\n        eventPattern: PluginEventType | `plugin.${string}`,\n        fnOrFilter: EventFilter | ((event: PluginEvent) => Promise<void>),\n        maybeFn?: (event: PluginEvent) => Promise<void>,\n      ): void {\n        let filter: EventFilter | null = null;\n        let handler: (event: PluginEvent) => Promise<void>;\n\n        if (typeof fnOrFilter === \"function\") {\n          handler = fnOrFilter;\n        } else {\n          filter = fnOrFilter;\n          if (!maybeFn) throw new Error(\"Handler function is required when a filter is provided\");\n          handler = maybeFn;\n        }\n\n        subsFor(pluginId).push({ eventPattern, filter, handler });\n      },\n\n      /**\n       * Emit a plugin-namespaced event. The event type is automatically\n       * prefixed with `plugin.<pluginId>.` so:\n       * - `emit(\"sync-done\", payload)` becomes `\"plugin.acme.linear.sync-done\"`.\n       *\n       * Requires the `events.emit` capability (enforced by the host layer).\n       *\n       * @throws {Error} if `name` already contains the `plugin.` prefix\n       *   (prevents cross-namespace spoofing).\n       */\n      async emit(name: string, companyId: string, payload: unknown): Promise<PluginEventBusEmitResult> {\n        if (!name || name.trim() === \"\") {","sourceCodeStart":216,"sourceCodeEnd":252,"githubUrl":"https://github.com/paperclipai/paperclip/blob/120ae5428fa29bee300bcf806491cd4d965fbb7c/server/src/services/plugin-event-bus.ts#L216-L252","documentation":"API-contract guard in event bus subscribe: the two-argument form was used where the first argument is a filter object, so the third parameter (the handler function) is undefined. Callers must pass either (pattern, fn) or (pattern, filter, fn); the malformed subscribe call is at fault.","triggerScenarios":"Thrown at server/src/services/plugin-event-bus.ts:234 when the library encounters an invalid state.","commonSituations":"See trigger scenarios.","solutions":["Provide a handler function when subscribing with a filter, or remove the filter."],"exampleFix":null,"handlingStrategy":"validation","validationCode":null,"typeGuard":null,"tryCatchPattern":null,"preventionTips":[],"tags":[],"backgroundTag":null,"analyzedSha":"120ae5428fa29bee300bcf806491cd4d965fbb7c","analyzedAt":"2026-08-18T22:49:45.177Z","contentChangedAt":"2026-08-18T22:49:45.177Z","schemaVersion":2},"datasetVersion":"2026-09-14T00:17:10.932Z"}