Cache control
@duplojs/http/cacheController provides createCacheControllerHooks, a hook that automatically adds the Cache-Control header to matching responses.
The hook only adds the header to 2xx and 3xx responses.
On one route
ts
import { ResponseContract, useRouteBuilder } from "@duplojs/http";
import { createCacheControllerHooks } from "@duplojs/http/cacheController";
import { DPE } from "@duplojs/utils";
const articleSchema = DPE.object({
id: DPE.number(),
title: DPE.string(),
});
useRouteBuilder("GET", "/articles", {
hooks: [
createCacheControllerHooks({
public: true,
maxAge: 300,
staleWhileRevalidate: 60,
}),
],
})
.handler(
ResponseContract.ok("articles.list", articleSchema.array()),
(__, { response }) => response("articles.list", [
{
id: 1,
title: "Hello",
},
]),
);In this case, the configuration only applies to the GET /articles route.
public: trueallows shared caching.maxAge: 300allows a 5-minute cache.staleWhileRevalidate: 60lets clients serve a slightly stale response while revalidating.
On all Hub routes
ts
import { createHub } from "@duplojs/http";
import { createCacheControllerHooks } from "@duplojs/http/cacheController";
export const hub = createHub({ environment: "DEV" })
.addRouteHooks(
createCacheControllerHooks({
private: true,
noCache: true,
}),
);Here, the hook is added globally with addRouteHooks. Every route registered in this Hub inherits the same cache policy.
Config interface
ts
interface CacheControlDirectives {
maxAge?: number;
sMaxAge?: number;
public?: true;
private?: true | string[];
noCache?: true | string[];
noStore?: true;
noTransform?: true;
mustRevalidate?: true;
proxyRevalidate?: true;
immutable?: true;
staleWhileRevalidate?: number;
staleIfError?: number;
mustUnderstand?: true;
extensions?: Record<string, string>;
}Useful notes
privateandnoCachecan also receive a list of header names.extensionslets you add custom directives when you need a more specific header.
