vite-plugin-rebundle 1.1.0 → 1.1.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.d.ts +2 -2
- package/dist/index.js +1 -1
- package/dist/rebundle.d.ts +13 -9
- package/dist/rebundle.js +93 -71
- package/package.json +10 -9
package/dist/index.d.ts
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import { type
|
|
2
|
-
export default function rebundle(options?:
|
|
1
|
+
import { type OptionsInput } from './rebundle.js';
|
|
2
|
+
export default function rebundle(options?: OptionsInput): import("vite").Plugin<any>;
|
package/dist/index.js
CHANGED
package/dist/rebundle.d.ts
CHANGED
|
@@ -1,20 +1,24 @@
|
|
|
1
|
+
import * as $utils from '@eposlabs/utils';
|
|
1
2
|
import type { BuildOptions } from 'esbuild';
|
|
2
3
|
import type { Plugin } from 'vite';
|
|
3
4
|
export type Options = {
|
|
4
5
|
[chunkName: string]: BuildOptions;
|
|
5
6
|
};
|
|
6
|
-
export type
|
|
7
|
-
|
|
8
|
-
};
|
|
9
|
-
export declare class Rebundle {
|
|
7
|
+
export type OptionsInput = Options | (() => Options | Promise<Options>);
|
|
8
|
+
export declare class Rebundle extends $utils.Unit {
|
|
10
9
|
private options;
|
|
11
10
|
private config;
|
|
12
|
-
private
|
|
13
|
-
|
|
14
|
-
|
|
11
|
+
private chunkFiles;
|
|
12
|
+
private rebundledContent;
|
|
13
|
+
constructor(options: OptionsInput);
|
|
14
|
+
get vite(): Plugin;
|
|
15
15
|
private onConfigResolved;
|
|
16
16
|
private onWriteBundle;
|
|
17
17
|
private get outDir();
|
|
18
|
-
private
|
|
19
|
-
private
|
|
18
|
+
private outPath;
|
|
19
|
+
private outRead;
|
|
20
|
+
private outWrite;
|
|
21
|
+
private getOptions;
|
|
22
|
+
private readChunkFiles;
|
|
23
|
+
private removeDirectoryIfEmpty;
|
|
20
24
|
}
|
package/dist/rebundle.js
CHANGED
|
@@ -1,15 +1,18 @@
|
|
|
1
|
-
import $chalk from 'chalk';
|
|
2
1
|
import * as $esbuild from 'esbuild';
|
|
3
2
|
import * as $fs from 'node:fs/promises';
|
|
4
3
|
import * as $path from 'node:path';
|
|
5
|
-
|
|
4
|
+
import * as $utils from '@eposlabs/utils';
|
|
5
|
+
import $chalk from 'chalk';
|
|
6
|
+
export class Rebundle extends $utils.Unit {
|
|
6
7
|
options;
|
|
7
8
|
config = null;
|
|
8
|
-
|
|
9
|
+
chunkFiles = {};
|
|
10
|
+
rebundledContent = {};
|
|
9
11
|
constructor(options) {
|
|
12
|
+
super();
|
|
10
13
|
this.options = options;
|
|
11
14
|
}
|
|
12
|
-
get
|
|
15
|
+
get vite() {
|
|
13
16
|
return {
|
|
14
17
|
name: 'vite-plugin-rebundle',
|
|
15
18
|
apply: 'build',
|
|
@@ -34,83 +37,86 @@ export class Rebundle {
|
|
|
34
37
|
};
|
|
35
38
|
};
|
|
36
39
|
onWriteBundle = async (output, bundle) => {
|
|
40
|
+
const options = await this.getOptions();
|
|
37
41
|
// Get entry js chunks
|
|
38
42
|
const entryJsChunks = Object.values(bundle)
|
|
39
43
|
.filter(chunkOrAsset => chunkOrAsset.type === 'chunk')
|
|
40
44
|
.filter(chunk => chunk.isEntry && $path.extname(chunk.fileName) === '.js');
|
|
41
|
-
// Get non-entry chunks (.js, .js.map)
|
|
42
|
-
const nonEntryChunks = Object.values(bundle)
|
|
43
|
-
.filter(chunkOrAsset => chunkOrAsset.type === 'chunk')
|
|
44
|
-
.filter(chunk => !chunk.isEntry);
|
|
45
45
|
// Rebundle entry js chunks with esbuild
|
|
46
46
|
await Promise.all(entryJsChunks.map(async (chunk) => {
|
|
47
47
|
if (!this.config)
|
|
48
48
|
throw this.never;
|
|
49
|
-
|
|
50
|
-
const
|
|
51
|
-
const
|
|
52
|
-
const
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
console.log(`${dir}${name} ${tag}`);
|
|
82
|
-
});
|
|
49
|
+
const chunkPath = this.outPath(chunk.fileName);
|
|
50
|
+
const chunkBuildOptions = options[chunk.name] ?? {};
|
|
51
|
+
const chunkFiles = await this.readChunkFiles(chunk);
|
|
52
|
+
const chunkFilePaths = Object.keys(chunkFiles);
|
|
53
|
+
const chunkChanged = chunkFilePaths.some(path => chunkFiles[path] !== this.chunkFiles[path]);
|
|
54
|
+
// Update files cache
|
|
55
|
+
Object.assign(this.chunkFiles, chunkFiles);
|
|
56
|
+
// Modified? -> Rebundle
|
|
57
|
+
if (chunkChanged) {
|
|
58
|
+
// Build with esbuild
|
|
59
|
+
await $esbuild.build({
|
|
60
|
+
sourcemap: Boolean(this.config.build.sourcemap),
|
|
61
|
+
...chunkBuildOptions,
|
|
62
|
+
outfile: chunkPath,
|
|
63
|
+
entryPoints: [chunkPath],
|
|
64
|
+
bundle: true,
|
|
65
|
+
minify: false,
|
|
66
|
+
allowOverwrite: true,
|
|
67
|
+
plugins: [
|
|
68
|
+
...(chunkBuildOptions.plugins ?? []),
|
|
69
|
+
{
|
|
70
|
+
name: 'logger',
|
|
71
|
+
setup: build => {
|
|
72
|
+
build.onEnd(result => {
|
|
73
|
+
if (result.errors.length > 0)
|
|
74
|
+
return;
|
|
75
|
+
const outDir = $chalk.dim(`${this.outDir}/`);
|
|
76
|
+
const fileName = $chalk.cyan(chunk.fileName);
|
|
77
|
+
const rebundleTag = $chalk.dim.cyan('rebundle');
|
|
78
|
+
console.log(`${outDir}${fileName} ${rebundleTag}`);
|
|
79
|
+
});
|
|
80
|
+
},
|
|
83
81
|
},
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
82
|
+
],
|
|
83
|
+
});
|
|
84
|
+
// Save chunk content
|
|
85
|
+
this.rebundledContent[chunk.fileName] = await this.outRead(chunk.fileName);
|
|
86
|
+
// Save sourcemap content
|
|
87
|
+
if (chunk.sourcemapFileName) {
|
|
88
|
+
this.rebundledContent[chunk.sourcemapFileName] = await this.outRead(chunk.sourcemapFileName);
|
|
89
|
+
}
|
|
90
|
+
}
|
|
91
|
+
// Overwrite chunk
|
|
92
|
+
await this.outWrite(chunk.fileName, this.rebundledContent[chunk.fileName]);
|
|
93
|
+
chunk.code = this.rebundledContent[chunk.fileName];
|
|
94
|
+
// Overwrite sourcemap
|
|
89
95
|
if (chunk.sourcemapFileName) {
|
|
90
|
-
const
|
|
91
|
-
if (
|
|
96
|
+
const sourcemapAsset = bundle[chunk.sourcemapFileName];
|
|
97
|
+
if (sourcemapAsset.type !== 'asset')
|
|
92
98
|
throw this.never;
|
|
93
|
-
|
|
94
|
-
|
|
99
|
+
await this.outWrite(chunk.sourcemapFileName, this.rebundledContent[chunk.sourcemapFileName]);
|
|
100
|
+
sourcemapAsset.source = this.rebundledContent[chunk.sourcemapFileName];
|
|
95
101
|
}
|
|
96
102
|
}));
|
|
103
|
+
// Get non-entry chunks (.js, .js.map)
|
|
104
|
+
const nonEntryChunks = Object.values(bundle)
|
|
105
|
+
.filter(chunkOrAsset => chunkOrAsset.type === 'chunk')
|
|
106
|
+
.filter(chunk => !chunk.isEntry);
|
|
97
107
|
// Remove all non-entry chunks
|
|
98
108
|
for (const chunk of nonEntryChunks) {
|
|
99
|
-
// Remove
|
|
100
|
-
|
|
101
|
-
await $fs.unlink(path);
|
|
109
|
+
// Remove chunk
|
|
110
|
+
await $fs.unlink(this.outPath(chunk.fileName));
|
|
102
111
|
delete bundle[chunk.fileName];
|
|
103
|
-
// Remove sourcemap
|
|
112
|
+
// Remove sourcemap
|
|
104
113
|
if (chunk.sourcemapFileName) {
|
|
105
|
-
|
|
106
|
-
await $fs.unlink(sourcemapPath);
|
|
114
|
+
await $fs.unlink(this.outPath(chunk.sourcemapFileName));
|
|
107
115
|
delete bundle[chunk.sourcemapFileName];
|
|
108
116
|
}
|
|
109
|
-
// Remove containing directory if empty
|
|
110
|
-
const dir = $path.dirname(
|
|
111
|
-
|
|
112
|
-
if (files.length === 0)
|
|
113
|
-
await $fs.rmdir(dir);
|
|
117
|
+
// Remove containing directory if empty (recursively)
|
|
118
|
+
const dir = $path.dirname(this.outPath(chunk.fileName));
|
|
119
|
+
await this.removeDirectoryIfEmpty(dir);
|
|
114
120
|
}
|
|
115
121
|
};
|
|
116
122
|
// ---------------------------------------------------------------------------
|
|
@@ -121,16 +127,32 @@ export class Rebundle {
|
|
|
121
127
|
throw this.never;
|
|
122
128
|
return this.config.build.outDir;
|
|
123
129
|
}
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
+
outPath(path) {
|
|
131
|
+
return $path.join(this.outDir, path);
|
|
132
|
+
}
|
|
133
|
+
async outRead(path) {
|
|
134
|
+
return await $fs.readFile(this.outPath(path), 'utf-8');
|
|
135
|
+
}
|
|
136
|
+
async outWrite(path, content) {
|
|
137
|
+
await $fs.writeFile(this.outPath(path), content, 'utf-8');
|
|
138
|
+
}
|
|
139
|
+
async getOptions() {
|
|
140
|
+
if (typeof this.options !== 'function')
|
|
141
|
+
return this.options;
|
|
142
|
+
return await this.options();
|
|
143
|
+
}
|
|
144
|
+
async readChunkFiles(chunk) {
|
|
145
|
+
const files = {};
|
|
146
|
+
await Promise.all([chunk.fileName, ...chunk.imports].map(async (path) => {
|
|
147
|
+
files[path] = await this.outRead(path);
|
|
130
148
|
}));
|
|
131
|
-
return
|
|
149
|
+
return files;
|
|
132
150
|
}
|
|
133
|
-
|
|
134
|
-
|
|
151
|
+
async removeDirectoryIfEmpty(dir) {
|
|
152
|
+
const files = await $fs.readdir(dir);
|
|
153
|
+
if (files.length > 0)
|
|
154
|
+
return;
|
|
155
|
+
await $fs.rmdir(dir);
|
|
156
|
+
await this.removeDirectoryIfEmpty($path.dirname(dir));
|
|
135
157
|
}
|
|
136
158
|
}
|
package/package.json
CHANGED
|
@@ -1,17 +1,21 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "vite-plugin-rebundle",
|
|
3
|
-
"version": "1.1.
|
|
3
|
+
"version": "1.1.1",
|
|
4
4
|
"type": "module",
|
|
5
5
|
"license": "MIT",
|
|
6
6
|
"author": "imkost",
|
|
7
7
|
"description": "Vite plugin that forces single-file output per entry. Ensures each entry point is bundled into a standalone file without code-splitting.",
|
|
8
|
+
"keywords": [
|
|
9
|
+
"vite",
|
|
10
|
+
"vite-plugin"
|
|
11
|
+
],
|
|
8
12
|
"scripts": {
|
|
9
13
|
"dev": "rm -rf dist && tsc --watch",
|
|
10
14
|
"build": "rm -rf dist && tsc",
|
|
11
15
|
"lint": "eslint src",
|
|
12
|
-
"release": "npm
|
|
13
|
-
"release:
|
|
14
|
-
"release:minor": "npm version minor && npm run release"
|
|
16
|
+
"release": "npm version patch && npm run release:raw",
|
|
17
|
+
"release:raw": "npm run build && npm publish",
|
|
18
|
+
"release:minor": "npm version minor && npm run release:raw"
|
|
15
19
|
},
|
|
16
20
|
"exports": {
|
|
17
21
|
"import": "./dist/index.js"
|
|
@@ -19,11 +23,8 @@
|
|
|
19
23
|
"files": [
|
|
20
24
|
"dist"
|
|
21
25
|
],
|
|
22
|
-
"keywords": [
|
|
23
|
-
"vite",
|
|
24
|
-
"vite-plugin"
|
|
25
|
-
],
|
|
26
26
|
"dependencies": {
|
|
27
|
-
"chalk": "^5.6.0"
|
|
27
|
+
"chalk": "^5.6.0",
|
|
28
|
+
"esbuild": "^0.25.9"
|
|
28
29
|
}
|
|
29
30
|
}
|