1- import * as fs from ' node:fs' ;
2- import * as path from ' node:path' ;
3- import { fileURLToPath } from ' node:url' ;
1+ import * as fs from " node:fs" ;
2+ import * as path from " node:path" ;
3+ import { fileURLToPath } from " node:url" ;
44
55interface Package {
66 name : string ;
@@ -9,23 +9,23 @@ interface Package {
99 hasVitePlusConfig : boolean ;
1010}
1111
12- const __dirname = path . join ( fileURLToPath ( import . meta. url ) , '..' ) ;
12+ const __dirname = path . join ( fileURLToPath ( import . meta. url ) , ".." ) ;
1313
1414class MonorepoGenerator {
1515 private packages : Map < string , Package > = new Map ( ) ;
1616 private readonly PACKAGE_COUNT = 1000 ;
1717 private readonly MAX_DEPS_PER_PACKAGE = 8 ;
1818 private readonly MIN_DEPS_PER_PACKAGE = 2 ;
1919 private readonly SCRIPT_NAMES = [
20- ' build' ,
21- ' test' ,
22- ' lint' ,
23- ' dev' ,
24- ' start' ,
25- ' prepare' ,
26- ' compile' ,
20+ " build" ,
21+ " test" ,
22+ " lint" ,
23+ " dev" ,
24+ " start" ,
25+ " prepare" ,
26+ " compile" ,
2727 ] ;
28- private readonly CATEGORIES = [ ' core' , ' util' , ' feature' , ' service' , ' app' ] ;
28+ private readonly CATEGORIES = [ " core" , " util" , " feature" , " service" , " app" ] ;
2929
3030 constructor ( private rootDir : string ) { }
3131
@@ -39,7 +39,7 @@ class MonorepoGenerator {
3939
4040 private generatePackageName ( index : number ) : string {
4141 const category = this . getRandomElement ( this . CATEGORIES ) ;
42- const paddedIndex = index . toString ( ) . padStart ( 2 , '0' ) ;
42+ const paddedIndex = index . toString ( ) . padStart ( 2 , "0" ) ;
4343 return `${ category } -${ paddedIndex } ` ;
4444 }
4545
@@ -66,7 +66,7 @@ class MonorepoGenerator {
6666 selectedCommands . push ( this . getRandomElement ( commands ) ) ;
6767 }
6868
69- return selectedCommands . join ( ' && ' ) ;
69+ return selectedCommands . join ( " && " ) ;
7070 }
7171
7272 private generateScripts ( packageName : string ) : Record < string , string > {
@@ -100,7 +100,7 @@ class MonorepoGenerator {
100100 // Create a complex graph by selecting dependencies from different layers
101101 // Prefer packages with lower indices (creates deeper dependency chains)
102102 const eligiblePackages = availablePackages . filter ( ( pkg ) => {
103- const pkgIndex = parseInt ( pkg . split ( '-' ) [ 1 ] ) ;
103+ const pkgIndex = parseInt ( pkg . split ( "-" ) [ 1 ] ) ;
104104 return pkgIndex < currentIndex ;
105105 } ) ;
106106
@@ -119,8 +119,8 @@ class MonorepoGenerator {
119119 // Add some cross-category dependencies for complexity
120120 if ( Math . random ( ) > 0.3 ) {
121121 const crossCategoryDeps = availablePackages . filter ( ( pkg ) => {
122- const category = pkg . split ( '-' ) [ 0 ] ;
123- return category !== currentIndex . toString ( ) . split ( '-' ) [ 0 ] ;
122+ const category = pkg . split ( "-" ) [ 0 ] ;
123+ return category !== currentIndex . toString ( ) . split ( "-" ) [ 0 ] ;
124124 } ) ;
125125
126126 if ( crossCategoryDeps . length > 0 ) {
@@ -147,7 +147,8 @@ class MonorepoGenerator {
147147 const hasVitePlusConfig = Math . random ( ) > 0.3 ;
148148
149149 // Select dependencies from packages created before this one
150- const dependencies = i === 0 ? [ ] : this . selectDependencies ( i , allPackageNames . slice ( 0 , i ) ) ;
150+ const dependencies =
151+ i === 0 ? [ ] : this . selectDependencies ( i , allPackageNames . slice ( 0 , i ) ) ;
151152
152153 this . packages . set ( packageName , {
153154 name : packageName ,
@@ -181,79 +182,88 @@ class MonorepoGenerator {
181182
182183 // Create the scenario: A has build, B doesn't, C has build
183184 const scriptName = this . getRandomElement ( this . SCRIPT_NAMES ) ;
184- pkgA . scripts [ scriptName ] = this . generateScriptCommand ( scriptName , nameA ) ;
185+ pkgA . scripts [ scriptName ] = this . generateScriptCommand (
186+ scriptName ,
187+ nameA ,
188+ ) ;
185189 delete pkgB . scripts [ scriptName ] ; // B doesn't have the script
186- pkgC . scripts [ scriptName ] = this . generateScriptCommand ( scriptName , nameC ) ;
190+ pkgC . scripts [ scriptName ] = this . generateScriptCommand (
191+ scriptName ,
192+ nameC ,
193+ ) ;
187194 }
188195 }
189196 }
190197
191198 private writePackage ( pkg : Package ) : void {
192- const packageDir = path . join ( this . rootDir , ' packages' , pkg . name ) ;
199+ const packageDir = path . join ( this . rootDir , " packages" , pkg . name ) ;
193200
194201 // Create directory structure
195202 fs . mkdirSync ( packageDir , { recursive : true } ) ;
196- fs . mkdirSync ( path . join ( packageDir , ' src' ) , { recursive : true } ) ;
203+ fs . mkdirSync ( path . join ( packageDir , " src" ) , { recursive : true } ) ;
197204
198205 // Write package.json
199206 const packageJson = {
200207 name : `@monorepo/${ pkg . name } ` ,
201- version : ' 1.0.0' ,
202- main : ' src/index.js' ,
208+ version : " 1.0.0" ,
209+ main : " src/index.js" ,
203210 scripts : pkg . scripts ,
204- dependencies : pkg . dependencies . reduce ( ( deps , dep ) => {
205- deps [ `@monorepo/${ dep } ` ] = 'workspace:*' ;
206- return deps ;
207- } , { } as Record < string , string > ) ,
211+ dependencies : pkg . dependencies . reduce (
212+ ( deps , dep ) => {
213+ deps [ `@monorepo/${ dep } ` ] = "workspace:*" ;
214+ return deps ;
215+ } ,
216+ { } as Record < string , string > ,
217+ ) ,
208218 } ;
209219
210220 fs . writeFileSync (
211- path . join ( packageDir , ' package.json' ) ,
221+ path . join ( packageDir , " package.json" ) ,
212222 JSON . stringify ( packageJson , null , 2 ) ,
213223 ) ;
214224
215225 // Write source file
216226 const indexContent = `// ${ pkg . name } module
217- export function ${ pkg . name . replace ( '-' , '_' ) } () {
227+ export function ${ pkg . name . replace ( "-" , "_" ) } () {
218228 console.log('Executing ${ pkg . name } ');
219- ${ pkg . dependencies . map ( ( dep ) => ` require('@monorepo/${ dep } ');` ) . join ( '\n' ) }
229+ ${ pkg . dependencies . map ( ( dep ) => ` require('@monorepo/${ dep } ');` ) . join ( "\n" ) }
220230}
221231
222- module.exports = { ${ pkg . name . replace ( '-' , '_' ) } };
232+ module.exports = { ${ pkg . name . replace ( "-" , "_" ) } };
223233` ;
224234
225- fs . writeFileSync ( path . join ( packageDir , ' src' , ' index.js' ) , indexContent ) ;
235+ fs . writeFileSync ( path . join ( packageDir , " src" , " index.js" ) , indexContent ) ;
226236
227237 // Write vite-plus.json if needed
228238 if ( pkg . hasVitePlusConfig ) {
229239 const vitePlusConfig = {
230- extends : ' ../../vite-plus.json' ,
240+ extends : " ../../vite-plus.json" ,
231241 tasks : {
232242 build : {
233243 cache : true ,
234244 env : {
235- NODE_ENV : ' production' ,
245+ NODE_ENV : " production" ,
236246 } ,
237247 } ,
238248 } ,
239249 } ;
240250
241251 fs . writeFileSync (
242- path . join ( packageDir , ' vite-plus.json' ) ,
252+ path . join ( packageDir , " vite-plus.json" ) ,
243253 JSON . stringify ( vitePlusConfig , null , 2 ) ,
244254 ) ;
245255 }
246256 }
247257
248258 public generate ( ) : void {
249- console . log ( ' Generating monorepo structure...' ) ;
259+ console . log ( " Generating monorepo structure..." ) ;
250260
251261 // Clean and create root directory
252262 if ( fs . existsSync ( this . rootDir ) ) {
253263 fs . rmSync ( this . rootDir , { recursive : true , force : true } ) ;
254264 }
255265 fs . mkdirSync ( this . rootDir , { recursive : true } ) ;
256- fs . mkdirSync ( path . join ( this . rootDir , ' packages' ) , { recursive : true } ) ;
266+ fs . mkdirSync ( path . join ( this . rootDir , " packages" ) , { recursive : true } ) ;
257267
258268 // Generate packages
259269 this . generatePackages ( ) ;
@@ -270,22 +280,22 @@ module.exports = { ${pkg.name.replace('-', '_')} };
270280
271281 // Write root package.json
272282 const rootPackageJson = {
273- name : ' monorepo-benchmark' ,
274- version : ' 1.0.0' ,
283+ name : " monorepo-benchmark" ,
284+ version : " 1.0.0" ,
275285 private : true ,
276- workspaces : [ ' packages/*' ] ,
286+ workspaces : [ " packages/*" ] ,
277287 scripts : {
278- ' build:all' : ' vite run build' ,
279- ' test:all' : ' vite run test' ,
280- ' lint:all' : ' vite run lint' ,
288+ " build:all" : " vite run build" ,
289+ " test:all" : " vite run test" ,
290+ " lint:all" : " vite run lint" ,
281291 } ,
282292 devDependencies : {
283- ' @voidzero-dev/vite-plus' : '*' ,
293+ " @voidzero-dev/vite-plus" : "*" ,
284294 } ,
285295 } ;
286296
287297 fs . writeFileSync (
288- path . join ( this . rootDir , ' package.json' ) ,
298+ path . join ( this . rootDir , " package.json" ) ,
289299 JSON . stringify ( rootPackageJson , null , 2 ) ,
290300 ) ;
291301
@@ -294,7 +304,7 @@ module.exports = { ${pkg.name.replace('-', '_')} };
294304 - 'packages/*'
295305` ;
296306 fs . writeFileSync (
297- path . join ( this . rootDir , ' pnpm-workspace.yaml' ) ,
307+ path . join ( this . rootDir , " pnpm-workspace.yaml" ) ,
298308 pnpmWorkspace ,
299309 ) ;
300310
@@ -317,7 +327,7 @@ module.exports = { ${pkg.name.replace('-', '_')} };
317327 } ;
318328
319329 fs . writeFileSync (
320- path . join ( this . rootDir , ' vite-plus.json' ) ,
330+ path . join ( this . rootDir , " vite-plus.json" ) ,
321331 JSON . stringify ( rootVitePlusConfig , null , 2 ) ,
322332 ) ;
323333
@@ -349,25 +359,23 @@ module.exports = { ${pkg.name.replace('-', '_')} };
349359 }
350360 }
351361
352- console . log ( ' \nStatistics:' ) ;
362+ console . log ( " \nStatistics:" ) ;
353363 console . log ( `- Total packages: ${ this . packages . size } ` ) ;
354364 console . log (
355- `- Average dependencies per package: ${
356- (
357- totalDeps / this . packages . size
358- ) . toFixed ( 2 )
359- } `,
365+ `- Average dependencies per package: ${ (
366+ totalDeps / this . packages . size
367+ ) . toFixed ( 2 ) } `,
360368 ) ;
361369 console . log ( `- Max dependencies in a package: ${ maxDeps } ` ) ;
362370 console . log ( `- Packages with vite-plus.json: ${ packagesWithVitePlus } ` ) ;
363- console . log ( ' - Script distribution:' ) ;
371+ console . log ( " - Script distribution:" ) ;
364372 for ( const [ script , count ] of scriptCounts ) {
365373 console . log ( ` - ${ script } : ${ count } packages` ) ;
366374 }
367375 }
368376}
369377
370378// Main execution
371- const outputDir = path . join ( __dirname , ' fixtures' , ' monorepo' ) ;
379+ const outputDir = path . join ( __dirname , " fixtures" , " monorepo" ) ;
372380const generator = new MonorepoGenerator ( outputDir ) ;
373381generator . generate ( ) ;
0 commit comments