Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion _components/Footer.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -59,7 +59,7 @@ const data = [
},
{
label: "Deno API Reference",
href: "/api/deno/~/Deno",
href: "/api/deno/",
},
],
},
Expand Down
2 changes: 1 addition & 1 deletion _components/SidebarNav/comp.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ import ReferenceSidebarNav from "../../reference/_components/ReferenceSidebarNav
export default function (data: Lume.Data) {
const sectionData = data.sectionData;
const currentUrl = data.currentUrl.replace(/\/$/, "");
const isReference = currentUrl.startsWith("/api/");
const isReference = currentUrl === "/api" || currentUrl.startsWith("/api/");

if (isReference) {
return <ReferenceSidebarNav {...data} />;
Expand Down
2 changes: 1 addition & 1 deletion _includes/layout.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -148,7 +148,7 @@ export default function Layout(data: Lume.Data) {
/>
<div
class={`layout ${
data.toc?.length || isReference
(data.toc?.length || isReference) && !data.fullWidth
? "layout--three-column"
: "layout--two-column"
}`}
Expand Down
73 changes: 73 additions & 0 deletions _includes/reference/apiIndex.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,73 @@
import type { Group } from "../../reference/_lib/group.ts";

export const layout = "doc.tsx";

export interface ApiIndexData {
title: string;
intro: string;
aboutUrl: string;
aboutLabel: string;
allSymbolsUrl: string;
groups: { title: string; url: string; slug: string; group: Group }[];
}

/** Landing page for one API kind: a dense, Ctrl+F-able index of every symbol,
* grouped by category/module. Clicking a symbol jumps to its full docs on the
* grouped reference page. */
export default function ApiIndex(
{ data, comp }: { data: ApiIndexData } & Lume.Data,
_helpers: Lume.Helpers,
) {
return (
<main id="content" className="ddoc markdown-body" tabIndex={-1}>
<div className="flex flex-wrap items-baseline justify-between gap-2">
<h1 className="!mb-0">{data.title}</h1>
<p className="!my-0 text-sm whitespace-nowrap">
<a href={data.aboutUrl}>{data.aboutLabel}</a>
{" · "}
<a href={data.allSymbolsUrl}>All symbols</a>
</p>
</div>
<p className="mt-2 max-w-prose text-foreground-secondary">
{data.intro}
</p>

{data.groups.map(({ title, url, slug, group }) => (
<section key={slug} className="mt-8">
<h2 id={slug} className="!mb-2 scroll-mt-16 !border-0">
<a href={url} className="!text-foreground-primary hover:underline">
{title}
</a>
</h2>
<ul className="!list-none !pl-0 !my-0">
{group.sections.flatMap((section) =>
section.nodes.map((node) => (
<li
key={node.name}
className="flex items-baseline gap-2 py-px !mt-0"
aria-label={node.deprecated ? "deprecated" : undefined}
>
<comp.DocNodeKindIcon kinds={node.doc_node_kind_ctx} />
<a
href={node.href}
className={`font-mono text-sm whitespace-nowrap ${
node.deprecated ? "line-through opacity-60" : ""
}`}
>
{node.name}
</a>
{node.docs && (
<div
className="text-sm text-foreground-secondary line-clamp-1 [&_p]:inline [&_div]:inline min-w-0"
dangerouslySetInnerHTML={{ __html: node.docs }}
/>
)}
</li>
))
)}
</ul>
</section>
))}
</main>
);
}
86 changes: 86 additions & 0 deletions _includes/reference/landing.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,86 @@
export const layout = "doc.tsx";

export interface LandingTile {
title: string;
href: string;
description: string | null;
}

export interface LandingSection {
key: string;
title: string;
description: string;
href: string;
allSymbolsHref: string;
tiles: LandingTile[];
/** Render tiles in a denser grid (used for the long Node module list). */
dense?: boolean;
}

export interface LandingData {
intro: string;
sections: LandingSection[];
}

/** The /api/ hub: every API group presented as a tile grid, generated from
* the same grouping data as the reference pages themselves. */
export default function ApiLanding(
{ data }: { data: LandingData } & Lume.Data,
_helpers: Lume.Helpers,
) {
return (
<main
id="content"
className="ddoc markdown-body"
data-color-mode="auto"
data-light-theme="light"
data-dark-theme="dark"
>
<h1>API reference</h1>
<p className="max-w-prose text-foreground-secondary">{data.intro}</p>

{data.sections.map((section) => (
<section key={section.key} className="mt-10">
<header className="flex flex-wrap items-baseline justify-between gap-2">
<h2 className="!mb-0 !border-0">
<a href={section.href} className="!text-foreground-primary">
{section.title}
</a>
</h2>
<a
className="text-sm whitespace-nowrap"
href={section.allSymbolsHref}
>
View all symbols <span aria-hidden="true">-&gt;</span>
</a>
</header>
<p className="mt-2 max-w-prose text-foreground-secondary">
{section.description}
</p>
<div
className={`grid grid-cols-1 sm:grid-cols-2 gap-3 mt-4 ${
section.dense ? "lg:grid-cols-4" : "lg:grid-cols-3"
}`}
>
{section.tiles.map((tile) => (
<a
key={tile.href}
href={tile.href}
className="group flex flex-col gap-1 p-4 rounded-lg border border-foreground-tertiary !no-underline hover:border-primary transition-colors duration-150"
>
<span className="font-semibold !text-foreground-primary group-hover:underline underline-offset-4 decoration-primary">
{tile.title}
</span>
{tile.description && (
<span className="text-sm text-foreground-secondary">
{tile.description}
</span>
)}
</a>
))}
</div>
</section>
))}
</main>
);
}
52 changes: 52 additions & 0 deletions _includes/reference/multiSymbol.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,52 @@
import type { Group } from "../../reference/_lib/group.ts";

export const layout = "doc.tsx";

/** A grouped reference page: every symbol of a category (Deno, Web) or
* module (Node) documented on a single page — a symbol index up top,
* full documentation below. */
export default function MultiSymbol(
{ data, comp }: { data: Group } & Lume.Data,
_helpers: Lume.Helpers,
) {
return (
<comp.Base data={{ breadcrumbs_ctx: data.breadcrumbs }} comp={comp}>
<div className="multiSymbolPage">
<header>
<h1 className="ref-h1">{data.title}</h1>
{data.docs && <div dangerouslySetInnerHTML={{ __html: data.docs }} />}
<comp.UsageLarge usages={data.usage} />
</header>

<section className="mt-8" id="symbol-index">
{data.sections.map((section) => (
<div className="mb-6">
<h2 className="ref-h2" id={section.anchor}>{section.title}</h2>
<comp.NamespaceSection namespaceSections={section.nodes} />
</div>
))}
</section>

<hr className="my-10" />

<section id="symbol-docs">
{data.symbols.map((symbol) => (
<SymbolDivider comp={comp} symbol={symbol} />
))}
</section>
</div>
</comp.Base>
);
}

function SymbolDivider(
// deno-lint-ignore no-explicit-any
{ comp, symbol }: { comp: any; symbol: Group["symbols"][number] },
) {
return (
<>
<comp.SymbolArticle symbol={symbol} />
<hr className="my-10 last:hidden" />
</>
);
}
1 change: 1 addition & 0 deletions api/deno/index.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@
title: "Deno Namespace APIs"
description: "A guide to Deno's built-in runtime APIs. Learn about file system operations, network functionality, permissions management, and other core capabilities available through the global Deno namespace."
layout: doc.tsx
url: /api/deno/about/
oldUrl:
- /runtime/manual/runtime/
- /runtime/manual/runtime/builtin_apis/
Expand Down
1 change: 1 addition & 0 deletions api/node/index.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@
title: "Node.js Built-in APIs"
description: "Complete reference for Node.js built-in modules and globals supported in Deno. Explore Node.js APIs including fs, http, crypto, process, buffer, and more with compatibility information."
layout: doc.tsx
url: /api/node/about/
oldUrl:
- /runtime/manual/node/compatibility/
- /runtime/manual/npm_nodejs/compatibility_mode/
Expand Down
1 change: 1 addition & 0 deletions api/web/index.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@
title: "Web Platform APIs"
description: "A guide to the Web Platform APIs available in Deno. Learn about fetch, events, workers, storage, and other web standard APIs, including implementation details and deviations from browser specifications."
layout: doc.tsx
url: /api/web/about/
oldUrl:
- /runtime/manual/runtime/navigator_api/
- /runtime/manual/runtime/web_platform_apis/
Expand Down
19 changes: 17 additions & 2 deletions middleware/redirects.ts
Original file line number Diff line number Diff line change
Expand Up @@ -140,6 +140,23 @@ function loadFromJson() {
);
}

// Redirects from old per-symbol API reference URLs to their anchor on the
// grouped reference pages, generated by reference/reference.page.ts. The
// file does not exist yet (it is produced by a later step of the reference
// rearchitecture), in which case this is a no-op.
if (existsSync("./_site/api/_redirects.json")) {
const apiRedirects = JSON.parse(
new TextDecoder().decode(
Deno.readFileSync("./_site/api/_redirects.json"),
),
) as Record<string, string>;
redirects = { ...apiRedirects, ...redirects };
} else {
log.warn(
`🔗 <cyan>redirectsMiddleware</cyan>: No './_site/api/_redirects.json' found.`,
);
}

log.info(
`🔗 <cyan>redirectsMiddleware</cyan>: Total number of redirects loaded: ${
Object.keys(redirects).length
Expand All @@ -154,8 +171,6 @@ function addGoLinksAndRedirectLinks(redirects: Record<string, string>) {
`🔗 addGoLinksAndRedirectLinks: Adding additional redirects...`,
);

redirects["/api/"] = "/api/deno/";

log.debug(
`🔗 <cyan>redirectsMiddleware</cyan>: Reading redirects from 'go.json'...`,
);
Expand Down
24 changes: 24 additions & 0 deletions orama/generate_orama_index_full.ts
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@

import { walk } from "@std/fs";
import { fromFileUrl, join, relative } from "@std/path";
import { buildReference } from "../reference/_lib/group.ts";
import { MarkdownIndexer } from "./indexing/MarkdownIndexer.ts";
import { FileSelector } from "./identification/FileSelector.ts";
import { IndexCollection } from "./indexing/IndexCollection.ts";
Expand Down Expand Up @@ -316,6 +317,8 @@ function processApiSymbol(
async function processApiReference(): Promise<OramaFullDocument[]> {
console.log("\n🔧 Processing API reference documentation...");
const apiDocs: OramaFullDocument[] = [];
// deno-lint-ignore no-explicit-any
const referenceJsons: Record<string, any> = {};

for (const refFile of REFERENCE_FILES) {
const fullPath = join(ROOT_DIR, refFile.path);
Expand All @@ -326,6 +329,7 @@ async function processApiReference(): Promise<OramaFullDocument[]> {

const content = await Deno.readTextFile(fullPath);
const data = JSON.parse(content);
referenceJsons[refFile.apiType] = data;

let processedCount = 0;
let skippedCount = 0;
Expand Down Expand Up @@ -362,6 +366,26 @@ async function processApiReference(): Promise<OramaFullDocument[]> {
}
}

// Symbols now live as anchors on grouped reference pages; remap the old
// per-symbol URLs so search results land directly on the right anchor.
if (referenceJsons.deno && referenceJsons.web && referenceJsons.node) {
try {
const { redirects } = buildReference(referenceJsons);
let remapped = 0;
for (const doc of apiDocs) {
const target = redirects[doc.path];
if (target) {
doc.path = target;
doc.url = `${BASE_URL}${target}`;
remapped++;
}
}
console.log(` Remapped ${remapped} API doc URLs to grouped pages.`);
} catch (error) {
console.warn(`Could not remap API URLs to grouped pages: ${error}`);
}
}

return apiDocs;
}

Expand Down
Loading
Loading