Skip to content

Commit

Permalink
add filter prop to APIReference component
Browse files Browse the repository at this point in the history
  • Loading branch information
souporserious committed Oct 3, 2024
1 parent d6cdba2 commit c9abdc5
Show file tree
Hide file tree
Showing 5 changed files with 68 additions and 17 deletions.
5 changes: 5 additions & 0 deletions .changeset/nice-points-train.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
'renoun': minor
---

Adds `filter` prop to `APIReference` component.
16 changes: 9 additions & 7 deletions packages/renoun/src/collections/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -11,23 +11,24 @@ import { dirname, resolve } from 'node:path'
import globParent from 'glob-parent'
import { minimatch } from 'minimatch'

import { resolveType } from '../project/index.js'
import { createSlug } from '../utils/create-slug.js'
import { extractExportByIdentifier } from '../utils/extract-export-by-identifier.js'
import { filePathToPathname } from '../utils/file-path-to-pathname.js'
import { getJsDocMetadata } from '../utils/get-js-doc-metadata.js'
import { getExportedDeclaration } from '../utils/get-exported-declaration.js'
import { formatNameAsTitle } from '../utils/format-name-as-title.js'
import {
getDeclarationLocation,
type DeclarationPosition,
} from '../utils/get-declaration-location.js'
import { getDirectorySourceFile } from '../utils/get-directory-source-file.js'
import { getEditPath } from '../utils/get-edit-path.js'
import { getExportedDeclaration } from '../utils/get-exported-declaration.js'
import { getGitMetadata } from '../utils/get-git-metadata.js'
import { getJsDocMetadata } from '../utils/get-js-doc-metadata.js'
import { resolveType } from '../project/index.js'
import { resolveTsConfigPath } from '../utils/resolve-ts-config-path.js'
import type { SymbolFilter } from '../utils/resolve-type.js'
import { getSourcePathMap } from '../utils/get-source-files-path-map.js'
import { getSourceFilesOrderMap } from '../utils/get-source-files-sort-order.js'
import { resolveTsConfigPath } from '../utils/resolve-ts-config-path.js'
import { extractExportByIdentifier } from '../utils/extract-export-by-identifier.js'

type GetImport = (slug: string) => Promise<any>

Expand Down Expand Up @@ -84,7 +85,7 @@ export interface ExportSource<Value> extends BaseSource {
getName(): string

/** The resolved type of the exported source based on the TypeScript type if it exists. */
getType(): Promise<ReturnType<typeof resolveType>>
getType(filter?: SymbolFilter): Promise<ReturnType<typeof resolveType>>

/** The name of the exported source formatted as a title. */
getTitle(): string
Expand Down Expand Up @@ -269,7 +270,7 @@ class Export<Value, AllExports extends FileExports = FileExports>
)
}

async getType() {
async getType(filter?: SymbolFilter) {
if (!this.exportDeclaration) {
throw new Error(
`[renoun] Export could not be statically analyzed from source file at "${this.source.getPath()}".`
Expand All @@ -281,6 +282,7 @@ class Export<Value, AllExports extends FileExports = FileExports>
projectOptions: {
tsConfigFilePath: this.source.getCollection().options.tsConfigFilePath,
},
filter,
})
}

Expand Down
27 changes: 20 additions & 7 deletions packages/renoun/src/components/APIReference.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -4,24 +4,31 @@ import { Fragment, Suspense } from 'react'
import type { CSSObject } from 'restyle'

import type { ExportSource } from '../collections/index.js'
import { CodeInline } from './CodeInline.js'
import { MDXContent } from './MDXContent.js'
import { MDXComponents } from './MDXComponents.js'
import { createSlug } from '../utils/create-slug.js'
import type {
AllTypes,
ResolvedType,
SymbolFilter,
TypeOfKind,
} from '../utils/resolve-type.js'
import { isParameterType, isPropertyType } from '../utils/resolve-type.js'
import { CodeInline } from './CodeInline.js'
import { MDXContent } from './MDXContent.js'
import { MDXComponents } from './MDXComponents.js'

const mdxComponents = {
p: (props) => <p {...props} css={{ margin: 0 }} />,
code: (props) => <MDXComponents.code {...props} paddingY="0" />,
} satisfies MDXComponents

async function APIReferenceAsync({ source }: { source: ExportSource<any> }) {
const type = await source.getType()
async function APIReferenceAsync({
source,
filter,
}: {
source: ExportSource<any>
filter?: SymbolFilter
}) {
const type = await source.getType(filter)

if (type === undefined) {
return null
Expand Down Expand Up @@ -424,10 +431,16 @@ function TypeValue({
}

/** Displays type documentation for all types related to a collection export source. */
export function APIReference({ source }: { source: ExportSource<any> }) {
export function APIReference({
source,
filter,
}: {
source: ExportSource<any>
filter?: SymbolFilter
}) {
return (
<Suspense fallback="Loading API references...">
<APIReferenceAsync source={source} />
<APIReferenceAsync source={source} filter={filter} />
</Suspense>
)
}
6 changes: 5 additions & 1 deletion packages/renoun/src/project/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ import {
createHighlighter,
type Highlighter,
} from '../utils/create-highlighter.js'
import type { SymbolFilter } from '../utils/resolve-type.js'
import type { DistributiveOmit } from '../types.js'
import { WebSocketClient } from './rpc/client.js'
import { getProject } from './get-project.js'
Expand Down Expand Up @@ -78,9 +79,11 @@ export async function analyzeSourceText(
export async function resolveType({
declaration,
projectOptions,
filter,
}: {
declaration: Node
projectOptions?: ProjectOptions
filter?: SymbolFilter
}) {
if (client) {
const filePath = declaration.getSourceFile().getFilePath()
Expand All @@ -89,11 +92,12 @@ export async function resolveType({
return client.callMethod('resolveType', {
filePath,
position,
filter: filter?.toString(),
tsConfigFilePath: projectOptions?.tsConfigFilePath,
})
}

return import('../utils/resolve-type.js').then(({ resolveType }) => {
return resolveType(declaration.getType(), declaration)
return resolveType(declaration.getType(), declaration, filter)
})
}
31 changes: 29 additions & 2 deletions packages/renoun/src/project/server.ts
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,10 @@ import {
type Highlighter,
} from '../utils/create-highlighter.js'
import { getRootDirectory } from '../utils/get-root-directory.js'
import { resolveType as baseResolveType } from '../utils/resolve-type.js'
import {
resolveType as baseResolveType,
type SymbolFilter,
} from '../utils/resolve-type.js'
import { WebSocketServer } from './rpc/server.js'
import { getProject } from './get-project.js'
import { ProjectOptions } from './types.js'
Expand Down Expand Up @@ -83,10 +86,12 @@ export function createServer() {
'resolveType',
async function resolveType({
projectOptions,
filter,
...options
}: {
filePath: string
position: number
filter?: string
projectOptions?: ProjectOptions
}) {
const project = await getProject(projectOptions)
Expand All @@ -100,7 +105,29 @@ export function createServer() {
}

const exportDeclaration = declaration.getParentOrThrow()
return baseResolveType(exportDeclaration.getType(), exportDeclaration)
const filterFn = filter
? (new Function(
'symbolMetadata',
`try {
return (${filter})(symbolMetadata)
} catch (error) {
if (error instanceof ReferenceError) {
throw new Error(
'[renoun]: A ReferenceError occured in the collection filter, this may have been caused by a variable defined outside the function scope. Ensure that all variables are defined within the filter function since it is serialized.',
{ cause: error }
)
} else {
throw error
}
}`
) as SymbolFilter)
: undefined

return baseResolveType(
exportDeclaration.getType(),
exportDeclaration,
filterFn
)
}
)

Expand Down

0 comments on commit c9abdc5

Please sign in to comment.