@@ -29,7 +29,7 @@ export interface AddCommandOptions {
2929
3030export interface PackageManager {
3131 get name ( ) : string
32- get representativeLockfile ( ) : string | undefined
32+ get representativeLockfiles ( ) : string [ ]
3333 get representativeConfigFile ( ) : string | undefined
3434 installCommand ( ) : Runnable
3535 addCommand ( options : AddCommandOptions ) : Runnable
@@ -44,9 +44,20 @@ export abstract class PackageManagerDetector {
4444 abstract get name ( ) : string
4545 abstract detectUserAgent ( userAgent : string ) : boolean
4646 abstract detectRuntime ( ) : boolean
47- abstract get representativeLockfile ( ) : string | undefined
47+ abstract get representativeLockfiles ( ) : string [ ]
4848 abstract get representativeConfigFile ( ) : string | undefined
49- abstract detectLockfile ( dir : string ) : Promise < string >
49+
50+ async detectLockfile ( dir : string ) : Promise < string > {
51+ for ( const lockfile of this . representativeLockfiles ) {
52+ try {
53+ return await accessR ( path . join ( dir , lockfile ) )
54+ } catch {
55+ continue
56+ }
57+ }
58+ throw new NotDetectedError ( )
59+ }
60+
5061 abstract detectConfigFile ( dir : string ) : Promise < string >
5162 abstract detectExecutable ( lookup : PathLookup ) : Promise < void >
5263 abstract installCommand ( ) : Runnable
@@ -71,18 +82,14 @@ export class NpmDetector extends PackageManagerDetector implements PackageManage
7182 return false
7283 }
7384
74- get representativeLockfile ( ) : string {
75- return 'package-lock.json'
85+ get representativeLockfiles ( ) : string [ ] {
86+ return [ 'package-lock.json' ]
7687 }
7788
7889 get representativeConfigFile ( ) : undefined {
7990 return
8091 }
8192
82- async detectLockfile ( dir : string ) : Promise < string > {
83- return await accessR ( path . join ( dir , this . representativeLockfile ) )
84- }
85-
8693 // eslint-disable-next-line require-await, @typescript-eslint/no-unused-vars
8794 async detectConfigFile ( dir : string ) : Promise < string > {
8895 throw new NotDetectedError ( )
@@ -126,19 +133,14 @@ export class CNpmDetector extends PackageManagerDetector implements PackageManag
126133 return false
127134 }
128135
129- get representativeLockfile ( ) : undefined {
130- return
136+ get representativeLockfiles ( ) : string [ ] {
137+ return [ ]
131138 }
132139
133140 get representativeConfigFile ( ) : undefined {
134141 return
135142 }
136143
137- // eslint-disable-next-line require-await
138- async detectLockfile ( ) : Promise < string > {
139- throw new NotDetectedError ( )
140- }
141-
142144 // eslint-disable-next-line require-await, @typescript-eslint/no-unused-vars
143145 async detectConfigFile ( dir : string ) : Promise < string > {
144146 throw new NotDetectedError ( )
@@ -182,18 +184,14 @@ export class PNpmDetector extends PackageManagerDetector implements PackageManag
182184 return false
183185 }
184186
185- get representativeLockfile ( ) : string {
186- return 'pnpm-lock.yaml'
187+ get representativeLockfiles ( ) : string [ ] {
188+ return [ 'pnpm-lock.yaml' ]
187189 }
188190
189191 get representativeConfigFile ( ) : string {
190192 return 'pnpm-workspace.yaml'
191193 }
192194
193- async detectLockfile ( dir : string ) : Promise < string > {
194- return await accessR ( path . join ( dir , this . representativeLockfile ) )
195- }
196-
197195 async detectConfigFile ( dir : string ) : Promise < string > {
198196 return await accessR ( path . join ( dir , this . representativeConfigFile ) )
199197 }
@@ -307,18 +305,14 @@ export class YarnDetector extends PackageManagerDetector implements PackageManag
307305 return false
308306 }
309307
310- get representativeLockfile ( ) : string {
311- return 'yarn.lock'
308+ get representativeLockfiles ( ) : string [ ] {
309+ return [ 'yarn.lock' ]
312310 }
313311
314312 get representativeConfigFile ( ) : undefined {
315313 return
316314 }
317315
318- async detectLockfile ( dir : string ) : Promise < string > {
319- return await accessR ( path . join ( dir , this . representativeLockfile ) )
320- }
321-
322316 // eslint-disable-next-line require-await, @typescript-eslint/no-unused-vars
323317 async detectConfigFile ( dir : string ) : Promise < string > {
324318 throw new NotDetectedError ( )
@@ -362,18 +356,14 @@ export class DenoDetector extends PackageManagerDetector implements PackageManag
362356 return process . versions . deno !== undefined
363357 }
364358
365- get representativeLockfile ( ) : string {
366- return 'deno.lock'
359+ get representativeLockfiles ( ) : string [ ] {
360+ return [ 'deno.lock' ]
367361 }
368362
369363 get representativeConfigFile ( ) : string {
370364 return 'deno.json'
371365 }
372366
373- async detectLockfile ( dir : string ) : Promise < string > {
374- return await accessR ( path . join ( dir , this . representativeLockfile ) )
375- }
376-
377367 async detectConfigFile ( dir : string ) : Promise < string > {
378368 return await accessR ( path . join ( dir , this . representativeConfigFile ) )
379369 }
@@ -460,18 +450,14 @@ export class BunDetector extends PackageManagerDetector implements PackageManage
460450 return process . versions . bun !== undefined
461451 }
462452
463- get representativeLockfile ( ) : string {
464- return 'bun.lockb'
453+ get representativeLockfiles ( ) : string [ ] {
454+ return [ 'bun.lock' , 'bun. lockb']
465455 }
466456
467457 get representativeConfigFile ( ) : undefined {
468458 return
469459 }
470460
471- async detectLockfile ( dir : string ) : Promise < string > {
472- return await accessR ( path . join ( dir , this . representativeLockfile ) )
473- }
474-
475461 // eslint-disable-next-line require-await, @typescript-eslint/no-unused-vars
476462 async detectConfigFile ( dir : string ) : Promise < string > {
477463 throw new NotDetectedError ( )
@@ -731,9 +717,7 @@ export async function detectNearestLockfile (
731717 }
732718 }
733719
734- const lockfiles = detectors . reduce < string [ ] > ( ( acc , detector ) => {
735- return acc . concat ( detector . representativeLockfile ?? [ ] )
736- } , [ ] )
720+ const lockfiles = detectors . flatMap ( detector => detector . representativeLockfiles )
737721
738722 throw new NoLockfileFoundError ( searchPaths , lockfiles )
739723}
0 commit comments