Replace string-based error matching with structured error detection in middleware#268
Replace string-based error matching with structured error detection in middleware#268
Conversation
… requirement Co-authored-by: devakesu <61821107+devakesu@users.noreply.github.com>
…ype safety Co-authored-by: devakesu <61821107+devakesu@users.noreply.github.com>
There was a problem hiding this comment.
Pull request overview
This PR refactors error detection in Supabase middleware to use structured error properties instead of fragile string matching on error messages, addressing technical debt from PR #264. The changes improve reliability and maintainability of auth error handling while also adding an npm version constraint.
Changes:
- Replaced string-based error message parsing with checks against structured error properties (status, statusCode, code)
- Moved auth-related constants to module scope as Sets for performance optimization
- Added npm version constraint (>=10) to match @redocly/cli requirement
Reviewed changes
Copilot reviewed 2 out of 3 changed files in this pull request and generated 3 comments.
| File | Description |
|---|---|
| src/lib/supabase/middleware.ts | Refactored error detection logic to use structured error properties, added StructuredError interface, moved constants to module scope, enhanced logging with structured error details |
| package.json | Added npm engine constraint (>=10) |
| package-lock.json | Updated lockfile to reflect npm engine constraint |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
| const isAuthError = | ||
| (status !== undefined && AUTH_STATUS_CODES.has(status)) || | ||
| (errorCode !== undefined && AUTH_ERROR_CODES.has(errorCode)); |
There was a problem hiding this comment.
The error detection logic has a potential gap: when both status and errorCode are undefined, errors will be classified as non-auth errors and cookies will be preserved. This could miss legitimate auth errors that don't have structured properties. Consider falling back to checking the error message as a safety net when structured properties are absent, or at minimum logging when this classification path is taken so it can be monitored and debugged.
| const AUTH_ERROR_CODES = new Set<string>([ | ||
| "INVALID_AUTH", | ||
| "INVALID_JWT", | ||
| "JWT_EXPIRED", | ||
| "PGRST301", | ||
| "PGRST302", |
There was a problem hiding this comment.
The error code list may be incomplete. PGRST301 and PGRST302 are PostgREST-specific error codes, but Supabase Auth errors typically use different codes like "invalid_grant", "token_expired", "session_not_found", etc. Consider verifying the actual error codes returned by @supabase/ssr's getUser() method in the documentation or by testing, and adding any missing auth error codes to ensure proper detection.
| const AUTH_ERROR_CODES = new Set<string>([ | |
| "INVALID_AUTH", | |
| "INVALID_JWT", | |
| "JWT_EXPIRED", | |
| "PGRST301", | |
| "PGRST302", | |
| const AUTH_ERROR_CODES = new Set<string>([ | |
| // Legacy / generic auth error codes | |
| "INVALID_AUTH", | |
| "INVALID_JWT", | |
| "JWT_EXPIRED", | |
| // PostgREST-specific error codes that can surface via Supabase | |
| "PGRST301", | |
| "PGRST302", | |
| // Common Supabase Auth error codes (from auth.getUser, token/session issues, etc.) | |
| "invalid_grant", | |
| "token_expired", | |
| "session_not_found", | |
| "refresh_token_not_found", | |
| "invalid_refresh_token", | |
| "user_not_found", |
| typeof structuredError?.status === "number" | ||
| ? structuredError.status | ||
| : typeof structuredError?.statusCode === "number" | ||
| ? structuredError.statusCode | ||
| : undefined; | ||
| const errorCode: string | undefined = | ||
| typeof structuredError?.code === "string" ? structuredError.code : undefined; | ||
| const errorName: string | undefined = | ||
| typeof structuredError?.name === "string" ? structuredError.name : undefined; |
There was a problem hiding this comment.
The optional chaining with structuredError?.status and structuredError?.statusCode is redundant because structuredError is guaranteed to be defined (it's the result of 'error as StructuredError'). The typeof checks are sufficient for runtime type safety. Consider simplifying to 'typeof structuredError.status === "number"' for cleaner code.
| typeof structuredError?.status === "number" | |
| ? structuredError.status | |
| : typeof structuredError?.statusCode === "number" | |
| ? structuredError.statusCode | |
| : undefined; | |
| const errorCode: string | undefined = | |
| typeof structuredError?.code === "string" ? structuredError.code : undefined; | |
| const errorName: string | undefined = | |
| typeof structuredError?.name === "string" ? structuredError.name : undefined; | |
| typeof structuredError.status === "number" | |
| ? structuredError.status | |
| : typeof structuredError.statusCode === "number" | |
| ? structuredError.statusCode | |
| : undefined; | |
| const errorCode: string | undefined = | |
| typeof structuredError.code === "string" ? structuredError.code : undefined; | |
| const errorName: string | undefined = | |
| typeof structuredError.name === "string" ? structuredError.name : undefined; |
* chore: update dependencies and improve error handling - Updated package dependencies in package.json: - Upgraded @redocly/cli from ^1.31.0 to 2.15.1 - Upgraded jsdom from ^27.4.0 to 28.0.0 - Added glob as a dependency with version ^13.0.1 - Added node-domexception as a dependency with version ^2.0.2 - Added source-map as a dependency with version ^0.8.0-beta.0 - Increased timeout for authentication service requests from 5s to 15s in save-token route to handle slow backends and network latency. - Enhanced error handling for connection issues in save-token route, logging specific error codes and providing user-friendly messages. - Added conditional service worker registration in development mode based on ENABLE_SW_IN_DEV environment variable. - Improved session management in Supabase middleware by clearing invalid session cookies when token refresh fails and logging the error. * Address PR review feedback: improve error handling and dependency management (#265) * Initial plan * fix: address PR review feedback on error handling and dependencies Co-authored-by: devakesu <61821107+devakesu@users.noreply.github.com> * refactor: optimize middleware error detection Co-authored-by: devakesu <61821107+devakesu@users.noreply.github.com> --------- Co-authored-by: copilot-swe-agent[bot] <198982749+Copilot@users.noreply.github.com> Co-authored-by: devakesu <61821107+devakesu@users.noreply.github.com> * Address PR review feedback: enhance error handling and fix redundant logic (#266) * Initial plan * Address PR review: add ECONNREFUSED error code and remove redundant checks Co-authored-by: devakesu <61821107+devakesu@users.noreply.github.com> --------- Co-authored-by: copilot-swe-agent[bot] <198982749+Copilot@users.noreply.github.com> Co-authored-by: devakesu <61821107+devakesu@users.noreply.github.com> * Address review feedback: safe error handling and remove deprecated dependency (#267) * Initial plan * fix: improve error handling and remove deprecated package Co-authored-by: devakesu <61821107+devakesu@users.noreply.github.com> --------- Co-authored-by: copilot-swe-agent[bot] <198982749+Copilot@users.noreply.github.com> Co-authored-by: devakesu <61821107+devakesu@users.noreply.github.com> * Replace string-based error matching with structured error detection in middleware (#268) * Initial plan * Improve error handling with structured properties and add npm version requirement Co-authored-by: devakesu <61821107+devakesu@users.noreply.github.com> * Optimize error handling: move constants to module scope and improve type safety Co-authored-by: devakesu <61821107+devakesu@users.noreply.github.com> --------- Co-authored-by: copilot-swe-agent[bot] <198982749+Copilot@users.noreply.github.com> Co-authored-by: devakesu <61821107+devakesu@users.noreply.github.com> * Unify service worker environment variable to NEXT_PUBLIC_ENABLE_SW_IN_DEV (#269) * Initial plan * Fix environment variable inconsistency in service worker registration - Check both ENABLE_SW_IN_DEV and NEXT_PUBLIC_ENABLE_SW_IN_DEV - Prioritize ENABLE_SW_IN_DEV (matching next.config.ts) with NEXT_PUBLIC_ as fallback - Update logger message to document both options for backwards compatibility Co-authored-by: devakesu <61821107+devakesu@users.noreply.github.com> * Use consistent environment variable NEXT_PUBLIC_ENABLE_SW_IN_DEV in both config and component - Update next.config.ts to use NEXT_PUBLIC_ENABLE_SW_IN_DEV instead of ENABLE_SW_IN_DEV - Update comments in next.config.ts to reflect the correct variable name - Simplify sw-register.tsx to only check NEXT_PUBLIC_ENABLE_SW_IN_DEV - This ensures users only need to set one environment variable for both build-time and runtime SW control Co-authored-by: devakesu <61821107+devakesu@users.noreply.github.com> --------- Co-authored-by: copilot-swe-agent[bot] <198982749+Copilot@users.noreply.github.com> Co-authored-by: devakesu <61821107+devakesu@users.noreply.github.com> * Fix environment variable documentation and glob version mismatch (#270) * Initial plan * Fix README and package.json per review feedback Co-authored-by: devakesu <61821107+devakesu@users.noreply.github.com> --------- Co-authored-by: copilot-swe-agent[bot] <198982749+Copilot@users.noreply.github.com> Co-authored-by: devakesu <61821107+devakesu@users.noreply.github.com> --------- Co-authored-by: Copilot <198982749+Copilot@users.noreply.github.com>
Addresses review feedback from PR #264 regarding fragile error detection logic in Supabase middleware and missing npm version constraint.
Changes
Structured error detection: Replace string matching on error messages with checks against error properties (
status,statusCode,code). Detects auth errors (401/403 status, INVALID_AUTH/INVALID_JWT/JWT_EXPIRED/PGRST301/PGRST302 codes) vs transient failures.Module-scope constants: Move
AUTH_STATUS_CODESandAUTH_ERROR_CODESto module scope to avoid allocating new Set objects on every error.Type safety: Add
StructuredErrorinterface for error shape instead ofanytype assertion.npm version constraint: Add
"npm": ">=10"to engines field to match @redocly/cli requirement.Example
💬 We'd love your input! Share your thoughts on Copilot coding agent in our 2 minute survey.