-
Notifications
You must be signed in to change notification settings - Fork 0
Getting Started
npm install two-go --save-devNode 18 or newer (it uses the native fetch). ESM only, so use import or a
dynamic import() from CommonJS. Zero runtime dependencies.
go() takes a base URL, or an options object for defaults:
import { go } from "two-go";
const api = go({
baseURL: "https://api.example.com",
headers: { "x-api-key": "secret" },
timeout: 10000,
});
const res = await api.get("/users").query({ page: 1 }).expectStatus(200);
console.log(res.status, res.time, res.get("data[0].name"));Every verb (get, put, post, patch, delete, head, options) returns
a chainable, thenable builder. Awaiting it sends the request and replays the
checks. The resolved GoResponse has status, statusText, headers
(lowercase keys), body (parsed JSON or text), text, time, url, method,
and get(path).
await api.post("/users")
.header("x-request-id", "abc")
.headers({ "x-trace": "1" })
.query({ page: 1, tags: ["a", "b"] })
.bearer("TOKEN")
.json({ name: "Ada" })
.timeout(5000)
.expectStatus(201);Body helpers: .json(obj), .form(obj), .text(str). Absolute http(s)://
paths bypass the base URL.
Because checks throw, there is no adapter. With node:test:
import { test } from "node:test";
import { go } from "two-go";
const api = go("https://api.example.com");
test("GET /users", async () => {
await api.get("/users").expectStatus(200).expectJson("data[0].id");
});node --testJest, Vitest, and Mocha work the same way. There is also a built-in runner and
CLI: put suites in *.twogo.mjs files and run npx two-go.
// test/users.twogo.mjs
import { go, suite } from "two-go";
const api = go("https://api.example.com");
suite("users", ({ test }) => {
test("lists users", async () => {
await api.get("/users").expectStatus(200);
});
});For machine-readable output: npx two-go --reporter junit --out results.xml.