Skip to content

Commit 8c5823f

Browse files
authored
feat(lint): add ./lint export and use it for oxlint config generation (#710)
docs(cli): rewrite package.json exports management section in BUNDLING.md Replaces the inaccurate three-layer pipeline description with a correct two-category breakdown (manual vs automated). The previous version incorrectly claimed sync-remote-deps.ts managed CLI package.json exports and referenced ./rolldown/* entries that don't exist in this package. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com> feat(lint): add `./lint` export and use it for oxlint config generation - Add `./lint` subpath export to CLI package.json - Create `src/lint.ts` to re-export `defineConfig` from the lint module - Update Rust config generator to import from `vite-plus/lint` instead of `oxlint` Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com> <!-- CURSOR_SUMMARY --> --- > [!NOTE] > **Medium Risk** > Changes package export surface and the CLI’s generated lint config import path, which could break lint config resolution if the new subpath export or build output is misconfigured. Snap-test harness changes also alter module resolution behavior in tests. > > **Overview** > Adds a new public subpath export `vite-plus/lint` that re-exports `oxlint`’s `defineConfig` (and related types), and updates the Rust CLI config generator to emit temp lint configs that import from `vite-plus/lint` instead of `oxlint`. > > Updates snap-test infrastructure to create a real `node_modules` in the temp workspace and symlink the `vite-plus` package itself so `vite-plus/*` imports resolve during tests, and refreshes global CLI snapshots accordingly. > > Rewrites `packages/cli/BUNDLING.md` to clarify `package.json` exports as *manual vs automated* (with `./test/*` handled by the sync step) and documents the new `./lint` export. > > <sup>Written by [Cursor Bugbot](https://cursor.com/dashboard?tab=bugbot) for commit f9329cf. This will update automatically on new commits. Configure [here](https://cursor.com/dashboard?tab=bugbot).</sup> <!-- /CURSOR_SUMMARY -->
1 parent bdef013 commit 8c5823f

File tree

7 files changed

+88
-27
lines changed

7 files changed

+88
-27
lines changed

packages/cli/BUNDLING.md

Lines changed: 37 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -504,14 +504,44 @@ const CORE_PACKAGE_NAME = '@voidzero-dev/vite-plus-core';
504504
const TEST_PACKAGE_NAME = '@voidzero-dev/vite-plus-test';
505505
```
506506

507-
### Package.json Auto-Update
507+
### Package.json Exports Management
508508

509-
The build script automatically updates `package.json`:
509+
The `exports` field in `package.json` has two categories: **manual** and **automated**.
510510

511-
1. Removes old `./test/*` exports
512-
2. Adds new exports from test package
513-
3. Ensures `dist/test` is in the `files` array
511+
#### Manual exports
514512

515-
Core package exports (`./client`, `./module-runner`, `./internal`, `./dist/client/*`, `./types/*`) are defined statically in `package.json` and not auto-generated, since they match upstream Vite's exports structure.
513+
All non-`./test*` exports are manually maintained in `package.json`. These fall into two groups:
516514

517-
This keeps the CLI package exports in sync with both upstream Vite and the test package without manual maintenance.
515+
**CLI-native exports** — point to CLI's own compiled TypeScript (built by `buildCli()` via tsc):
516+
517+
| Export | Description |
518+
| ---------------- | -------------------------- |
519+
| `.` | Main entry (CLI utilities) |
520+
| `./bin` | CLI binary entry point |
521+
| `./binding` | NAPI native binding |
522+
| `./lint` | Lint utilities |
523+
| `./pack` | Pack utilities |
524+
| `./package.json` | Package metadata |
525+
526+
**Core shim exports** — point to shim files auto-generated by `syncCorePackageExports()` that re-export from `@voidzero-dev/vite-plus-core`. The shim files are regenerated on each build, but the `package.json` entries themselves are manual:
527+
528+
| Export | Description |
529+
| -------------------- | ----------------------------------------------------------------------- |
530+
| `./client` | Triple-slash reference for ambient type declarations (CSS modules, etc) |
531+
| `./module-runner` | Vite module runner for SSR/environments |
532+
| `./internal` | Internal Vite APIs |
533+
| `./dist/client/*` | Client runtime files |
534+
| `./types/internal/*` | Blocked (`null`) to prevent access to internal types |
535+
| `./types/*` | Type-only re-exports |
536+
537+
**Note**: The core package's own exports (which the shims point to) are generated upstream by `packages/tools/src/sync-remote-deps.ts`. See [Core Package Bundling](../core/BUNDLING.md) for details.
538+
539+
#### Automated exports (`./test/*`)
540+
541+
All `./test*` exports are fully managed by `syncTestPackageExports()`. The build script:
542+
543+
1. Reads `packages/test/package.json` exports
544+
2. Creates shim files in `dist/test/`
545+
3. Removes old `./test*` exports from `package.json`
546+
4. Merges in newly generated test exports
547+
5. Ensures `dist/test` is in the `files` array

packages/cli/binding/src/cli.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -263,7 +263,7 @@ impl SubcommandResolver {
263263

264264
let config_path = config_dir.join(temp_filename);
265265
let content = format!(
266-
"import {{ defineConfig }} from 'oxlint';\nimport viteConfig from './{config_basename}';\nexport default defineConfig(viteConfig.{field_name} as any);\n"
266+
"import {{ defineConfig }} from 'vite-plus/lint';\nimport viteConfig from './{config_basename}';\nexport default defineConfig(viteConfig.{field_name} as any);\n"
267267
);
268268
write(&config_path, content).await?;
269269

packages/cli/package.json

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -55,6 +55,10 @@
5555
"import": "./binding/index.cjs",
5656
"require": "./binding/index.cjs"
5757
},
58+
"./lint": {
59+
"types": "./dist/lint.d.ts",
60+
"import": "./dist/lint.js"
61+
},
5862
"./package.json": "./package.json",
5963
"./pack": {
6064
"types": "./dist/pack.d.ts",

packages/cli/snap-tests-global/cli-helper-message/snap.txt

Lines changed: 8 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -55,16 +55,16 @@ VITE+ - The Unified Toolchain for the Web
5555
vp v<semver>
5656

5757
Local vite-plus:
58-
vite-plus Not found
58+
vite-plus v<semver>
5959

6060
Tools:
61-
vite Not found
62-
rolldown Not found
63-
vitest Not found
64-
oxfmt Not found
65-
oxlint Not found
66-
oxlint-tsgolint Not found
67-
tsdown Not found
61+
vite v<semver>
62+
rolldown v<semver>
63+
vitest v<semver>
64+
oxfmt v<semver>
65+
oxlint v<semver>
66+
oxlint-tsgolint v<semver>
67+
tsdown v<semver>
6868

6969
> vp install -h # show install help message
7070
VITE+ - The Unified Toolchain for the Web

packages/cli/snap-tests-global/command-version-no-side-effects/snap.txt

Lines changed: 8 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -4,16 +4,16 @@ VITE+ - The Unified Toolchain for the Web
44
vp v<semver>
55

66
Local vite-plus:
7-
vite-plus Not found
7+
vite-plus v<semver>
88

99
Tools:
10-
vite Not found
11-
rolldown Not found
12-
vitest Not found
13-
oxfmt Not found
14-
oxlint Not found
15-
oxlint-tsgolint Not found
16-
tsdown Not found
10+
vite v<semver>
11+
rolldown v<semver>
12+
vitest v<semver>
13+
oxfmt v<semver>
14+
oxlint v<semver>
15+
oxlint-tsgolint v<semver>
16+
tsdown v<semver>
1717

1818
> test -f .node-version && echo 'FAIL: .node-version was created' || echo 'OK: no .node-version created'
1919
OK: no .node-version created

packages/cli/src/lint.ts

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
export {
2+
type AllowWarnDeny,
3+
type DummyRule,
4+
type DummyRuleMap,
5+
type ExternalPluginEntry,
6+
type ExternalPluginsConfig,
7+
type OxlintConfig,
8+
type OxlintEnv,
9+
type OxlintGlobals,
10+
type OxlintOverride,
11+
type RuleCategories,
12+
defineConfig,
13+
} from 'oxlint';

packages/tools/src/snap-test.ts

Lines changed: 17 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -113,10 +113,24 @@ export async function snapTest() {
113113
}
114114
}
115115

116-
// Make dependencies available in the test cases
116+
// Make dependencies available in the test cases.
117+
// Create a real node_modules directory so we can add the CLI package itself
118+
// alongside the symlinked dependencies (needed for `vite-plus/*` imports in
119+
// generated config files like .vite-plus-lint.tmp.mts).
120+
const tempNodeModules = path.join(tempTmpDir, 'node_modules');
121+
fs.mkdirSync(tempNodeModules);
122+
const cliNodeModules = path.resolve('node_modules');
123+
for (const entry of fs.readdirSync(cliNodeModules)) {
124+
fs.symlinkSync(
125+
path.join(cliNodeModules, entry),
126+
path.join(tempNodeModules, entry),
127+
process.platform === 'win32' ? 'junction' : 'dir',
128+
);
129+
}
130+
// Add the CLI package itself so `vite-plus/*` subpath imports resolve
117131
fs.symlinkSync(
118-
path.resolve('node_modules'),
119-
path.join(tempTmpDir, 'node_modules'),
132+
path.resolve('.'),
133+
path.join(tempNodeModules, 'vite-plus'),
120134
process.platform === 'win32' ? 'junction' : 'dir',
121135
);
122136

0 commit comments

Comments
 (0)