mirror of
https://github.com/pnpm/pnpm.git
synced 2026-01-11 00:18:32 -05:00
fix: don't recursively switch to the same pnpm version (#8468)
This commit is contained in:
5
.changeset/curvy-mice-learn.md
Normal file
5
.changeset/curvy-mice-learn.md
Normal file
@@ -0,0 +1,5 @@
|
||||
---
|
||||
"@pnpm/env.path": minor
|
||||
---
|
||||
|
||||
Add a new field to the return object: `updated`. When `false`, the prepended paths were already present in the path.
|
||||
5
.changeset/lazy-fans-hunt.md
Normal file
5
.changeset/lazy-fans-hunt.md
Normal file
@@ -0,0 +1,5 @@
|
||||
---
|
||||
"pnpm": patch
|
||||
---
|
||||
|
||||
Throw an exception if pnpm switches to the same version of itself.
|
||||
19
env/path/src/index.ts
vendored
19
env/path/src/index.ts
vendored
@@ -1,12 +1,27 @@
|
||||
import path from 'path'
|
||||
import PATH from 'path-name'
|
||||
|
||||
export function prependDirsToPath (prependDirs: string[], env = process.env): { name: string, value: string } {
|
||||
export interface PrependDirsToPathResult {
|
||||
name: string
|
||||
value: string
|
||||
updated: boolean
|
||||
}
|
||||
|
||||
export function prependDirsToPath (prependDirs: string[], env = process.env): PrependDirsToPathResult {
|
||||
const prepend = prependDirs.join(path.delimiter)
|
||||
if (env[PATH] != null && (env[PATH] === prepend || env[PATH]!.startsWith(`${prepend}${path.delimiter}`))) {
|
||||
return {
|
||||
name: PATH,
|
||||
value: env[PATH]!,
|
||||
updated: false,
|
||||
}
|
||||
}
|
||||
return {
|
||||
name: PATH,
|
||||
value: [
|
||||
...prependDirs,
|
||||
prepend,
|
||||
...(env[PATH] != null ? [env[PATH]] : []),
|
||||
].join(path.delimiter),
|
||||
updated: true,
|
||||
}
|
||||
}
|
||||
|
||||
12
env/path/test/index.ts
vendored
12
env/path/test/index.ts
vendored
@@ -6,9 +6,21 @@ test('prependDirsToPath', () => {
|
||||
expect(prependDirsToPath(['foo'], {})).toStrictEqual({
|
||||
name: PATH,
|
||||
value: 'foo',
|
||||
updated: true,
|
||||
})
|
||||
expect(prependDirsToPath(['foo'], { [PATH]: 'bar' })).toStrictEqual({
|
||||
name: PATH,
|
||||
value: `foo${path.delimiter}bar`,
|
||||
updated: true,
|
||||
})
|
||||
expect(prependDirsToPath(['foo', 'qar'], { [PATH]: `foo${path.delimiter}qar${path.delimiter}bar` })).toStrictEqual({
|
||||
name: PATH,
|
||||
value: `foo${path.delimiter}qar${path.delimiter}bar`,
|
||||
updated: false,
|
||||
})
|
||||
expect(prependDirsToPath(['foo', 'qar'], { [PATH]: `foo${path.delimiter}qar` })).toStrictEqual({
|
||||
name: PATH,
|
||||
value: `foo${path.delimiter}qar`,
|
||||
updated: false,
|
||||
})
|
||||
})
|
||||
|
||||
@@ -1,6 +1,7 @@
|
||||
import fs from 'fs'
|
||||
import path from 'path'
|
||||
import { type Config } from '@pnpm/config'
|
||||
import { PnpmError } from '@pnpm/error'
|
||||
import { globalWarn } from '@pnpm/logger'
|
||||
import { getCurrentPackageName, packageManager } from '@pnpm/cli-meta'
|
||||
import { prependDirsToPath } from '@pnpm/env.path'
|
||||
@@ -37,7 +38,12 @@ export async function switchCliVersion (config: Config): Promise<void> {
|
||||
[`${pkgName}@${pm.version}`]
|
||||
)
|
||||
}
|
||||
const pnpmEnv = prependDirsToPath([path.join(dir, 'bin')])
|
||||
const wantedPnpmBinDir = path.join(dir, 'bin')
|
||||
const pnpmEnv = prependDirsToPath([wantedPnpmBinDir])
|
||||
if (!pnpmEnv.updated) {
|
||||
// We throw this error to prevent an infinite recursive call of the same pnpm version.
|
||||
throw new PnpmError('VERSION_SWITCH_FAIL', `Failed to switch pnpm to v${pm.version}. Looks like pnpm CLI is missing at "${wantedPnpmBinDir}" or is incorrect`)
|
||||
}
|
||||
const { status } = spawn.sync('pnpm', process.argv.slice(2), {
|
||||
stdio: 'inherit',
|
||||
env: {
|
||||
|
||||
Reference in New Issue
Block a user