[{"data":1,"prerenderedAt":356},["ShallowReactive",2],{"content-query-Q0g9r8n2KU":3},{"_path":4,"_dir":5,"_draft":6,"_partial":6,"_locale":5,"title":7,"description":5,"summary":8,"order":9,"body":10,"_type":350,"_id":351,"_source":352,"_file":353,"_stem":354,"_extension":355},"\u002Fsecurity-fixes","",false,"Security Fixes — FastYoke","Known security findings and their fix status across FastYoke releases.",6,{"type":11,"children":12,"toc":347},"root",[13,21,112],{"type":14,"tag":15,"props":16,"children":20},"element","hero",{"eyebrow":17,"tagline":18,"title":19},"Trust","A running log of known security findings and the releases that resolved them.","Security fixes",[],{"type":14,"tag":22,"props":23,"children":26},"marketing-section",{"band":24,"max-width":25},"white","6xl",[27],{"type":14,"tag":28,"props":29,"children":38},"section",{"className":30},[31,32,33,34,35,36,37],"mx-auto","max-w-3xl","px-4","py-8","text-base","leading-relaxed","text-[var(--brand-text-secondary)]",[39,63,86],{"type":14,"tag":40,"props":41,"children":42},"p",{},[43,46,53,55,61],{"type":44,"value":45},"text","FastYoke publishes each material security fix once it ships. This page lists\nknown findings — both ones we found internally and ones reported by customers\nor external researchers — and shows the release that resolved each. For our\nbroader privacy posture and legal terms, see ",{"type":14,"tag":47,"props":48,"children":50},"a",{"href":49},"\u002Fprivacy",[51],{"type":44,"value":52},"Privacy",{"type":44,"value":54}," and\n",{"type":14,"tag":47,"props":56,"children":58},{"href":57},"\u002Fterms",[59],{"type":44,"value":60},"Terms",{"type":44,"value":62},".",{"type":14,"tag":64,"props":65,"children":68},"callout",{"title":66,"type":67},"Reporting a vulnerability","info",[69],{"type":14,"tag":40,"props":70,"children":71},{},[72,74,84],{"type":44,"value":73},"Email ",{"type":14,"tag":75,"props":76,"children":77},"strong",{},[78],{"type":14,"tag":47,"props":79,"children":81},{"href":80},"mailto:security@fastyoke.io",[82],{"type":44,"value":83},"security@fastyoke.io",{"type":44,"value":85}," with steps to reproduce and any impact you've\nobserved. We acknowledge new reports within two business days.",{"type":14,"tag":40,"props":87,"children":88},{},[89,91,96,98,103,105,110],{"type":44,"value":90},"Status: ",{"type":14,"tag":75,"props":92,"children":93},{},[94],{"type":44,"value":95},"Fixed",{"type":44,"value":97}," — resolved in the listed release; customers on that version\nor newer are not exposed. ",{"type":14,"tag":75,"props":99,"children":100},{},[101],{"type":44,"value":102},"Mitigated",{"type":44,"value":104}," — a compensating control prevents\nexploitation; a code-level fix is pending. ",{"type":14,"tag":75,"props":106,"children":107},{},[108],{"type":44,"value":109},"Investigating",{"type":44,"value":111}," — acknowledged\nand under triage.",{"type":14,"tag":22,"props":113,"children":115},{"band":114,"max-width":25},"gray",[116,121,134,184,217,265,278,304,313,322],{"type":14,"tag":117,"props":118,"children":120},"div",{"id":119},"security-fixes-list",[],{"type":14,"tag":122,"props":123,"children":128},"security-fix",{"fixed-at":124,"fixed-in":125,"status":126,"title":127},"2026-06-07","3.19.0","fixed","Role-based access control enforcement hardening",[129],{"type":14,"tag":40,"props":130,"children":131},{},[132],{"type":44,"value":133},"We closed gaps where some authorization checks weren't consistently enforced: certain\nentity-write actions and the Settings area could be reached by roles that shouldn't have\nhad access. Role permissions are now enforced on entity writes, Settings is restricted to\nadministrators and managers, and the Manager system role was completed so role names\nresolve correctly. No abuse was observed; this tightens least-privilege enforcement across\nthe admin application.",{"type":14,"tag":122,"props":135,"children":139},{"fixed-at":136,"fixed-in":137,"status":126,"title":138},"2026-06-04","3.16.0","Admin session tokens moved out of browser storage (XSS hardening)",[140],{"type":14,"tag":40,"props":141,"children":142},{},[143,145,152,154,160,162,168,169,175,177,182],{"type":44,"value":144},"The admin application previously kept its session token (a JWT) in the\nbrowser's ",{"type":14,"tag":146,"props":147,"children":149},"code",{"className":148},[],[150],{"type":44,"value":151},"localStorage",{"type":44,"value":153},". A script injected through a cross-site-scripting\nflaw could read it from storage and reuse it elsewhere. The token is now\ncarried in an ",{"type":14,"tag":146,"props":155,"children":157},{"className":156},[],[158],{"type":44,"value":159},"HttpOnly",{"type":44,"value":161},", ",{"type":14,"tag":146,"props":163,"children":165},{"className":164},[],[166],{"type":44,"value":167},"Secure",{"type":44,"value":161},{"type":14,"tag":146,"props":170,"children":172},{"className":171},[],[173],{"type":44,"value":174},"SameSite=Strict",{"type":44,"value":176}," cookie that page scripts\ncannot read, and it is no longer written to ",{"type":14,"tag":146,"props":178,"children":180},{"className":179},[],[181],{"type":44,"value":151},{"type":44,"value":183},"; the live-updates\nWebSocket also authenticates from that cookie instead of a token placed in the\nURL. This is defense-in-depth — we have no report of an exploit — that limits\nthe reach of any future cross-site-scripting flaw to a single browser tab\nrather than a portable, stealable token. The platform-admin and\norganization-admin consoles received the same treatment.",{"type":14,"tag":122,"props":185,"children":187},{"fixed-at":136,"fixed-in":137,"status":126,"title":186},"Stricter origin matching for embedded-form framing",[188],{"type":14,"tag":40,"props":189,"children":190},{},[191,193,199,201,207,209,215],{"type":44,"value":192},"Tenants choose which sites may embed their hosted forms in an iframe, and\nFastYoke enforces that allow-list with a Content-Security-Policy\n",{"type":14,"tag":146,"props":194,"children":196},{"className":195},[],[197],{"type":44,"value":198},"frame-ancestors",{"type":44,"value":200}," directive. Origin comparison is now scheme-exact: a bare\nhost on the allow-list matches only its ",{"type":14,"tag":146,"props":202,"children":204},{"className":203},[],[205],{"type":44,"value":206},"https:\u002F\u002F",{"type":44,"value":208}," origin, and an entry that\nalready includes a scheme matches that scheme exactly. Previously the scheme\nwas disregarded when comparing, so an insecure (",{"type":14,"tag":146,"props":210,"children":212},{"className":211},[],[213],{"type":44,"value":214},"http:\u002F\u002F",{"type":44,"value":216},") variant of an\nallowed host could satisfy the check. No abuse was observed; this tightens the\nembedding boundary against a downgraded-origin framing attempt.",{"type":14,"tag":122,"props":218,"children":222},{"fixed-at":136,"fixed-in":137,"status":126,"title":219,"advisory-label":220,"advisory-url":221},"Uninitialized memory disclosure in the ws library (build-time dependency)","GHSA-58qx-3vcg-4xpx","https:\u002F\u002Fgithub.com\u002Fadvisories\u002FGHSA-58qx-3vcg-4xpx",[223],{"type":14,"tag":40,"props":224,"children":225},{},[226,228,234,236,242,244,249,251,256,258,263],{"type":44,"value":227},"A moderate advisory (CVE-2026-45736) in the ",{"type":14,"tag":146,"props":229,"children":231},{"className":230},[],[232],{"type":44,"value":233},"ws",{"type":44,"value":235}," Node WebSocket library\nreported that ",{"type":14,"tag":146,"props":237,"children":239},{"className":238},[],[240],{"type":44,"value":241},"websocket.close()",{"type":44,"value":243}," could disclose uninitialized memory when\ngiven a typed-array reason argument. In FastYoke ",{"type":14,"tag":146,"props":245,"children":247},{"className":246},[],[248],{"type":44,"value":233},{"type":44,"value":250}," appears only as a\nbuild-, development-, and test-time transitive dependency (Nuxt tooling and\nthe test DOM environment); the shipped product uses the browser's native\nWebSocket on the client and a Rust WebSocket server on the backend — neither\nis the ",{"type":14,"tag":146,"props":252,"children":254},{"className":253},[],[255],{"type":44,"value":233},{"type":44,"value":257}," library — so no shipped release was exposed to the vulnerable\npath. We updated to ",{"type":14,"tag":146,"props":259,"children":261},{"className":260},[],[262],{"type":44,"value":233},{"type":44,"value":264}," ≥ 8.20.1 to clear the advisory and keep the\ndependency tree clean.",{"type":14,"tag":122,"props":266,"children":272},{"fixed-at":267,"fixed-in":268,"status":126,"title":269,"advisory-label":270,"advisory-url":271},"2026-05-15","3.1.2","TLS hostname-verification regression in lettre's boring-tls backend","RUSTSEC-2026-0141","https:\u002F\u002Frustsec.org\u002Fadvisories\u002FRUSTSEC-2026-0141",[273],{"type":14,"tag":40,"props":274,"children":275},{},[276],{"type":44,"value":277},"A bug in lettre 0.11.21's boring-tls integration silently disabled TLS\nhostname verification for callers on that backend. FastYoke compiles lettre\nwith rustls, so no shipped release of FastYoke was exposed to the vulnerable\ncode path. We bumped to 0.11.22 to clear the advisory and remove the flagged\ncrate from our dependency tree.",{"type":14,"tag":122,"props":279,"children":282},{"fixed-at":267,"fixed-in":280,"status":126,"title":281},"3.1.0","Production CORS now refuses to start without an allow-list",[283],{"type":14,"tag":40,"props":284,"children":285},{},[286,288,294,296,302],{"type":44,"value":287},"The backend previously fell back to a permissive\n",{"type":14,"tag":146,"props":289,"children":291},{"className":290},[],[292],{"type":44,"value":293},"Access-Control-Allow-Origin: *",{"type":44,"value":295}," when ",{"type":14,"tag":146,"props":297,"children":299},{"className":298},[],[300],{"type":44,"value":301},"CORS_ALLOWED_ORIGINS",{"type":44,"value":303}," was unset. We\nchanged production deploys to refuse to start without an explicit allow-list,\nmatching the fail-closed posture used for the JWT signing secret. Sandbox and\nlocal-dev environments keep the permissive fallback so browser-based testing\nisn't blocked.",{"type":14,"tag":122,"props":305,"children":307},{"fixed-at":267,"fixed-in":280,"status":126,"title":306},"API-layer audit remediation",[308],{"type":14,"tag":40,"props":309,"children":310},{},[311],{"type":44,"value":312},"We ran a comprehensive audit of the API layer covering tenant-isolation gaps,\nSSRF egress vectors, authentication hardening, and reflected XSS surfaces.\nAll findings were remediated and shipped before any release of v3 reached\ngeneral availability.",{"type":14,"tag":122,"props":314,"children":316},{"fixed-at":267,"fixed-in":280,"status":126,"title":315},"Connection-listing endpoints now require explicit permission",[317],{"type":14,"tag":40,"props":318,"children":319},{},[320],{"type":44,"value":321},"The endpoints that list and read integration connections previously allowed\nany authenticated identity to enumerate which providers a tenant had\nconfigured — a useful reconnaissance signal for an attacker holding a\nlow-privilege token. They now require the same permission that gates\nconnection creation and deletion. The cancel endpoint for FSM jobs was also\ntightened to resolve the tenant id from the session, not from request input.",{"type":14,"tag":122,"props":323,"children":325},{"fixed-at":267,"fixed-in":280,"status":126,"title":324},"Per-route rate limiting on unauthenticated surfaces",[326],{"type":14,"tag":40,"props":327,"children":328},{},[329,331,337,339,345],{"type":44,"value":330},"Three unauthenticated request paths — login, invitation acceptance, and\npublic form submission — previously had no per-IP throttle and were bounded\nonly by CPU. Each now mounts a token-bucket limiter with a ",{"type":14,"tag":146,"props":332,"children":334},{"className":333},[],[335],{"type":44,"value":336},"Retry-After",{"type":44,"value":338},"\nresponse on rejection. Login and invitation acceptance throttle per source\nIP; form submission throttles per ",{"type":14,"tag":146,"props":340,"children":342},{"className":341},[],[343],{"type":44,"value":344},"(source IP, form slug)",{"type":44,"value":346}," so cross-form\nabuse from one IP is caught while a single user submitting to multiple forms\nis not penalised.",{"title":5,"searchDepth":348,"depth":348,"links":349},2,[],"markdown","content:security-fixes.md","content","security-fixes.md","security-fixes","md",1783575522402]