Defjs

Swap Fetch for one client with withHTTPHandle and keep the operation unchanged.

Test with a local Fetch handle

withHTTPHandle(...) replaces Fetch for that client only. You still get URL building, interceptors, status dispatch, and Struct decoding — without DNS, TLS, or a real server.

See Client for details.

import {
  createClient,
  defineRequest,
  struct,
  withEndpoint,
  withHTTPHandle,
} from "@defjs/core";

const getUser = defineRequest({
  method: "GET",
  path: "/users/:id",
  input: struct.object({ id: struct.number() }),
  builder: (input) => ({ path: { id: input.id } }),
  output: struct.object({ id: struct.number(), name: struct.string() }),
  error: struct.object({ message: struct.string() }),
});

const client = createClient(
  withEndpoint("https://fixture.invalid"),
  withHTTPHandle(async (input, init) => {
    const request = new Request(input, init);
    const id = new URL(request.url).pathname.split("/").at(-1);
    if (id === "7")
      return Response.json({ id: 7, name: "Ada" }, { status: 200 });
    return Response.json({ message: "User not found" }, { status: 404 });
  }),
);
async function main() {
  const [error, user, response] = await getUser(client, { id: 7 });
  if (error) {
    // The test boundary rejects failures so the test process cannot pass.
    throw error;
  }
  console.log(user.name, response.status);
}

await main();
Ada 200

Use the same getUser operation against a real withEndpoint(...) client in production — only the handle changes.

Edit this page on GitHub
Released under the MIT License. · Copyright © 2026 MunMunMiao

On this page