@dogsbay/render-html 0.2.0-beta.118 → 0.2.0-beta.120

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/css/api.css CHANGED
@@ -1,5 +1,8 @@
1
1
  /* Generated by packages/render-html/scripts/sync-sources.mjs from @dogsbay/ui api-symbol.css, api-source.css, EndpointSection.astro, PropertyItem.astro. Do not edit. */
2
- /* API Symbol badges — colored by kind */
2
+ /* API Symbol badges, coloured by kind. Text on its own 20% tint must reach
3
+ WCAG AA (4.5:1) on the page background: the light colours were L 0.5–0.6
4
+ (3.2–4.0:1) and are L 0.44 (5.0:1 or more); render-html's
5
+ tests/contrast.test.ts measures every kind in both modes. */
3
6
  .api-badge {
4
7
  display: inline-flex;
5
8
  align-items: center;
@@ -14,8 +17,8 @@
14
17
  }
15
18
 
16
19
  .api-badge-class {
17
- background-color: oklch(0.55 0.18 265 / 0.2);
18
- color: oklch(0.55 0.18 265);
20
+ background-color: oklch(0.44 0.18 265 / 0.2);
21
+ color: oklch(0.44 0.18 265);
19
22
  }
20
23
  .dark .api-badge-class {
21
24
  background-color: oklch(0.7 0.15 265 / 0.2);
@@ -23,8 +26,8 @@
23
26
  }
24
27
 
25
28
  .api-badge-meth {
26
- background-color: oklch(0.55 0.15 155 / 0.2);
27
- color: oklch(0.55 0.15 155);
29
+ background-color: oklch(0.44 0.15 155 / 0.2);
30
+ color: oklch(0.44 0.15 155);
28
31
  }
29
32
  .dark .api-badge-meth {
30
33
  background-color: oklch(0.7 0.15 155 / 0.2);
@@ -32,8 +35,8 @@
32
35
  }
33
36
 
34
37
  .api-badge-attr {
35
- background-color: oklch(0.6 0.15 55 / 0.2);
36
- color: oklch(0.6 0.15 55);
38
+ background-color: oklch(0.44 0.15 55 / 0.2);
39
+ color: oklch(0.44 0.15 55);
37
40
  }
38
41
  .dark .api-badge-attr {
39
42
  background-color: oklch(0.75 0.15 55 / 0.2);
@@ -41,8 +44,8 @@
41
44
  }
42
45
 
43
46
  .api-badge-func {
44
- background-color: oklch(0.55 0.18 330 / 0.2);
45
- color: oklch(0.55 0.18 330);
47
+ background-color: oklch(0.44 0.18 330 / 0.2);
48
+ color: oklch(0.44 0.18 330);
46
49
  }
47
50
  .dark .api-badge-func {
48
51
  background-color: oklch(0.7 0.15 330 / 0.2);
@@ -50,8 +53,8 @@
50
53
  }
51
54
 
52
55
  .api-badge-module {
53
- background-color: oklch(0.5 0.12 200 / 0.2);
54
- color: oklch(0.5 0.12 200);
56
+ background-color: oklch(0.44 0.12 200 / 0.2);
57
+ color: oklch(0.44 0.12 200);
55
58
  }
56
59
  .dark .api-badge-module {
57
60
  background-color: oklch(0.65 0.12 200 / 0.2);
@@ -1,4 +1,4 @@
1
- /** Block Markdown → HTML (an operation's description). */
1
+ /** Block Markdown → HTML (an operation's description); headings become bold paragraphs. */
2
2
  export declare function apiBlockHtml(text: string): string;
3
3
  /** One line of Markdown → inline HTML (a parameter or property). */
4
4
  export declare function apiInlineHtml(text: string): string;
@@ -13,9 +13,18 @@
13
13
  */
14
14
  import MarkdownIt from "markdown-it";
15
15
  const md = new MarkdownIt({ html: false, linkify: false, typographer: false });
16
- /** Block Markdown → HTML (an operation's description). */
16
+ /**
17
+ * The description's own headings as bold paragraphs: an operation sits
18
+ * under the page's outline (a tag h2, or only the page h1), and an `## Auth`
19
+ * in a spec description put an h2 inside the card, skipping or breaking the
20
+ * page's heading order (axe heading-order).
21
+ */
22
+ const blockMd = new MarkdownIt({ html: false, linkify: false, typographer: false });
23
+ blockMd.renderer.rules.heading_open = () => "<p><strong>";
24
+ blockMd.renderer.rules.heading_close = () => "</strong></p>\n";
25
+ /** Block Markdown → HTML (an operation's description); headings become bold paragraphs. */
17
26
  export function apiBlockHtml(text) {
18
- return md.render(text).trim();
27
+ return blockMd.render(text).trim();
19
28
  }
20
29
  /** One line of Markdown → inline HTML (a parameter or property). */
21
30
  export function apiInlineHtml(text) {
package/dist/api.js CHANGED
@@ -30,7 +30,9 @@ function apiSymbol(n, ctx) {
30
30
  const kind = str(p.kind) ?? "func";
31
31
  const signature = str(p.signature);
32
32
  const bases = Array.isArray(p.bases) ? p.bases.map(String) : [];
33
- const level = n.type === "api-class" ? 2 : 3;
33
+ // apiSymbolLevels' rule (@dogsbay/serialize-core), applied as the page renders: one below the
34
+ // last heading before the symbol (h2 with none), or one below the enclosing symbol.
35
+ const level = Math.min(6, (ctx.apiParentLevel ?? ctx.lastHeadingLevel ?? 1) + 1);
34
36
  const badgeKind = kind === "method" ? "meth" : kind;
35
37
  // ApiSymbol's slug, so a link to #mypkg-client reaches the same symbol on both pipelines.
36
38
  const id = uniqueId(ctx, name.toLowerCase().replace(/[^\w]/g, "-").replace(/-+/g, "-"));
@@ -41,7 +43,17 @@ function apiSymbol(n, ctx) {
41
43
  `<h${level} id="${esc(id)}" class="!mt-0 !mb-0 !border-0"><code class="text-lg font-semibold">${esc(name)}</code></h${level}></div>` +
42
44
  (signature ? codeHtml(signature, "python", ctx) : "") +
43
45
  (bases.length ? `<p class="api-symbol-bases">Bases: ${bases.map((b) => `<code>${esc(b)}</code>`).join("")}</p>` : "") +
44
- `<div class="mt-3">${renderBlocks(n.children, ctx)}</div></div>\n`);
46
+ `<div class="mt-3">${nested(ctx, level, () => renderBlocks(n.children, ctx))}</div></div>\n`);
47
+ }
48
+ function nested(ctx, level, f) {
49
+ const was = ctx.apiParentLevel;
50
+ ctx.apiParentLevel = level;
51
+ try {
52
+ return f();
53
+ }
54
+ finally {
55
+ ctx.apiParentLevel = was;
56
+ }
45
57
  }
46
58
  const CODE_IN_HTML = /<pre><code(?:\s+class="language-(\w+)")?>([\s\S]*?)<\/code><\/pre>/g;
47
59
  const decodeCode = (s) => s.replace(/&amp;/g, "&").replace(/&lt;/g, "<").replace(/&gt;/g, ">").replace(/&quot;/g, '"');
@@ -172,12 +184,12 @@ const LOCATIONS = [
172
184
  ["header", "Header Parameters"],
173
185
  ["cookie", "Cookie Parameters"],
174
186
  ];
175
- /** PropertyList.astro: parameters grouped by location. */
187
+ /** PropertyList.astro: parameters grouped by location, each group's label a <p> (an h4 skipped a level under an h2). */
176
188
  function propertyList(params, ctx) {
177
189
  const groups = LOCATIONS.map(([loc, label]) => ({ label, items: params.filter((p) => p.in === loc) })).filter((g) => g.items.length);
178
190
  return (`<div>` +
179
191
  groups
180
- .map((g) => `<div class="mb-4 last:mb-0"><h4 class="mb-1 text-[11px] font-semibold uppercase tracking-wider text-muted-foreground">${g.label}</h4>` +
192
+ .map((g) => `<div class="mb-4 last:mb-0"><p class="mb-1 text-[11px] font-semibold uppercase tracking-wider text-muted-foreground">${g.label}</p>` +
181
193
  `<div class="rounded-lg border bg-card">${g.items.map((p) => propertyItem(p, 0, ctx)).join("")}</div></div>`)
182
194
  .join("") +
183
195
  `</div>`);
@@ -268,7 +280,8 @@ function exampleLang(contentType) {
268
280
  return "yaml";
269
281
  return "json";
270
282
  }
271
- const PANEL_HEADING = "mb-3 text-xs font-semibold uppercase tracking-wider text-white/60";
283
+ /** The code column's titles: labels, not headings (an operation page has only its h1 above them). */
284
+ const PANEL_LABEL = "mb-3 text-xs font-semibold uppercase tracking-wider text-white/60";
272
285
  /** The code column's blocks, in format-astro's order: samples, the request body example, response examples. */
273
286
  function codePanels(p) {
274
287
  const out = [];
@@ -310,8 +323,8 @@ function endpoint(n, ctx) {
310
323
  `<div class="space-y-3">${sections}</div></div>`;
311
324
  const panels = codePanels(p)
312
325
  .map((c) => c.samples
313
- ? `<div><h3 class="${PANEL_HEADING}">${esc(c.title)}</h3>${codeSamples(c.samples, ctx)}</div>`
314
- : `<div><h3 class="${PANEL_HEADING}">${esc(c.title)}</h3>${codeHtml(c.code, c.lang, ctx)}</div>`)
326
+ ? `<div><p class="${PANEL_LABEL}">${esc(c.title)}</p>${codeSamples(c.samples, ctx)}</div>`
327
+ : `<div><p class="${PANEL_LABEL}">${esc(c.title)}</p>${codeHtml(c.code, c.lang, ctx)}</div>`)
315
328
  .join("");
316
329
  // Embedded among prose unless the host says the page is an operation page (apiPageLayout in @dogsbay/serialize-core).
317
330
  const page = ctx.embeddedEndpoints === false;
package/dist/render.d.ts CHANGED
@@ -75,6 +75,10 @@ export interface RenderContext {
75
75
  * would flood the TOC. Their ids are reserved either way.
76
76
  */
77
77
  apiSymbolHeadings?: boolean;
78
+ /** The level of the last heading rendered outside an autodoc symbol (set as rendering goes). */
79
+ lastHeadingLevel?: number;
80
+ /** While rendering an autodoc symbol's body: that symbol's heading level. */
81
+ apiParentLevel?: number;
78
82
  }
79
83
  export { FOREIGN_END, FOREIGN_START };
80
84
  export { scriptUrl };
package/dist/render.js CHANGED
@@ -302,6 +302,8 @@ function block(n, ctx) {
302
302
  const id = uniqueId(ctx, str(p.id) ?? str(p.slug) ?? slugify(text));
303
303
  if (level === 2 || level === 3)
304
304
  ctx.headings.push({ depth: level, id, text });
305
+ if (ctx.apiParentLevel === undefined)
306
+ ctx.lastHeadingLevel = level;
305
307
  // Astro serializer: a hover pilcrow link, hidden from assistive tech (the heading is the target).
306
308
  const anchor = level > 1 ? `<a href="#${esc(id)}" class="ml-2 text-muted-foreground no-underline opacity-0 group-hover:opacity-100 focus:opacity-100" aria-hidden="true" tabindex="-1">&para;</a>` : "";
307
309
  const { id: _i, ...rest } = passthrough(p, "group scroll-mt-20");
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@dogsbay/render-html",
3
- "version": "0.2.0-beta.118",
3
+ "version": "0.2.0-beta.120",
4
4
  "description": "Dogsbay MD TreeNode → HTML with the Astro components' markup and classes. No highlighter, math or CSS compiler unless you pass one; Worker- and browser-safe",
5
5
  "type": "module",
6
6
  "main": "./dist/index.js",
@@ -30,9 +30,9 @@
30
30
  "dependencies": {
31
31
  "htmlparser2": "^10.1.0",
32
32
  "markdown-it": "^14.3.0",
33
- "@dogsbay/format-dogsbay-md": "0.2.0-beta.118",
34
- "@dogsbay/types": "0.2.0-beta.118",
35
- "@dogsbay/serialize-core": "0.2.0-beta.118"
33
+ "@dogsbay/format-dogsbay-md": "0.2.0-beta.120",
34
+ "@dogsbay/serialize-core": "0.2.0-beta.120",
35
+ "@dogsbay/types": "0.2.0-beta.120"
36
36
  },
37
37
  "peerDependencies": {
38
38
  "katex": "^0.16.0"