From d1955f7c9e1f4897399c2f060456a92b9b384a3f Mon Sep 17 00:00:00 2001 From: iCrawl Date: Sun, 9 Apr 2023 18:40:49 +0200 Subject: [PATCH] feat(website): static, optional, private, inherits, extends --- .../api/[package]/[version]/[item]/route.ts | 35 -------- .../[package]/[version]/[item]/route.ts | 80 +++++++++++++++++++ apps/website/src/util/summary.ts | 60 -------------- 3 files changed, 80 insertions(+), 95 deletions(-) delete mode 100644 apps/website/src/app/api/[package]/[version]/[item]/route.ts create mode 100644 apps/website/src/app/api/packages/[package]/[version]/[item]/route.ts delete mode 100644 apps/website/src/util/summary.ts diff --git a/apps/website/src/app/api/[package]/[version]/[item]/route.ts b/apps/website/src/app/api/[package]/[version]/[item]/route.ts deleted file mode 100644 index da2343fe5..000000000 --- a/apps/website/src/app/api/[package]/[version]/[item]/route.ts +++ /dev/null @@ -1,35 +0,0 @@ -import { generatePath } from '@discordjs/api-extractor-utils'; -import { tryResolveSummaryText } from '@discordjs/scripts'; -import type { ApiDeclaredItem, ApiItemContainerMixin } from '@microsoft/api-extractor-model'; -import type { NextRequest } from 'next/server'; -import { NextResponse } from 'next/server'; -import { memberPredicate } from '~/components/documentation/util'; -import { fetchMember } from '~/util/fetchMember'; -import { resolveMembers } from '~/util/members'; - -export const revalidate = 3_600; - -export async function GET(_: NextRequest, { params }: { params: { item: string; package: string; version: string } }) { - const member = await fetchMember({ - package: params.package, - version: params.version, - item: params.item, - }); - - if (!member) { - return new Response(null, { status: 404 }); - } - - return NextResponse.json({ - name: member.displayName, - kind: member.kind, - summary: tryResolveSummaryText(member as ApiDeclaredItem) ?? '', - path: generatePath(member.getHierarchy(), params.version), - members: resolveMembers(member as ApiItemContainerMixin, memberPredicate).map((member) => ({ - name: member.item.displayName, - kind: member.item.kind, - summary: tryResolveSummaryText(member.item as ApiDeclaredItem) ?? '', - path: generatePath(member.item.getHierarchy(), params.version), - })), - }); -} diff --git a/apps/website/src/app/api/packages/[package]/[version]/[item]/route.ts b/apps/website/src/app/api/packages/[package]/[version]/[item]/route.ts new file mode 100644 index 000000000..a940be277 --- /dev/null +++ b/apps/website/src/app/api/packages/[package]/[version]/[item]/route.ts @@ -0,0 +1,80 @@ +import { generatePath } from '@discordjs/api-extractor-utils'; +import { tryResolveSummaryText } from '@discordjs/scripts'; +import type { ApiClass, ApiDeclaredItem, ApiItemContainerMixin } from '@microsoft/api-extractor-model'; +import { ExcerptTokenKind } from '@microsoft/api-extractor-model'; +import type { NextRequest } from 'next/server'; +import { NextResponse } from 'next/server'; +import { memberPredicate } from '~/components/documentation/util'; +import { fetchMember } from '~/util/fetchMember'; +import { resolveMembers } from '~/util/members'; + +export const revalidate = 3_600; + +export async function GET(_: NextRequest, { params }: { params: { item: string; package: string; version: string } }) { + const member = await fetchMember({ + package: params.package, + version: params.version, + item: params.item, + }); + + if (!member) { + return new Response(null, { status: 404 }); + } + + const model = member.getAssociatedModel(); + const excerpt = (member as ApiClass).extendsType?.excerpt; + + return NextResponse.json({ + name: member.displayName, + kind: member.kind, + extendsFrom: + excerpt?.spannedTokens + .map((token) => { + if (token.kind === ExcerptTokenKind.Reference) { + const referenceItem = member + .getAssociatedModel() + ?.resolveDeclarationReference(token.canonicalReference!, model).resolvedApiItem; + + if (referenceItem) { + return { + name: referenceItem.displayName, + kind: referenceItem.kind, + summary: tryResolveSummaryText(referenceItem as unknown as ApiDeclaredItem) ?? '', + path: generatePath(referenceItem.getHierarchy(), params.version), + }; + } + } + + return null; + }) + .filter(Boolean) ?? null, + summary: tryResolveSummaryText(member as ApiDeclaredItem) ?? '', + path: generatePath(member.getHierarchy(), params.version), + members: resolveMembers(member as ApiItemContainerMixin, memberPredicate).map((member) => { + const isDeprecated = Boolean(member.item.tsdocComment?.deprecatedBlock); + + return { + inheritedFrom: member.inherited + ? { + name: member.inherited.displayName, + kind: member.inherited.kind, + summary: tryResolveSummaryText(member.inherited as unknown as ApiDeclaredItem) ?? '', + path: generatePath(member.inherited.getHierarchy(), params.version), + } + : null, + name: member.item.displayName, + kind: member.item.kind, + deprecated: isDeprecated, + // @ts-expect-error: Typings + readonly: member.item.isReadonly ?? false, + optional: member.item.isOptional, + // @ts-expect-error: Typings + static: member.item.isStatic ?? false, + // @ts-expect-error: Typings + protected: member.item.isProtected ?? false, + summary: tryResolveSummaryText(member.item as ApiDeclaredItem) ?? '', + path: generatePath(member.item.getHierarchy(), params.version), + }; + }), + }); +} diff --git a/apps/website/src/util/summary.ts b/apps/website/src/util/summary.ts deleted file mode 100644 index 7b2d1cc80..000000000 --- a/apps/website/src/util/summary.ts +++ /dev/null @@ -1,60 +0,0 @@ -import type { - ApiItemJSON, - DocNodeJSON, - DocCodeSpanJSON, - DocPlainTextJSON, - DocNodeContainerJSON, - DocLinkTagJSON, -} from '@discordjs/api-extractor-utils'; - -export function tryResolveDescription(member: ApiItemJSON) { - const { summary } = member!; - - if (!summary) { - return null; - } - - let retVal = ''; - - function recurseNodes(node: DocNodeJSON, emitMarkdownLinks = false) { - switch (node.kind) { - case 'CodeSpan': - retVal += (node as DocCodeSpanJSON).code; - break; - case 'LinkTag': { - const { text, urlDestination } = node as DocLinkTagJSON; - - if (text && urlDestination && emitMarkdownLinks) { - retVal += `[${text}](${urlDestination})`; - } else { - retVal += text ?? urlDestination ?? ''; - } - - break; - } - - case 'PlainText': - retVal += (node as DocPlainTextJSON).text; - break; - case 'Section': - case 'Paragraph': - for (const currentNode of (node as DocNodeContainerJSON).nodes) { - recurseNodes(currentNode); - } - - break; - default: - break; - } - } - - for (const node of summary.nodes) { - recurseNodes(node); - } - - if (retVal === '') { - return null; - } - - return retVal; -}