@marianmeres/http-utils
v2.5.1
Published
[](https://www.npmjs.com/package/@marianmeres/http-utils) [](https://jsr.io/@marianmeres/http-utils) [
- 📦 Deno & Node.js - Works in both runtimes
- 🦾 Generic return types - Optional type parameters for typed responses
Installation
deno add jsr:@marianmeres/http-utilsnpm install @marianmeres/http-utilsimport { createHttpApi, opts, HTTP_ERROR } from "@marianmeres/http-utils";Quick Start
import { createHttpApi, opts, HTTP_ERROR, NotFound } from "@marianmeres/http-utils";
// Create an API client with base URL
const api = createHttpApi("https://api.example.com", {
headers: { "Authorization": "Bearer your-token" }
});
// GET request (options API with opts() wrapper)
const users = await api.get("/users", opts({
params: { headers: { "X-Custom": "value" } }
}));
// POST request (options API with opts() wrapper)
const newUser = await api.post("/users", opts({
data: { name: "John Doe" },
params: { headers: { "X-Custom": "value" } }
}));
// Legacy API (default behavior without opts())
const legacyUsers = await api.get("/users", { headers: { "X-Custom": "value" } });
const legacyUser = await api.post("/users", { name: "John Doe" });
// With type parameters for typed responses
interface User { id: number; name: string; }
const user = await api.get<User>("/users/1");
const created = await api.post<User>("/users", opts({ data: { name: "Jane" } }));
// Error handling
try {
await api.get("/not-found");
} catch (error) {
if (error instanceof NotFound) {
console.log("Resource not found");
}
// or use the namespace
if (error instanceof HTTP_ERROR.NotFound) {
console.log(error.status); // 404
console.log(error.body); // Response body
}
}API Overview
createHttpApi(base?, defaults?, errorExtractor?)
Creates an HTTP API client.
const api = createHttpApi("https://api.example.com", {
headers: { "Authorization": "Bearer token" }
});HTTP Methods
// GET (options API with opts() wrapper)
const data = await api.get("/users", opts({
params: { headers: { "X-Custom": "value" } },
respHeaders: {}
}));
// POST/PUT/PATCH/DELETE (options API with opts() wrapper)
await api.post("/users", opts({
data: { name: "John" },
params: { token: "bearer-token" }
}));
// Legacy API (default behavior without opts())
const data = await api.get("/users", { headers: { "X-Custom": "value" } });
await api.post("/users", { name: "John" });The opts() Helper
The opts() function explicitly marks an options object for the options-based API. Without it, arguments are treated as legacy positional parameters.
// Without opts() - legacy behavior: object is sent as request body
await api.post("/users", { data: { name: "John" } }); // Sends: { data: { name: "John" } }
// With opts() - options API: data is extracted and sent as body
await api.post("/users", opts({ data: { name: "John" } })); // Sends: { name: "John" }This makes the API unambiguous and prevents accidental misinterpretation of request data.
Error Handling
import { HTTP_ERROR, NotFound } from "@marianmeres/http-utils";
try {
await api.get("/resource");
} catch (error) {
if (error instanceof NotFound) {
console.log("Not found:", error.body);
}
// All errors have: status, statusText, body, cause
}Key Features
- Auto JSON: Response bodies are automatically parsed as JSON
- Bearer tokens: Use
tokenparam to auto-addAuthorization: Bearerheader - Response headers: Pass
respHeaders: {}to capture response headers - Raw response: Use
raw: trueto get the raw Response object - Non-throwing: Use
assert: falseto prevent throwing on errors - AbortController: Pass
signalfor request cancellation - Typed responses: Use generics for type-safe responses:
api.get<User>("/users/1")
Full API Reference
For complete API documentation including all error classes, HTTP status codes, types, and utilities, see API.md.
Utilities
getErrorMessage(error)
Extracts human-readable messages from any error format:
import { getErrorMessage } from "@marianmeres/http-utils";
try {
await api.get("/fail");
} catch (error) {
console.log(getErrorMessage(error)); // "Not Found"
}createHttpError(code, message?, body?, cause?)
Manually create HTTP errors:
import { createHttpError } from "@marianmeres/http-utils";
const error = createHttpError(404, "User not found", { userId: 123 });
throw error; // instanceof NotFound