From 3192c96e82aec00f9b88b4e0f257b426d3e3a48d Mon Sep 17 00:00:00 2001 From: Patrik Oldsberg Date: Sat, 4 Feb 2023 16:50:00 +0100 Subject: [PATCH] repo-tools: update type-deps to analyze all entry points Signed-off-by: Patrik Oldsberg --- .../src/commands/api-reports/api-extractor.ts | 35 +++++------------ .../src/commands/type-deps/type-deps.ts | 15 ++++--- packages/repo-tools/src/lib/entryPoints.ts | 39 +++++++++++++++++++ 3 files changed, 59 insertions(+), 30 deletions(-) create mode 100644 packages/repo-tools/src/lib/entryPoints.ts diff --git a/packages/repo-tools/src/commands/api-reports/api-extractor.ts b/packages/repo-tools/src/commands/api-reports/api-extractor.ts index 0c23d42437..1fe7602617 100644 --- a/packages/repo-tools/src/commands/api-reports/api-extractor.ts +++ b/packages/repo-tools/src/commands/api-reports/api-extractor.ts @@ -19,7 +19,6 @@ import { relative as relativePath, basename, join, - extname, } from 'path'; import { execFile } from 'child_process'; import fs from 'fs-extra'; @@ -63,6 +62,7 @@ import { IMarkdownEmitterContext } from '@microsoft/api-documenter/lib/markdown/ import { AstDeclaration } from '@microsoft/api-extractor/lib/analyzer/AstDeclaration'; import { paths as cliPaths } from '../../lib/paths'; import minimatch from 'minimatch'; +import { getPackageExportNames } from '../../lib/entryPoints'; const tmpDir = cliPaths.resolveTargetRoot( './node_modules/.cache/api-extractor', @@ -313,30 +313,15 @@ async function findPackageEntryPoints(packageDirs: string[]): Promise< cliPaths.resolveTargetRoot(packageDir, 'package.json'), ); - if (pkg.exports && typeof pkg.exports !== 'string') { - return Object.entries(pkg.exports).flatMap(([mount, path]) => { - const ext = extname(String(path)); - if (!['.ts', '.tsx', '.cts', '.mts'].includes(ext)) { - return []; // Ignore non-TS entry points - } - let name = mount; - if (name.startsWith('./')) { - name = name.slice(2); - } - if (!name || name === '.') { - return [{ packageDir, name: 'index' }]; - } - return [{ packageDir, name }]; - }); - } - - return { - packageDir, - name: 'index', - usesExperimentalTypeBuild: pkg.scripts?.build?.includes( - '--experimental-type-build', - ), - }; + return ( + getPackageExportNames(pkg)?.map(name => ({ packageDir, name })) ?? { + packageDir, + name: 'index', + usesExperimentalTypeBuild: pkg.scripts?.build?.includes( + '--experimental-type-build', + ), + } + ); }), ).then(results => results.flat()); } diff --git a/packages/repo-tools/src/commands/type-deps/type-deps.ts b/packages/repo-tools/src/commands/type-deps/type-deps.ts index 0ad9a5cfc8..17164cea39 100644 --- a/packages/repo-tools/src/commands/type-deps/type-deps.ts +++ b/packages/repo-tools/src/commands/type-deps/type-deps.ts @@ -20,6 +20,7 @@ import { resolve as resolvePath } from 'path'; // eslint-disable-next-line @backstage/no-undeclared-imports import chalk from 'chalk'; import { getPackages, Package } from '@manypkg/get-packages'; +import { getPackageExportNames } from '../../lib/entryPoints'; export default async () => { const { packages } = await getPackages(resolvePath('.')); @@ -96,11 +97,15 @@ function findAllDeps(declSrc: string) { * missing or incorrect in package.json */ function checkTypes(pkg: Package) { - const typeDecl = fs.readFileSync( - resolvePath(pkg.dir, 'dist/index.d.ts'), - 'utf8', - ); - const allDeps = findAllDeps(typeDecl); + const entryPointNames = getPackageExportNames(pkg.packageJson) ?? ['index']; + + const allDeps = entryPointNames.flatMap(name => { + const typeDecl = fs.readFileSync( + resolvePath(pkg.dir, `dist/${name}.d.ts`), + 'utf8', + ); + return findAllDeps(typeDecl); + }); const deps = Array.from(new Set(allDeps)); const errors = []; diff --git a/packages/repo-tools/src/lib/entryPoints.ts b/packages/repo-tools/src/lib/entryPoints.ts new file mode 100644 index 0000000000..df5633c103 --- /dev/null +++ b/packages/repo-tools/src/lib/entryPoints.ts @@ -0,0 +1,39 @@ +/* + * Copyright 2023 The Backstage Authors + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +import { extname } from 'path'; +import { JsonObject } from '@backstage/types'; + +export function getPackageExportNames(pkg: JsonObject): string[] | undefined { + if (pkg.exports && typeof pkg.exports !== 'string') { + return Object.entries(pkg.exports).flatMap(([mount, path]) => { + const ext = extname(String(path)); + if (!['.ts', '.tsx', '.cts', '.mts'].includes(ext)) { + return []; // Ignore non-TS entry points + } + let name = mount; + if (name.startsWith('./')) { + name = name.slice(2); + } + if (!name || name === '.') { + return ['index']; + } + return [name]; + }); + } + + return undefined; +}