{"id":"CVE-2026-120215","kind":"vulnerability","aliases":["CVE-2026-120215"],"related":[],"title":"@fastify/cors: preflight request can crash Node.js process with onSend","description":"@fastify/cors is the CORS plugin for the Fastify web framework. In versions 8.2.0 through 11.3.x, an application that registers the plugin with the non-default onSend hook option crashes on a CORS preflight. On an OPTIONS request that carries the Origin and Access-Control-Request-Method headers, the plugin calls reply.send from inside the onSend hook and re-enters the send pipeline, so a second write of the response headers throws an uncaught ERR_HTTP_HEADERS_SENT that can terminate the Node.js process when no process-level handler is installed. An unauthenticated remote client can trigger this with a single preflight request, so the impact is availability only, and exploitation requires the non-default onSend configuration. The issue is fixed in @fastify/cors 11.4.0, where onSend is no longer an accepted hook value and registration fails with a clear error instead of crashing at request time, and users should upgrade to 11.4.0 or later. As a workaround, use any other hook such as the default onRequest, or set preflight to false.","summary":"When @fastify/cors is registered with the non-default onSend hook, a single CORS preflight request makes the plugin re-send response headers, throwing an uncaught error. With no process-level error handler, this can terminate the Node.js process.","severity":"low","cvss":3.7,"epss":null,"exploited":false,"exploited_at":null,"products":[],"ecosystems":[],"tags":["@fastify/cors","fastify","node.js","package"],"not_affected_if":["default-hook","no-process-crash-handler-needed","preflight-disabled"],"how_to_check":"- Check the installed version with `npm ls @fastify/cors`; versions 8.2.0 through 11.3.x are in range.\n- Search the application code for registrations of the CORS plugin that set the `hook` option to `onSend`.\n- Check whether the process has an `uncaughtException` handler installed.","fix":"- `@fastify/cors` `11.4.0` or later; in 11.4.0 `onSend` is rejected at registration instead of crashing at request time.\n- Workaround stated in the source: use another hook such as the default `onRequest`, or set `preflight` to `false`.","status":"open","published_at":"2026-11-02T11:17:31+00:00","first_seen_at":"2026-11-02T11:22:54+00:00","triaged_at":"2026-11-02T11:24:21+00:00","updated_at":"2026-11-02T11:24:21+00:00","category":"package","confidence":0.8,"triage":{"at":"2026-11-02T11:24:21Z","model":"claude-haiku-5-5","output":{"fix":"- `@fastify/cors` `11.4.0` or later; in 11.4.0 `onSend` is rejected at registration instead of crashing at request time.\n- Workaround stated in the source: use another hook such as the default `onRequest`, or set `preflight` to `false`.","reach":"internet","title":"@fastify/cors: preflight request can crash Node.js process with onSend","impact":"low","summary":"When @fastify/cors is registered with the non-default onSend hook, a single CORS preflight request makes the plugin re-send response headers, throwing an uncaught error. With no process-level error handler, this can terminate the Node.js process.","audience":"developers","category":"package","nicknames":[],"who_cares":["fastify","node.js","@fastify/cors"],"confidence":0.8,"fix_status":"available","needs_auth":"no","worst_case":"Node.js process terminates after one unauthenticated preflight request","analyst_note":"","how_to_check":"- Check the installed version with `npm ls @fastify/cors`; versions 8.2.0 through 11.3.x are in range.\n- Search the application code for registrations of the CORS plugin that set the `hook` option to `onSend`.\n- Check whether the process has an `uncaughtException` handler installed.","plain_action":"","needs_analyst":false,"not_affected_if":["default-hook","preflight-disabled","no-process-crash-handler-needed"],"who_is_affected":"Only Fastify applications that register @fastify/cors with the non-default onSend hook option are exposed. Applications using the default hook or without CORS preflight handling can skip it. The impact is availability only, and the crash needs no authentication.","user_interaction":"no","needs_special_setup":"yes","severity_if_unknown":"low"},"cost_usd":0.000739,"input_tokens":4372,"output_tokens":604,"severity_before":"low"},"analyst_status":null,"analyst_note":null,"search":"'-120215':12A,15A '-2026':11A,14A '11.3':75C '11.4.0':189C,217C '8.2.0':73C 'accept':196C 'access':106C 'access-control-request-method':105C 'applic':78C 'avail':172C 'call':113C 'carri':101C 'clear':204C 'client':159C 'configur':182C 'control':107C 'cor':33B,64C,94C 'crash':5A,91C,208C 'cve':10A,13A 'default':28B,87C,180C,230C 'enter':123C 'err':138C 'error':47B,53B,205C 'exploit':175C 'fail':201C 'fals':236C 'fastifi':17B,68C 'fastify/cors':1A,16B,21B,61C,188C 'fix':186C 'framework':70C 'handler':54B,153C 'header':43B,110C,134C,140C 'hook':30B,89C,119C,197C,226C 'http':139C 'impact':170C 'insid':116C 'instal':155C 'instead':206C 'issu':184C 'later':219C 'level':52B,152C 'longer':194C 'make':36B 'method':109C 'node.js':6A,18B,59B,146C 'non':27B,86C,179C 'non-default':26B,85C,178C 'onrequest':231C 'onsend':9A,29B,88C,118C,181C,191C 'option':90C,98C 'origin':103C 'packag':19B 'pipelin':126C 'plugin':38B,65C,82C,112C 'preflight':2A,34B,95C,166C,234C 'process':7A,51B,60B,147C,151C 'process-level':50B,150C 're':40B,122C 're-ent':121C 're-send':39B 'regist':23B,80C 'registr':200C 'remot':158C 'reply.send':114C 'request':3A,35B,99C,108C,167C,210C 'requir':176C 'respons':42B,133C 'second':129C 'send':41B,125C 'sent':141C 'set':233C 'singl':32B,165C 'termin':57B,144C 'throw':44B,135C 'time':211C 'trigger':161C 'unauthent':157C 'uncaught':46B,137C 'upgrad':215C 'use':223C 'user':213C 'valu':198C 'version':72C 'web':69C 'workaround':222C 'write':130C 'x':76C","nicknames":[],"mitigations":[],"who_affected":"Only Fastify applications that register @fastify/cors with the non-default onSend hook option are exposed. Applications using the default hook or without CORS preflight handling can skip it. The impact is availability only, and the crash needs no authentication.","tier":"C","verified":{},"analyst_revisit_at":null,"fix_status":"available","audience":"developers","plain_action":null,"pkeys":[],"ptokens":[],"labels":["cors","fastify","low","nodejs","package"],"first_public_at":"2026-11-02T08:50:58+00:00","kev":null,"cvss_vector":"CVSS:3.1/AV:N/AC:H/PR:N/UI:N/S:U/C:N/I:N/A:L","cvss_by":"ce714d77-add3-4f53-aff5-83d477b104bb","poc_count":0,"sources":[{"source":"nvd","external_id":"CVE-2026-120215","url":"https://nvd.nist.gov/vuln/detail/CVE-2026-120215","severity":null,"published_at":"2026-11-02T11:17:31+00:00","modified_at":"2026-11-02T11:17:31+00:00","first_seen_at":"2026-11-02T11:22:54+00:00","fetched_at":"2026-11-02T11:22:54+00:00","note":null}],"documents":[{"id":51567,"url":"https://github.com/fastify/fastify-cors/security/advisories/GHSA-8c3j-mm64-257c","title":"Vendor advisory: github.com","kind":"vendor","source":"nvd","publisher":"vendor","text":null,"published_at":"2026-11-02T08:50:58+00:00","relation":"advisory","confidence":null,"note":"Vendor advisory: github.com"}],"notice":"Free to read at a human pace. An API with keys and an MCP server are in preparation; early access: hello@infrastack.ai"}