JSPM

@gianstack/result

0.1.0
    • ESM via JSPM
    • ES Module Entrypoint
    • Export Map
    • Keywords
    • License
    • Repository URL
    • TypeScript Types
    • README
    • Created
    • Published
    • Downloads 587
    • Score
      100M100P100Q104349F
    • License MIT

    Transport-agnostic Result and AppError primitives for explicit no-throw expected failures.

    Package Exports

    • @gianstack/result

    Readme

    @gianstack/result

    Transport-agnostic primitives for modeling expected failures without using throw as normal control flow.

    What this package gives you

    • a minimal Result union built around ok / err;
    • a generic AppError shape with stable code: string;
    • one explicit normalizeUnknownError(cause, fallback) entrypoint;
    • small tryResult and tryResultAsync helpers for throw-based APIs;
    • ESM-only output that is safe to consume in Next.js on both server and client.

    What this package does not do

    This package does not provide:

    • a built-in error-code catalog;
    • transport mapping for HTTP, GraphQL, tRPC, or Next.js boundaries;
    • logging, telemetry, or status-code policies;
    • monadic helpers like map, andThen, match, or unwrap.

    The goal is to stay small, explicit, and reusable. Repository-specific error catalogs and transport adapters belong in higher layers.

    Install

    pnpm add @gianstack/result

    Core API

    import {
      appError,
      err,
      normalizeUnknownError,
      ok,
      tryResultAsync,
      type AppError,
      type Result,
    } from "@gianstack/result";
    
    type SaveUserResult = Result<{ id: string }, AppError>;
    
    export async function saveUser(input: string): Promise<SaveUserResult> {
      if (input.length === 0) {
        return err(appError({ code: "validation_failed" }));
      }
    
      const persisted = await tryResultAsync(
        async () => ({ id: input.toLowerCase() }),
        (cause) => appError({ code: "unexpected", cause }),
      );
    
      if (!persisted.ok) {
        return persisted;
      }
    
      return ok(persisted.value);
    }
    
    export function toAppError(cause: unknown): AppError {
      return normalizeUnknownError(cause, { code: "unexpected" });
    }

    Design constraints

    • Expected failures should travel through Result, not throw.
    • Invariant violations should still fail loudly.
    • AppError.message is developer-oriented only.
    • Call sites should branch on error.code, not on message.
    • normalizeUnknownError requires an explicit fallback so the package never invents repository-specific semantics.

    Support matrix

    • ESM only
    • browser-safe runtime
    • server-safe runtime
    • no framework peer dependencies

    Development contract

    Before publishing a new version, this package must pass:

    • pnpm --filter @gianstack/result lint
    • pnpm --filter @gianstack/result check-types
    • pnpm --filter @gianstack/result test
    • pnpm --filter @gianstack/result build
    • pnpm --filter @gianstack/result pack:check
    • pnpm --filter @gianstack/result smoke:consumer

    For repository-level release notes and contributor workflow, see CONTRIBUTING.md and docs/result.md.