Skip to content

feat(utils): introduce errors-as-values convention with tryCatchAsync helper [INTORG-713]#277

Open
Infi-Knight wants to merge 1 commit intostagingfrom
ravi/intorg-713
Open

feat(utils): introduce errors-as-values convention with tryCatchAsync helper [INTORG-713]#277
Infi-Knight wants to merge 1 commit intostagingfrom
ravi/intorg-713

Conversation

@Infi-Knight
Copy link
Copy Markdown
Contributor

@Infi-Knight Infi-Knight commented May 7, 2026

Summary

First sub-issue of INTORG-614. Adds a small tryCatchAsync helper, converts fetchStrapi to return T | Error, and documents the convention in CLAUDE.md.

The previous fetchStrapi quietly returned null on three different failure modes: missing Strapi config, non-ok response, exception inside the catch. Callers couldn't tell "Strapi is down" from "page doesn't exist," and the type signature lied. After this, callers narrow with instanceof Error before they can touch data. The type checker enforces it.

What's in the diff:

  • New tryCatchAsync<T>(fn: () => T | Promise<T>): Promise<T | Error> helper in src/utils/shared/tryCatch.ts and cms/src/utils/tryCatch.ts (mirrored so each side imports through its own utils barrel). Five vitest cases cover success, async rejection, sync throws, non-Error throw coercion, and a sync return.
  • fetchStrapi becomes <T = unknown>(endpoint): Promise<StrapiResponse<T> | Error>.
  • The four SSR preview routes declare typed response shapes (FoundationPagePreview, BlogPostPreview) and handle the Error case explicitly. Behaviour preserved: silent redirect to /404 on the foundation routes, throw on the blog routes.
  • CLAUDE.md gets a new "Errors as Values" section documenting the convention.

Related Issue

INTORG-713 (parent: INTORG-614). Foundation for the CMS-side subs INTORG-714, 715, 716.

Manual Test

The four SSR preview routes:

  1. Strapi works

Checks

  • pnpm run format
  • pnpm run lint

PR Checklist

  • PR title follows Conventional Commits (e.g. feat: ..., fix: ...)
  • Linked issue included
  • Scope is focused (target ~10-20 files when possible)
  • Screenshots for UI changes (if applicable)

… helper [INTORG-713]

The previous fetchStrapi quietly returned null on three different failure
modes (missing Strapi config, non-ok response, exception). Callers couldn't
tell "Strapi is down" from "page doesn't exist," and the type signature lied.

This adds a tryCatchAsync helper in src/utils/shared/ (mirrored to
cms/src/utils/ for later subs) that wraps throwing async work into a typed
T | Error union. fetchStrapi now returns Promise<StrapiResponse<T> | Error>,
so the type checker forces callers to narrow with instanceof Error before
reaching the data field.

The four SSR preview routes are updated to handle the Error case explicitly
and declare the response shape they actually use (FoundationPagePreview,
BlogPostPreview), removing the inline `as` cast that used to live in the
foundation-page previews and dropping any reliance on `any`.

Convention documented in CLAUDE.md under a new "Errors as Values" section.
Foundation for the CMS-side subs INTORG-714, 715, 716.
@netlify
Copy link
Copy Markdown

netlify Bot commented May 7, 2026

Deploy Preview for interledger-org-v5 ready!

Name Link
🔨 Latest commit ff75f35
🔍 Latest deploy log https://app.netlify.com/projects/interledger-org-v5/deploys/69fc68b4d073a300086e0844
😎 Deploy Preview https://deploy-preview-277--interledger-org-v5.netlify.app
📱 Preview on mobile
Toggle QR Code...

QR Code

Use your smartphone camera to open QR code link.

To edit notification comments on pull requests, go to your Netlify project configuration.

@Infi-Knight Infi-Knight self-assigned this May 7, 2026
@Infi-Knight Infi-Knight requested a review from Anca2022 May 7, 2026 11:25
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant