Skip to content

Commit

Permalink
fix: resolving peer deps with prerelease versions (pnpm#7981)
Browse files Browse the repository at this point in the history
close pnpm#7977
  • Loading branch information
zkochan authored Apr 21, 2024
1 parent e9530a8 commit abaf12e
Show file tree
Hide file tree
Showing 4 changed files with 51 additions and 17 deletions.
6 changes: 6 additions & 0 deletions .changeset/four-adults-burn.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
---
"@pnpm/resolve-dependencies": patch
"pnpm": patch
---

Resolve peer dependencies correctly, when they have prerelease versions [#7977](https://github.com/pnpm/pnpm/issues/7977).
29 changes: 29 additions & 0 deletions pkg-manager/resolve-dependencies/src/hoistPeers.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
import { type PreferredVersions } from '@pnpm/resolver-base'
import semver from 'semver'

export function hoistPeers (
missingRequiredPeers: Array<[string, { range: string }]>,
opts: {
autoInstallPeers: boolean
allPreferredVersions?: PreferredVersions
}
): Record<string, string> {
const dependencies: Record<string, string> = {}
for (const [peerName, { range }] of missingRequiredPeers) {
if (opts.allPreferredVersions![peerName]) {
const versions: string[] = []
const nonVersions: string[] = []
for (const [spec, specType] of Object.entries(opts.allPreferredVersions![peerName])) {
if (specType === 'version') {
versions.push(spec)
} else {
nonVersions.push(spec)
}
}
dependencies[peerName] = [semver.maxSatisfying(versions, '*', { includePrerelease: true }), ...nonVersions].join(' || ')
} else if (opts.autoInstallPeers) {
dependencies[peerName] = range
}
}
return dependencies
}
19 changes: 2 additions & 17 deletions pkg-manager/resolve-dependencies/src/resolveDependencies.ts
Original file line number Diff line number Diff line change
Expand Up @@ -57,6 +57,7 @@ import {
nodeIdContains,
splitNodeId,
} from './nodeIdUtils'
import { hoistPeers } from './hoistPeers'
import { wantedDepIsLocallyAvailable } from './wantedDepIsLocallyAvailable'
import { replaceVersionInPref } from './replaceVersionInPref'

Expand Down Expand Up @@ -329,23 +330,7 @@ export async function resolveRootDependencies (
)
)
if (!missingRequiredPeers.length && !missingOptionalPeerNames.length) break
const dependencies: Record<string, string> = {}
for (const [peerName, { range }] of missingRequiredPeers) {
if (ctx.allPreferredVersions![peerName]) {
const versions: string[] = []
const nonVersions: string[] = []
for (const [spec, specType] of Object.entries(ctx.allPreferredVersions![peerName])) {
if (specType === 'version') {
versions.push(spec)
} else {
nonVersions.push(spec)
}
}
dependencies[peerName] = [semver.maxSatisfying(versions, '*'), ...nonVersions].join(' || ')
} else if (ctx.autoInstallPeers) {
dependencies[peerName] = range
}
}
const dependencies = hoistPeers(missingRequiredPeers, ctx)
const nextMissingOptionalPeers: string[] = []
const optionalDependencies: Record<string, string> = {}
for (const missingOptionalPeerName of missingOptionalPeerNames) {
Expand Down
14 changes: 14 additions & 0 deletions pkg-manager/resolve-dependencies/test/hoistPeers.test.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
import { hoistPeers } from '../lib/hoistPeers'

test('hoistPeers picks an already available prerelease version', () => {
expect(hoistPeers([['foo', { range: '*' }]], {
autoInstallPeers: false,
allPreferredVersions: {
foo: {
'1.0.0-beta.0': 'version',
},
},
})).toStrictEqual({
foo: '1.0.0-beta.0',
})
})

0 comments on commit abaf12e

Please sign in to comment.