Skip to content

Commit

Permalink
feat: basic implementation of dts generation
Browse files Browse the repository at this point in the history
  • Loading branch information
Timeless0911 committed Aug 1, 2024
1 parent f8965f1 commit 688c31d
Show file tree
Hide file tree
Showing 39 changed files with 1,111 additions and 49 deletions.
4 changes: 2 additions & 2 deletions e2e/cases/alias/index.test.ts
Original file line number Diff line number Diff line change
@@ -1,9 +1,9 @@
import { expect, test } from 'vitest';
import { buildAndGetJsResults } from '#shared';
import { buildAndGetResults } from '#shared';

test('source.alias', async () => {
const fixturePath = __dirname;
const { entries } = await buildAndGetJsResults(fixturePath);
const { entries } = await buildAndGetResults(fixturePath);

expect(entries.esm).toContain('hello world');
expect(entries.cjs).toContain('hello world');
Expand Down
6 changes: 3 additions & 3 deletions e2e/cases/autoExtension/index.test.ts
Original file line number Diff line number Diff line change
@@ -1,17 +1,17 @@
import { extname, join } from 'node:path';
import { expect, test } from 'vitest';
import { buildAndGetJsResults } from '#shared';
import { buildAndGetResults } from '#shared';

test('autoExtension generate .mjs in build artifacts with esm format when type is commonjs', async () => {
const fixturePath = join(__dirname, 'type-commonjs');
const { entryFiles } = await buildAndGetJsResults(fixturePath);
const { entryFiles } = await buildAndGetResults(fixturePath);
expect(extname(entryFiles.esm!)).toEqual('.mjs');
expect(extname(entryFiles.cjs!)).toEqual('.js');
});

test('autoExtension generate .cjs in build artifacts with cjs format when type is module', async () => {
const fixturePath = join(__dirname, 'type-module');
const { entryFiles } = await buildAndGetJsResults(fixturePath);
const { entryFiles } = await buildAndGetResults(fixturePath);
expect(extname(entryFiles.esm!)).toEqual('.js');
expect(extname(entryFiles.cjs!)).toEqual('.cjs');
});
4 changes: 2 additions & 2 deletions e2e/cases/bundle-false/index.test.ts
Original file line number Diff line number Diff line change
@@ -1,10 +1,10 @@
import { join } from 'node:path';
import { expect, test } from 'vitest';
import { buildAndGetJsResults } from '#shared';
import { buildAndGetResults } from '#shared';

test('bundle: false', async () => {
const fixturePath = join(__dirname, 'basic');
const { files } = await buildAndGetJsResults(fixturePath);
const { files } = await buildAndGetResults(fixturePath);

// TODO: record file paths with inline snapshot
// need to add path serialization
Expand Down
4 changes: 2 additions & 2 deletions e2e/cases/define/index.test.ts
Original file line number Diff line number Diff line change
@@ -1,9 +1,9 @@
import { expect, test } from 'vitest';
import { buildAndGetJsResults } from '#shared';
import { buildAndGetResults } from '#shared';

test('source.define', async () => {
const fixturePath = __dirname;
const { entries } = await buildAndGetJsResults(fixturePath);
const { entries } = await buildAndGetResults(fixturePath);

expect(entries.esm).not.toContain('console.info(VERSION)');
expect(entries.esm).toContain('1.0.0');
Expand Down
24 changes: 24 additions & 0 deletions e2e/cases/dts/bundle-false/rslib.config.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
import { defineConfig } from '@rslib/core';
import { generateBundleCjsConfig, generateBundleEsmConfig } from '#shared';

export default defineConfig({
lib: [
generateBundleEsmConfig(__dirname, {
bundle: false,
dts: {
bundle: false,
},
}),
generateBundleCjsConfig(__dirname, {
bundle: false,
dts: {
bundle: false,
},
}),
],
source: {
entry: {
main: ['./src/**'],
},
},
});
3 changes: 3 additions & 0 deletions e2e/cases/dts/bundle-false/src/index.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
export * from './utils/numbers';
export * from './utils/strings';
export * from './sum';
5 changes: 5 additions & 0 deletions e2e/cases/dts/bundle-false/src/sum.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
import { num1, num2, num3 } from './utils/numbers';
import { str1, str2, str3 } from './utils/strings';

export const numSum = num1 + num2 + num3;
export const strSum = str1 + str2 + str3;
3 changes: 3 additions & 0 deletions e2e/cases/dts/bundle-false/src/utils/numbers.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
export const num1 = 1;
export const num2 = 2;
export const num3 = 3;
3 changes: 3 additions & 0 deletions e2e/cases/dts/bundle-false/src/utils/strings.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
export const str1 = 'str1';
export const str2 = 'str2';
export const str3 = 'str3';
7 changes: 7 additions & 0 deletions e2e/cases/dts/bundle-false/tsconfig.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
{
"extends": "@rslib/tsconfig/base",
"compilerOptions": {
"baseUrl": "./"
},
"include": ["src"]
}
6 changes: 6 additions & 0 deletions e2e/cases/dts/bundle/package.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
{
"name": "dts-bundle-test",
"version": "1.0.0",
"private": true,
"type": "module"
}
25 changes: 25 additions & 0 deletions e2e/cases/dts/bundle/rslib.config.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
import { defineConfig } from '@rslib/core';
import {
generateBundleCjsConfig,
generateBundleEsmConfig,
} from '../../../scripts/shared';

export default defineConfig({
lib: [
generateBundleEsmConfig(__dirname, {
dts: {
bundle: true,
},
}),
generateBundleCjsConfig(__dirname, {
dts: {
bundle: true,
},
}),
],
source: {
entry: {
main: './src/index.ts',
},
},
});
3 changes: 3 additions & 0 deletions e2e/cases/dts/bundle/src/index.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
export * from './utils/numbers';
export * from './utils/strings';
export * from './sum';
5 changes: 5 additions & 0 deletions e2e/cases/dts/bundle/src/sum.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
import { num1, num2, num3 } from './utils/numbers';
import { str1, str2, str3 } from './utils/strings';

export const numSum = num1 + num2 + num3;
export const strSum = str1 + str2 + str3;
3 changes: 3 additions & 0 deletions e2e/cases/dts/bundle/src/utils/numbers.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
export const num1 = 1;
export const num2 = 2;
export const num3 = 3;
3 changes: 3 additions & 0 deletions e2e/cases/dts/bundle/src/utils/strings.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
export const str1 = 'str1';
export const str2 = 'str2';
export const str3 = 'str3';
7 changes: 7 additions & 0 deletions e2e/cases/dts/bundle/tsconfig.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
{
"extends": "@rslib/tsconfig/base",
"compilerOptions": {
"baseUrl": "./"
},
"include": ["src"]
}
18 changes: 18 additions & 0 deletions e2e/cases/dts/index.test.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
import { join } from 'node:path';
import { expect, test } from 'vitest';
import { buildAndGetResults } from '#shared';

test('dts when bundle: false', async () => {
const fixturePath = join(__dirname, 'bundle-false');
const { files } = await buildAndGetResults(fixturePath, 'dts');

expect(files.esm?.length).toBe(4);
expect(files.esm?.[0]!.endsWith('.d.ts')).toEqual(true);
});

test('dts when bundle: true', async () => {
const fixturePath = join(__dirname, 'bundle');
const { entryFiles } = await buildAndGetResults(fixturePath, 'dts');

expect(entryFiles.esm!.endsWith('index.d.ts')).toEqual(true);
});
4 changes: 2 additions & 2 deletions e2e/cases/externals/browser/index.test.ts
Original file line number Diff line number Diff line change
@@ -1,9 +1,9 @@
import { join } from 'node:path';
import { expect, test } from 'vitest';
import { buildAndGetJsResults } from '#shared';
import { buildAndGetResults } from '#shared';

test('should fail to build when `output.target` is not "node"', async () => {
const fixturePath = join(__dirname);
const build = buildAndGetJsResults(fixturePath);
const build = buildAndGetResults(fixturePath);
await expect(build).rejects.toThrowError('Rspack build failed!');
});
4 changes: 2 additions & 2 deletions e2e/cases/externals/node/index.test.ts
Original file line number Diff line number Diff line change
@@ -1,10 +1,10 @@
import { join } from 'node:path';
import { expect, test } from 'vitest';
import { buildAndGetJsResults } from '#shared';
import { buildAndGetResults } from '#shared';

test('auto externalize Node.js built-in modules when `output.target` is "node"', async () => {
const fixturePath = join(__dirname);
const { entries } = await buildAndGetJsResults(fixturePath);
const { entries } = await buildAndGetResults(fixturePath);

for (const external of [
'import * as __WEBPACK_EXTERNAL_MODULE_fs__ from "fs"',
Expand Down
4 changes: 2 additions & 2 deletions e2e/cases/syntax/config/index.test.ts
Original file line number Diff line number Diff line change
@@ -1,9 +1,9 @@
import { expect, test } from 'vitest';
import { buildAndGetJsResults } from '#shared';
import { buildAndGetResults } from '#shared';

test('should downgrade class private method by default', async () => {
const fixturePath = __dirname;
const { entries } = await buildAndGetJsResults(fixturePath);
const { entries } = await buildAndGetResults(fixturePath);

expect(entries.esm).toMatchSnapshot();
expect(entries.esm).not.toContain('#bar');
Expand Down
4 changes: 2 additions & 2 deletions e2e/cases/syntax/default/index.test.ts
Original file line number Diff line number Diff line change
@@ -1,9 +1,9 @@
import { expect, test } from 'vitest';
import { buildAndGetJsResults } from '#shared';
import { buildAndGetResults } from '#shared';

test('should downgrade class private method by default', async () => {
const fixturePath = __dirname;
const { entries } = await buildAndGetJsResults(fixturePath);
const { entries } = await buildAndGetResults(fixturePath);

expect(entries.esm).toMatchSnapshot();
expect(entries.esm).toContain('#bar');
Expand Down
2 changes: 1 addition & 1 deletion e2e/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@
},
"devDependencies": {
"@playwright/test": "1.43.1",
"@rsbuild/core": "1.0.1-beta.6",
"@rsbuild/core": "1.0.1-beta.8",
"@rslib/core": "workspace:*",
"@rslib/tsconfig": "workspace:*",
"@types/fs-extra": "^11.0.4",
Expand Down
35 changes: 24 additions & 11 deletions e2e/scripts/shared.ts
Original file line number Diff line number Diff line change
Expand Up @@ -37,31 +37,41 @@ export function generateBundleCjsConfig(
return mergeConfig(cjsBasicConfig, config)!;
}

export async function getJsResults(rslibConfig: RslibConfig) {
export async function getResults(rslibConfig: RslibConfig, type: 'js' | 'dts') {
const files: Record<string, string[]> = {};
const contents: Record<string, Record<string, string>> = {};
const entries: Record<string, string> = {};
const entryFiles: Record<string, string> = {};

for (const libConfig of rslibConfig.lib) {
const content = await globContentJSON(libConfig?.output?.distPath?.root!, {
let globFolder = '';
if (type === 'js') {
globFolder = libConfig?.output?.distPath?.root!;
} else if (type === 'dts' && libConfig.dts !== false) {
globFolder =
libConfig.dts?.distPath! ?? libConfig?.output?.distPath?.root!;
}

if (!globFolder) continue;

const regex = type === 'dts' ? /\.d.(ts|cts|mts)$/ : /\.(js|cjs|mjs)$/;

const content = await globContentJSON(globFolder, {
absolute: true,
ignore: ['/**/*.map'],
});

const jsFiles = Object.keys(content).filter((file) =>
/\.(js|cjs|mjs)$/.test(file),
);
const fileSet = Object.keys(content).filter((file) => regex.test(file));

if (jsFiles.length) {
files[libConfig.format!] = jsFiles;
if (fileSet.length) {
files[libConfig.format!] = fileSet;
contents[libConfig.format!] = content;
}

// Only applied in bundle mode, a shortcut to get single entry result
if (libConfig.bundle !== false && jsFiles.length === 1) {
if (libConfig.bundle !== false && fileSet.length === 1) {
entries[libConfig.format!] = Object.values(content)[0]!;
entryFiles[libConfig.format!] = jsFiles[0]!;
entryFiles[libConfig.format!] = fileSet[0]!;
}
}

Expand All @@ -73,11 +83,14 @@ export async function getJsResults(rslibConfig: RslibConfig) {
};
}

export const buildAndGetJsResults = async (fixturePath: string) => {
export const buildAndGetResults = async (
fixturePath: string,
type: 'js' | 'dts' = 'js',
) => {
const rslibConfig = await loadConfig(join(fixturePath, 'rslib.config.ts'));
process.chdir(fixturePath);
await build(rslibConfig);
const results = await getJsResults(rslibConfig);
const results = await getResults(rslibConfig, type);
return {
contents: results.contents,
files: results.files,
Expand Down
7 changes: 6 additions & 1 deletion packages/core/modern.config.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,12 @@
import { defineConfig, moduleTools } from '@modern-js/module-tools';
import prebundleConfig from './prebundle.config.mjs';

const externals = ['@rsbuild/core', /[\\/]compiled[\\/]/, /node:/];
const externals = [
'@rsbuild/core',
/[\\/]compiled[\\/]/,
/node:/,
'typescript',
];
const define = {
RSLIB_VERSION: require('./package.json').version,
};
Expand Down
21 changes: 18 additions & 3 deletions packages/core/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -26,26 +26,41 @@
"bin": {
"rslib": "./bin/rslib.js"
},
"files": ["bin", "dist", "dist-types", "compiled"],
"files": [
"bin",
"dist",
"dist-types",
"compiled"
],
"scripts": {
"build": "modern build",
"dev": "modern build --watch",
"prebundle": "prebundle"
},
"dependencies": {
"@rsbuild/core": "1.0.1-beta.6"
"@rsbuild/core": "1.0.1-beta.8",
"rsbuild-plugin-dts": "workspace:*"
},
"devDependencies": {
"@rslib/tsconfig": "workspace:*",
"@types/fs-extra": "^11.0.4",
"fast-glob": "^3.3.2",
"commander": "^12.1.0",
"fast-glob": "^3.3.2",
"fs-extra": "^11.2.0",
"picocolors": "1.0.1",
"prebundle": "1.1.0",
"rslog": "^1.2.2",
"typescript": "^5.5.3"
},
"peerDependencies": {
"@microsoft/api-extractor": "^7",
"typescript": "^5"
},
"peerDependenciesMeta": {
"@microsoft/api-extractor": {
"optional": true
}
},
"engines": {
"node": ">=16.0.0"
},
Expand Down
Loading

0 comments on commit 688c31d

Please sign in to comment.