@canonical/react-ssr 0.23.0 → 0.25.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/esm/index.js CHANGED
@@ -1,3 +1,4 @@
1
+ export * as adapter from "./lib/adapter/index.js";
1
2
  export * as renderer from "./lib/renderer/index.js";
2
3
  export * as server from "./lib/server/index.js";
3
4
  //# sourceMappingURL=index.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,QAAQ,MAAM,yBAAyB,CAAC;AACpD,OAAO,KAAK,MAAM,MAAM,uBAAuB,CAAC"}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,OAAO,MAAM,wBAAwB,CAAC;AAClD,OAAO,KAAK,QAAQ,MAAM,yBAAyB,CAAC;AACpD,OAAO,KAAK,MAAM,MAAM,uBAAuB,CAAC"}
@@ -0,0 +1,2 @@
1
+ export { buildCacheControl, getMimeType, matchPattern } from "./mime.js";
2
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../../../src/lib/adapter/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,iBAAiB,EAAE,WAAW,EAAE,YAAY,EAAE,MAAM,WAAW,CAAC"}
@@ -0,0 +1,85 @@
1
+ /**
2
+ * Minimal MIME type lookup for static asset serving.
3
+ *
4
+ * Covers the file types commonly produced by Vite builds (scripts, styles,
5
+ * images, fonts, source maps). Adapters use this when the platform doesn't
6
+ * provide native MIME detection (Cloudflare R2, Deno filesystem).
7
+ *
8
+ * No external dependencies — the lookup is a plain record.
9
+ */
10
+ const MIME_TYPES = {
11
+ ".html": "text/html; charset=utf-8",
12
+ ".js": "application/javascript; charset=utf-8",
13
+ ".mjs": "application/javascript; charset=utf-8",
14
+ ".css": "text/css; charset=utf-8",
15
+ ".json": "application/json; charset=utf-8",
16
+ ".svg": "image/svg+xml",
17
+ ".png": "image/png",
18
+ ".jpg": "image/jpeg",
19
+ ".jpeg": "image/jpeg",
20
+ ".gif": "image/gif",
21
+ ".webp": "image/webp",
22
+ ".avif": "image/avif",
23
+ ".ico": "image/x-icon",
24
+ ".woff": "font/woff",
25
+ ".woff2": "font/woff2",
26
+ ".ttf": "font/ttf",
27
+ ".otf": "font/otf",
28
+ ".txt": "text/plain; charset=utf-8",
29
+ ".xml": "application/xml; charset=utf-8",
30
+ ".wasm": "application/wasm",
31
+ ".map": "application/json; charset=utf-8",
32
+ };
33
+ /**
34
+ * Look up the MIME type for a file path based on its extension.
35
+ *
36
+ * Returns `"application/octet-stream"` for unknown extensions.
37
+ *
38
+ * @param path - File path or name (e.g. `"main.abc123.js"`, `"/assets/logo.png"`).
39
+ * @returns The MIME type string.
40
+ */
41
+ export function getMimeType(path) {
42
+ const dotIndex = path.lastIndexOf(".");
43
+ if (dotIndex === -1)
44
+ return "application/octet-stream";
45
+ const ext = path.slice(dotIndex).toLowerCase();
46
+ return MIME_TYPES[ext] ?? "application/octet-stream";
47
+ }
48
+ /**
49
+ * Build a `Cache-Control` header value from a cache configuration.
50
+ *
51
+ * @param cache - Cache configuration with optional directives.
52
+ * @returns A `Cache-Control` header string.
53
+ */
54
+ export function buildCacheControl(cache) {
55
+ const parts = [];
56
+ if (cache.maxAge != null)
57
+ parts.push(`max-age=${cache.maxAge}`);
58
+ if (cache.sMaxAge != null)
59
+ parts.push(`s-maxage=${cache.sMaxAge}`);
60
+ if (cache.staleWhileRevalidate != null)
61
+ parts.push(`stale-while-revalidate=${cache.staleWhileRevalidate}`);
62
+ return parts.length > 0 ? `public, ${parts.join(", ")}` : "public";
63
+ }
64
+ /**
65
+ * Match a URL pathname against a simple pattern.
66
+ *
67
+ * Supports three forms:
68
+ * - Exact match: `"/sitemap.xml"` matches only `"/sitemap.xml"`
69
+ * - Wildcard suffix: `"/api/*"` matches `"/api/"` and anything below
70
+ * - Catch-all: `"/*"` matches everything
71
+ *
72
+ * @param pattern - The route pattern.
73
+ * @param pathname - The URL pathname to test.
74
+ * @returns `true` if the pathname matches the pattern.
75
+ */
76
+ export function matchPattern(pattern, pathname) {
77
+ if (pattern === "/*")
78
+ return true;
79
+ if (pattern.endsWith("/*")) {
80
+ const prefix = pattern.slice(0, -2);
81
+ return pathname === prefix || pathname.startsWith(`${prefix}/`);
82
+ }
83
+ return pathname === pattern;
84
+ }
85
+ //# sourceMappingURL=mime.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"mime.js","sourceRoot":"","sources":["../../../../src/lib/adapter/mime.ts"],"names":[],"mappings":"AAAA;;;;;;;;GAQG;AAEH,MAAM,UAAU,GAA2B;IACzC,OAAO,EAAE,0BAA0B;IACnC,KAAK,EAAE,uCAAuC;IAC9C,MAAM,EAAE,uCAAuC;IAC/C,MAAM,EAAE,yBAAyB;IACjC,OAAO,EAAE,iCAAiC;IAC1C,MAAM,EAAE,eAAe;IACvB,MAAM,EAAE,WAAW;IACnB,MAAM,EAAE,YAAY;IACpB,OAAO,EAAE,YAAY;IACrB,MAAM,EAAE,WAAW;IACnB,OAAO,EAAE,YAAY;IACrB,OAAO,EAAE,YAAY;IACrB,MAAM,EAAE,cAAc;IACtB,OAAO,EAAE,WAAW;IACpB,QAAQ,EAAE,YAAY;IACtB,MAAM,EAAE,UAAU;IAClB,MAAM,EAAE,UAAU;IAClB,MAAM,EAAE,2BAA2B;IACnC,MAAM,EAAE,gCAAgC;IACxC,OAAO,EAAE,kBAAkB;IAC3B,MAAM,EAAE,iCAAiC;CAC1C,CAAC;AAEF;;;;;;;GAOG;AACH,MAAM,UAAU,WAAW,CAAC,IAAY;IACtC,MAAM,QAAQ,GAAG,IAAI,CAAC,WAAW,CAAC,GAAG,CAAC,CAAC;IACvC,IAAI,QAAQ,KAAK,CAAC,CAAC;QAAE,OAAO,0BAA0B,CAAC;IACvD,MAAM,GAAG,GAAG,IAAI,CAAC,KAAK,CAAC,QAAQ,CAAC,CAAC,WAAW,EAAE,CAAC;IAC/C,OAAO,UAAU,CAAC,GAAG,CAAC,IAAI,0BAA0B,CAAC;AACvD,CAAC;AAED;;;;;GAKG;AACH,MAAM,UAAU,iBAAiB,CAAC,KAIjC;IACC,MAAM,KAAK,GAAa,EAAE,CAAC;IAC3B,IAAI,KAAK,CAAC,MAAM,IAAI,IAAI;QAAE,KAAK,CAAC,IAAI,CAAC,WAAW,KAAK,CAAC,MAAM,EAAE,CAAC,CAAC;IAChE,IAAI,KAAK,CAAC,OAAO,IAAI,IAAI;QAAE,KAAK,CAAC,IAAI,CAAC,YAAY,KAAK,CAAC,OAAO,EAAE,CAAC,CAAC;IACnE,IAAI,KAAK,CAAC,oBAAoB,IAAI,IAAI;QACpC,KAAK,CAAC,IAAI,CAAC,0BAA0B,KAAK,CAAC,oBAAoB,EAAE,CAAC,CAAC;IACrE,OAAO,KAAK,CAAC,MAAM,GAAG,CAAC,CAAC,CAAC,CAAC,WAAW,KAAK,CAAC,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC,CAAC,QAAQ,CAAC;AACrE,CAAC;AAED;;;;;;;;;;;GAWG;AACH,MAAM,UAAU,YAAY,CAAC,OAAe,EAAE,QAAgB;IAC5D,IAAI,OAAO,KAAK,IAAI;QAAE,OAAO,IAAI,CAAC;IAClC,IAAI,OAAO,CAAC,QAAQ,CAAC,IAAI,CAAC,EAAE,CAAC;QAC3B,MAAM,MAAM,GAAG,OAAO,CAAC,KAAK,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC;QACpC,OAAO,QAAQ,KAAK,MAAM,IAAI,QAAQ,CAAC,UAAU,CAAC,GAAG,MAAM,GAAG,CAAC,CAAC;IAClE,CAAC;IACD,OAAO,QAAQ,KAAK,OAAO,CAAC;AAC9B,CAAC"}
@@ -0,0 +1,10 @@
1
+ /**
2
+ * Shared type contracts for SSR deployment adapters.
3
+ *
4
+ * These types define the interface between platform-specific adapters
5
+ * (Cloudflare Workers, Vercel, Deno Deploy) and the transport-agnostic
6
+ * renderers in `@canonical/react-ssr`. Adapters consume these types;
7
+ * renderers satisfy them.
8
+ */
9
+ export {};
10
+ //# sourceMappingURL=types.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"types.js","sourceRoot":"","sources":["../../../../src/lib/adapter/types.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG"}
@@ -1,3 +1,4 @@
1
+ export * as adapter from "./adapter/index.js";
1
2
  export * as renderer from "./renderer/index.js";
2
3
  export * as server from "./server/index.js";
3
4
  //# sourceMappingURL=index.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/lib/index.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,QAAQ,MAAM,qBAAqB,CAAC;AAChD,OAAO,KAAK,MAAM,MAAM,mBAAmB,CAAC"}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/lib/index.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,OAAO,MAAM,oBAAoB,CAAC;AAC9C,OAAO,KAAK,QAAQ,MAAM,qBAAqB,CAAC;AAChD,OAAO,KAAK,MAAM,MAAM,mBAAmB,CAAC"}
@@ -1,3 +1,4 @@
1
+ export * as adapter from "./lib/adapter/index.js";
1
2
  export * as renderer from "./lib/renderer/index.js";
2
3
  export * as server from "./lib/server/index.js";
3
4
  //# sourceMappingURL=index.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,QAAQ,MAAM,yBAAyB,CAAC;AACpD,OAAO,KAAK,MAAM,MAAM,uBAAuB,CAAC"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,OAAO,MAAM,wBAAwB,CAAC;AAClD,OAAO,KAAK,QAAQ,MAAM,yBAAyB,CAAC;AACpD,OAAO,KAAK,MAAM,MAAM,uBAAuB,CAAC"}
@@ -0,0 +1,3 @@
1
+ export { buildCacheControl, getMimeType, matchPattern } from "./mime.js";
2
+ export type { CacheConfig, RendererFactory, RendererResult, RouteDefinition, StaticAssetConfig, } from "./types.js";
3
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../../src/lib/adapter/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,iBAAiB,EAAE,WAAW,EAAE,YAAY,EAAE,MAAM,WAAW,CAAC;AACzE,YAAY,EACV,WAAW,EACX,eAAe,EACf,cAAc,EACd,eAAe,EACf,iBAAiB,GAClB,MAAM,YAAY,CAAC"}
@@ -0,0 +1,43 @@
1
+ /**
2
+ * Minimal MIME type lookup for static asset serving.
3
+ *
4
+ * Covers the file types commonly produced by Vite builds (scripts, styles,
5
+ * images, fonts, source maps). Adapters use this when the platform doesn't
6
+ * provide native MIME detection (Cloudflare R2, Deno filesystem).
7
+ *
8
+ * No external dependencies — the lookup is a plain record.
9
+ */
10
+ /**
11
+ * Look up the MIME type for a file path based on its extension.
12
+ *
13
+ * Returns `"application/octet-stream"` for unknown extensions.
14
+ *
15
+ * @param path - File path or name (e.g. `"main.abc123.js"`, `"/assets/logo.png"`).
16
+ * @returns The MIME type string.
17
+ */
18
+ export declare function getMimeType(path: string): string;
19
+ /**
20
+ * Build a `Cache-Control` header value from a cache configuration.
21
+ *
22
+ * @param cache - Cache configuration with optional directives.
23
+ * @returns A `Cache-Control` header string.
24
+ */
25
+ export declare function buildCacheControl(cache: {
26
+ maxAge?: number;
27
+ sMaxAge?: number;
28
+ staleWhileRevalidate?: number;
29
+ }): string;
30
+ /**
31
+ * Match a URL pathname against a simple pattern.
32
+ *
33
+ * Supports three forms:
34
+ * - Exact match: `"/sitemap.xml"` matches only `"/sitemap.xml"`
35
+ * - Wildcard suffix: `"/api/*"` matches `"/api/"` and anything below
36
+ * - Catch-all: `"/*"` matches everything
37
+ *
38
+ * @param pattern - The route pattern.
39
+ * @param pathname - The URL pathname to test.
40
+ * @returns `true` if the pathname matches the pattern.
41
+ */
42
+ export declare function matchPattern(pattern: string, pathname: string): boolean;
43
+ //# sourceMappingURL=mime.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"mime.d.ts","sourceRoot":"","sources":["../../../../src/lib/adapter/mime.ts"],"names":[],"mappings":"AAAA;;;;;;;;GAQG;AA0BH;;;;;;;GAOG;AACH,wBAAgB,WAAW,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM,CAKhD;AAED;;;;;GAKG;AACH,wBAAgB,iBAAiB,CAAC,KAAK,EAAE;IACvC,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,oBAAoB,CAAC,EAAE,MAAM,CAAC;CAC/B,GAAG,MAAM,CAOT;AAED;;;;;;;;;;;GAWG;AACH,wBAAgB,YAAY,CAAC,OAAO,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,GAAG,OAAO,CAOvE"}
@@ -0,0 +1,85 @@
1
+ /**
2
+ * Shared type contracts for SSR deployment adapters.
3
+ *
4
+ * These types define the interface between platform-specific adapters
5
+ * (Cloudflare Workers, Vercel, Deno Deploy) and the transport-agnostic
6
+ * renderers in `@canonical/react-ssr`. Adapters consume these types;
7
+ * renderers satisfy them.
8
+ */
9
+ /**
10
+ * The subset of a renderer that adapters need to produce a response.
11
+ *
12
+ * Any renderer (`JSXRenderer`, `SitemapRenderer`, `TextRenderer`) satisfies
13
+ * this interface after calling the appropriate render method.
14
+ */
15
+ export interface RendererResult {
16
+ /** Render to a web `ReadableStream` (Bun, Deno, Cloudflare Workers, Vercel Edge). */
17
+ renderToReadableStream: (signal?: AbortSignal) => Promise<ReadableStream>;
18
+ /** HTTP status code determined during rendering. */
19
+ statusCode: number;
20
+ /** Resolves when `statusCode` is determined. */
21
+ statusReady: Promise<void>;
22
+ }
23
+ /**
24
+ * A function that creates a renderer for a given request.
25
+ *
26
+ * All adapters use the Web Standard `Request` type. Adapters running on
27
+ * Node.js (e.g. Vercel serverless) convert `IncomingMessage` to `Request`
28
+ * internally before calling the factory.
29
+ */
30
+ export type RendererFactory = (request: Request) => RendererResult;
31
+ /**
32
+ * A route definition that maps a URL pattern to a renderer factory.
33
+ *
34
+ * Adapters iterate routes in order and use the first match. The pattern
35
+ * uses simple glob matching: `"/*"` matches everything, `"/sitemap.xml"`
36
+ * matches exactly, `"/api/*"` matches any path under `/api/`.
37
+ */
38
+ export interface RouteDefinition {
39
+ /** URL pattern (e.g. `"/sitemap.xml"`, `"/api/*"`, `"/*"`). */
40
+ pattern: string;
41
+ /** Factory that creates a renderer for matched requests. */
42
+ factory: RendererFactory;
43
+ /**
44
+ * Content-Type header for responses from this route.
45
+ * Defaults to `"text/html; charset=utf-8"` when omitted.
46
+ */
47
+ contentType?: string;
48
+ /** Cache configuration for responses from this route. */
49
+ cache?: CacheConfig;
50
+ }
51
+ /**
52
+ * Cache-Control header configuration.
53
+ *
54
+ * Adapters translate these values into platform-appropriate caching:
55
+ * - Cloudflare: Cache API (`caches.default.put`) + `Cache-Control` header
56
+ * - Vercel: `Cache-Control` header (CDN respects `s-maxage`)
57
+ * - Deno: `Cache-Control` header only
58
+ */
59
+ export interface CacheConfig {
60
+ /** Browser cache duration in seconds (`max-age`). */
61
+ maxAge?: number;
62
+ /** CDN/edge cache duration in seconds (`s-maxage`). */
63
+ sMaxAge?: number;
64
+ /** Duration in seconds to serve stale while revalidating (`stale-while-revalidate`). */
65
+ staleWhileRevalidate?: number;
66
+ }
67
+ /**
68
+ * Configuration for serving static assets (CSS, JS, images, fonts).
69
+ *
70
+ * Each entry maps a URL prefix to a source directory. The adapter serves
71
+ * matching requests from the source using the platform's optimal mechanism
72
+ * (R2 on Cloudflare, CDN on Vercel, filesystem on Deno/Bun).
73
+ */
74
+ export interface StaticAssetConfig {
75
+ /** URL path prefix (e.g. `"/assets"`). */
76
+ urlPrefix: string;
77
+ /**
78
+ * Source directory or key prefix.
79
+ * - Cloudflare: R2 key prefix (e.g. `"assets"`)
80
+ * - Vercel: not used (static assets served by CDN from `.vercel/output/static/`)
81
+ * - Deno/Bun: filesystem path (e.g. `"dist/client/assets"`)
82
+ */
83
+ directory: string;
84
+ }
85
+ //# sourceMappingURL=types.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../../../src/lib/adapter/types.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AAEH;;;;;GAKG;AACH,MAAM,WAAW,cAAc;IAC7B,qFAAqF;IACrF,sBAAsB,EAAE,CAAC,MAAM,CAAC,EAAE,WAAW,KAAK,OAAO,CAAC,cAAc,CAAC,CAAC;IAE1E,oDAAoD;IACpD,UAAU,EAAE,MAAM,CAAC;IAEnB,gDAAgD;IAChD,WAAW,EAAE,OAAO,CAAC,IAAI,CAAC,CAAC;CAC5B;AAED;;;;;;GAMG;AACH,MAAM,MAAM,eAAe,GAAG,CAAC,OAAO,EAAE,OAAO,KAAK,cAAc,CAAC;AAEnE;;;;;;GAMG;AACH,MAAM,WAAW,eAAe;IAC9B,+DAA+D;IAC/D,OAAO,EAAE,MAAM,CAAC;IAEhB,4DAA4D;IAC5D,OAAO,EAAE,eAAe,CAAC;IAEzB;;;OAGG;IACH,WAAW,CAAC,EAAE,MAAM,CAAC;IAErB,yDAAyD;IACzD,KAAK,CAAC,EAAE,WAAW,CAAC;CACrB;AAED;;;;;;;GAOG;AACH,MAAM,WAAW,WAAW;IAC1B,qDAAqD;IACrD,MAAM,CAAC,EAAE,MAAM,CAAC;IAEhB,uDAAuD;IACvD,OAAO,CAAC,EAAE,MAAM,CAAC;IAEjB,wFAAwF;IACxF,oBAAoB,CAAC,EAAE,MAAM,CAAC;CAC/B;AAED;;;;;;GAMG;AACH,MAAM,WAAW,iBAAiB;IAChC,0CAA0C;IAC1C,SAAS,EAAE,MAAM,CAAC;IAElB;;;;;OAKG;IACH,SAAS,EAAE,MAAM,CAAC;CACnB"}
@@ -1,3 +1,4 @@
1
+ export * as adapter from "./adapter/index.js";
1
2
  export * as renderer from "./renderer/index.js";
2
3
  export * as server from "./server/index.js";
3
4
  //# sourceMappingURL=index.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/lib/index.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,QAAQ,MAAM,qBAAqB,CAAC;AAChD,OAAO,KAAK,MAAM,MAAM,mBAAmB,CAAC"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/lib/index.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,OAAO,MAAM,oBAAoB,CAAC;AAC9C,OAAO,KAAK,QAAQ,MAAM,qBAAqB,CAAC;AAChD,OAAO,KAAK,MAAM,MAAM,mBAAmB,CAAC"}
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "@canonical/react-ssr",
3
3
  "description": "TBD",
4
- "version": "0.23.0",
4
+ "version": "0.25.0",
5
5
  "type": "module",
6
6
  "module": "dist/esm/index.js",
7
7
  "types": "dist/types/index.d.ts",
@@ -26,6 +26,7 @@
26
26
  },
27
27
  "homepage": "https://github.com/canonical/pragma#readme",
28
28
  "imports": {
29
+ "#adapter": "./src/lib/adapter/index.ts",
29
30
  "#renderer": "./src/lib/renderer/index.ts",
30
31
  "#server": "./src/lib/server/index.ts"
31
32
  },
@@ -58,13 +59,17 @@
58
59
  "./server": {
59
60
  "import": "./dist/esm/lib/server/index.js",
60
61
  "types": "./dist/types/lib/server/index.d.ts"
62
+ },
63
+ "./adapter": {
64
+ "import": "./dist/esm/lib/adapter/index.js",
65
+ "types": "./dist/types/lib/adapter/index.d.ts"
61
66
  }
62
67
  },
63
68
  "devDependencies": {
64
69
  "@biomejs/biome": "2.4.9",
65
- "@canonical/biome-config": "^0.23.0",
66
- "@canonical/typescript-config-react": "^0.23.0",
67
- "@canonical/webarchitect": "^0.23.0",
70
+ "@canonical/biome-config": "^0.25.0",
71
+ "@canonical/typescript-config-react": "^0.25.0",
72
+ "@canonical/webarchitect": "^0.25.0",
68
73
  "@types/express": "^5.0.6",
69
74
  "@types/node": "^24.12.0",
70
75
  "@types/react": "^19.2.14",
@@ -74,7 +79,7 @@
74
79
  "vitest": "^4.0.18"
75
80
  },
76
81
  "dependencies": {
77
- "@canonical/utils": "^0.23.0",
82
+ "@canonical/utils": "^0.25.0",
78
83
  "htmlparser2": "^10.1.0",
79
84
  "react": "^19.2.4",
80
85
  "react-dom": "^19.2.4"
@@ -87,5 +92,5 @@
87
92
  "optional": true
88
93
  }
89
94
  },
90
- "gitHead": "742f5396bc3f9ca01a49646ed5b67acfc9d001d2"
95
+ "gitHead": "c6005a14c8210772ad8c589a2b473946780b6c20"
91
96
  }