mirror of
https://github.com/pnpm/pnpm.git
synced 2026-05-24 08:35:19 -04:00
fix(resolve-dependencies): not update git protocol dependency when add unrelated dependency (#7054)
close #7008
This commit is contained in:
9
.changeset/serious-ghosts-taste.md
Normal file
9
.changeset/serious-ghosts-taste.md
Normal file
@@ -0,0 +1,9 @@
|
|||||||
|
---
|
||||||
|
"@pnpm/resolve-dependencies": patch
|
||||||
|
"@pnpm/core": patch
|
||||||
|
"@pnpm/lockfile-utils": patch
|
||||||
|
"@pnpm/pick-fetcher": patch
|
||||||
|
"pnpm": patch
|
||||||
|
---
|
||||||
|
|
||||||
|
Don't update git-hosted dependencies when adding unrelated dependency [#7008](https://github.com/pnpm/pnpm/issues/7008).
|
||||||
6
__fixtures__/with-git-protocol-dep/package.json
Normal file
6
__fixtures__/with-git-protocol-dep/package.json
Normal file
@@ -0,0 +1,6 @@
|
|||||||
|
{
|
||||||
|
"name":"with-git-protocol-dep",
|
||||||
|
"dependencies": {
|
||||||
|
"is-negative": "github:kevva/is-negative#master"
|
||||||
|
}
|
||||||
|
}
|
||||||
26
__fixtures__/with-git-protocol-dep/pnpm-lock.yaml
generated
Normal file
26
__fixtures__/with-git-protocol-dep/pnpm-lock.yaml
generated
Normal file
@@ -0,0 +1,26 @@
|
|||||||
|
lockfileVersion: '6.0'
|
||||||
|
|
||||||
|
settings:
|
||||||
|
autoInstallPeers: true
|
||||||
|
excludeLinksFromLockfile: false
|
||||||
|
|
||||||
|
dependencies:
|
||||||
|
is-negative:
|
||||||
|
specifier: github:kevva/is-negative#master
|
||||||
|
version: github.com/kevva/is-negative/219c424611ff4a2af15f7deeff4f93c62558c43d
|
||||||
|
|
||||||
|
packages:
|
||||||
|
|
||||||
|
/is-positive@3.1.0:
|
||||||
|
resolution: {integrity: sha512-8ND1j3y9/HP94TOvGzr69/FgbkX2ruOldhLEsTWwcJVfo4oRjwemJmJxt7RJkKYH8tz7vYBP9JcKQY8CLuJ90Q==}
|
||||||
|
engines: {node: '>=0.10.0'}
|
||||||
|
dev: false
|
||||||
|
|
||||||
|
github.com/kevva/is-negative/219c424611ff4a2af15f7deeff4f93c62558c43d:
|
||||||
|
resolution: {tarball: https://codeload.github.com/kevva/is-negative/tar.gz/219c424611ff4a2af15f7deeff4f93c62558c43d}
|
||||||
|
name: is-negative
|
||||||
|
version: 2.0.0
|
||||||
|
engines: {node: '>=0.10.0'}
|
||||||
|
dependencies:
|
||||||
|
is-positive: 3.1.0
|
||||||
|
dev: false
|
||||||
@@ -23,7 +23,7 @@ export function pickFetcher (fetcherByHostingType: Partial<Fetchers>, resolution
|
|||||||
return fetch
|
return fetch
|
||||||
}
|
}
|
||||||
|
|
||||||
function isGitHostedPkgUrl (url: string) {
|
export function isGitHostedPkgUrl (url: string) {
|
||||||
return (
|
return (
|
||||||
url.startsWith('https://codeload.github.com/') ||
|
url.startsWith('https://codeload.github.com/') ||
|
||||||
url.startsWith('https://bitbucket.org/') ||
|
url.startsWith('https://bitbucket.org/') ||
|
||||||
|
|||||||
@@ -41,6 +41,7 @@
|
|||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@pnpm/dependency-path": "workspace:*",
|
"@pnpm/dependency-path": "workspace:*",
|
||||||
"@pnpm/lockfile-types": "workspace:*",
|
"@pnpm/lockfile-types": "workspace:*",
|
||||||
|
"@pnpm/pick-fetcher": "workspace:*",
|
||||||
"@pnpm/resolver-base": "workspace:*",
|
"@pnpm/resolver-base": "workspace:*",
|
||||||
"@pnpm/types": "workspace:*",
|
"@pnpm/types": "workspace:*",
|
||||||
"get-npm-tarball-url": "^2.0.3",
|
"get-npm-tarball-url": "^2.0.3",
|
||||||
|
|||||||
@@ -4,6 +4,7 @@ import { type Resolution } from '@pnpm/resolver-base'
|
|||||||
import { type Registries } from '@pnpm/types'
|
import { type Registries } from '@pnpm/types'
|
||||||
import * as dp from '@pnpm/dependency-path'
|
import * as dp from '@pnpm/dependency-path'
|
||||||
import getNpmTarballUrl from 'get-npm-tarball-url'
|
import getNpmTarballUrl from 'get-npm-tarball-url'
|
||||||
|
import { isGitHostedPkgUrl } from '@pnpm/pick-fetcher'
|
||||||
import { nameVerFromPkgSnapshot } from './nameVerFromPkgSnapshot'
|
import { nameVerFromPkgSnapshot } from './nameVerFromPkgSnapshot'
|
||||||
|
|
||||||
export function pkgSnapshotToResolution (
|
export function pkgSnapshotToResolution (
|
||||||
@@ -13,7 +14,8 @@ export function pkgSnapshotToResolution (
|
|||||||
): Resolution {
|
): Resolution {
|
||||||
if (
|
if (
|
||||||
Boolean((pkgSnapshot.resolution as TarballResolution).type) ||
|
Boolean((pkgSnapshot.resolution as TarballResolution).type) ||
|
||||||
(pkgSnapshot.resolution as TarballResolution).tarball?.startsWith('file:')
|
(pkgSnapshot.resolution as TarballResolution).tarball?.startsWith('file:') ||
|
||||||
|
isGitHostedPkgUrl((pkgSnapshot.resolution as TarballResolution).tarball ?? '')
|
||||||
) {
|
) {
|
||||||
return pkgSnapshot.resolution as Resolution
|
return pkgSnapshot.resolution as Resolution
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -9,6 +9,9 @@
|
|||||||
"../../__typings__/**/*.d.ts"
|
"../../__typings__/**/*.d.ts"
|
||||||
],
|
],
|
||||||
"references": [
|
"references": [
|
||||||
|
{
|
||||||
|
"path": "../../fetching/pick-fetcher"
|
||||||
|
},
|
||||||
{
|
{
|
||||||
"path": "../../packages/dependency-path"
|
"path": "../../packages/dependency-path"
|
||||||
},
|
},
|
||||||
|
|||||||
@@ -6,12 +6,17 @@ import {
|
|||||||
addDependenciesToPackage,
|
addDependenciesToPackage,
|
||||||
install,
|
install,
|
||||||
} from '@pnpm/core'
|
} from '@pnpm/core'
|
||||||
|
import { fixtures } from '@pnpm/test-fixtures'
|
||||||
|
import { assertProject } from '@pnpm/assert-project'
|
||||||
import rimraf from '@zkochan/rimraf'
|
import rimraf from '@zkochan/rimraf'
|
||||||
import { isCI } from 'ci-info'
|
import { isCI } from 'ci-info'
|
||||||
import exists from 'path-exists'
|
import exists from 'path-exists'
|
||||||
import sinon from 'sinon'
|
import sinon from 'sinon'
|
||||||
import { testDefaults } from '../utils'
|
import { testDefaults } from '../utils'
|
||||||
|
|
||||||
|
const f = fixtures(__dirname)
|
||||||
|
const withGitProtocolDepFixture = f.find('with-git-protocol-dep')
|
||||||
|
|
||||||
test('from a github repo', async () => {
|
test('from a github repo', async () => {
|
||||||
const project = prepareEmpty()
|
const project = prepareEmpty()
|
||||||
|
|
||||||
@@ -278,3 +283,34 @@ test('re-adding a git repo with a different tag', async () => {
|
|||||||
}
|
}
|
||||||
)
|
)
|
||||||
})
|
})
|
||||||
|
|
||||||
|
test('should not update when adding unrelated dependency', async () => {
|
||||||
|
process.chdir(withGitProtocolDepFixture)
|
||||||
|
fs.rmSync('./node_modules', {
|
||||||
|
recursive: true,
|
||||||
|
force: true,
|
||||||
|
})
|
||||||
|
let manifest = JSON.parse(fs.readFileSync('./package.json', 'utf8'))
|
||||||
|
await install(manifest, await testDefaults({ preferFrozenLockfile: false, dir: withGitProtocolDepFixture, lockfileDir: withGitProtocolDepFixture }))
|
||||||
|
|
||||||
|
expect(fs.existsSync('./node_modules/.pnpm/github.com+kevva+is-negative@219c424611ff4a2af15f7deeff4f93c62558c43d')).toBe(true)
|
||||||
|
|
||||||
|
manifest = await addDependenciesToPackage(manifest, ['is-number'], await testDefaults({ preferFrozenLockfile: false }))
|
||||||
|
|
||||||
|
expect(manifest.dependencies).toHaveProperty('is-number')
|
||||||
|
expect(manifest.dependencies['is-negative']).toBe('github:kevva/is-negative#master')
|
||||||
|
|
||||||
|
const project = assertProject(withGitProtocolDepFixture)
|
||||||
|
await project.has('is-number')
|
||||||
|
expect(fs.existsSync('./node_modules/.pnpm/github.com+kevva+is-negative@219c424611ff4a2af15f7deeff4f93c62558c43d')).toBe(true)
|
||||||
|
expect((await project.readLockfile()).dependencies).toEqual({
|
||||||
|
'is-negative': {
|
||||||
|
specifier: 'github:kevva/is-negative#master',
|
||||||
|
version: 'github.com/kevva/is-negative/219c424611ff4a2af15f7deeff4f93c62558c43d',
|
||||||
|
},
|
||||||
|
'is-number': {
|
||||||
|
specifier: '^7.0.0',
|
||||||
|
version: '7.0.0',
|
||||||
|
},
|
||||||
|
})
|
||||||
|
})
|
||||||
|
|||||||
@@ -35,7 +35,7 @@ test("don't override existing spec in package.json on named installation", async
|
|||||||
expect(manifest.dependencies).toStrictEqual({
|
expect(manifest.dependencies).toStrictEqual({
|
||||||
'is-negative': '^1.0.1',
|
'is-negative': '^1.0.1',
|
||||||
'is-positive': '^2.0.0',
|
'is-positive': '^2.0.0',
|
||||||
sec: 'github:sindresorhus/sec#main',
|
sec: 'sindresorhus/sec#main',
|
||||||
})
|
})
|
||||||
})
|
})
|
||||||
|
|
||||||
|
|||||||
@@ -38,6 +38,7 @@
|
|||||||
"@pnpm/manifest-utils": "workspace:*",
|
"@pnpm/manifest-utils": "workspace:*",
|
||||||
"@pnpm/npm-resolver": "workspace:*",
|
"@pnpm/npm-resolver": "workspace:*",
|
||||||
"@pnpm/pick-registry-for-package": "workspace:*",
|
"@pnpm/pick-registry-for-package": "workspace:*",
|
||||||
|
"@pnpm/pick-fetcher": "workspace:*",
|
||||||
"@pnpm/prune-lockfile": "workspace:*",
|
"@pnpm/prune-lockfile": "workspace:*",
|
||||||
"@pnpm/read-package-json": "workspace:*",
|
"@pnpm/read-package-json": "workspace:*",
|
||||||
"@pnpm/resolver-base": "workspace:*",
|
"@pnpm/resolver-base": "workspace:*",
|
||||||
|
|||||||
@@ -920,6 +920,9 @@ function referenceSatisfiesWantedSpec (
|
|||||||
return false
|
return false
|
||||||
}
|
}
|
||||||
const { version } = nameVerFromPkgSnapshot(depPath, pkgSnapshot)
|
const { version } = nameVerFromPkgSnapshot(depPath, pkgSnapshot)
|
||||||
|
if (!semver.validRange(wantedDep.pref) && Object.values(opts.lockfile.importers).filter(importer => importer.specifiers[wantedDep.alias] === wantedDep.pref).length) {
|
||||||
|
return true
|
||||||
|
}
|
||||||
return semver.satisfies(version, wantedDep.pref, true)
|
return semver.satisfies(version, wantedDep.pref, true)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -7,6 +7,8 @@ import {
|
|||||||
} from '@pnpm/manifest-utils'
|
} from '@pnpm/manifest-utils'
|
||||||
import versionSelectorType from 'version-selector-type'
|
import versionSelectorType from 'version-selector-type'
|
||||||
import semver from 'semver'
|
import semver from 'semver'
|
||||||
|
import { isGitHostedPkgUrl } from '@pnpm/pick-fetcher'
|
||||||
|
import { type TarballResolution } from '@pnpm/resolver-base'
|
||||||
import { type ResolvedDirectDependency } from './resolveDependencyTree'
|
import { type ResolvedDirectDependency } from './resolveDependencyTree'
|
||||||
import { type ImporterToResolve } from '.'
|
import { type ImporterToResolve } from '.'
|
||||||
|
|
||||||
@@ -25,7 +27,16 @@ export async function updateProjectManifest (
|
|||||||
.filter((rdd, index) => importer.wantedDependencies[index]?.updateSpec)
|
.filter((rdd, index) => importer.wantedDependencies[index]?.updateSpec)
|
||||||
.map((rdd, index) => {
|
.map((rdd, index) => {
|
||||||
const wantedDep = importer.wantedDependencies[index]!
|
const wantedDep = importer.wantedDependencies[index]!
|
||||||
return resolvedDirectDepToSpecObject({ ...rdd, isNew: wantedDep.isNew, specRaw: wantedDep.raw, preserveNonSemverVersionSpec: wantedDep.preserveNonSemverVersionSpec }, importer, {
|
return resolvedDirectDepToSpecObject({
|
||||||
|
...rdd,
|
||||||
|
isNew:
|
||||||
|
wantedDep.isNew,
|
||||||
|
specRaw: wantedDep.raw,
|
||||||
|
preserveNonSemverVersionSpec: wantedDep.preserveNonSemverVersionSpec,
|
||||||
|
// For git-protocol dependencies that are already installed locally, there is no normalizedPref unless do force resolve,
|
||||||
|
// so we use pref in wantedDependency here.
|
||||||
|
normalizedPref: rdd.normalizedPref ?? (isGitHostedPkgUrl((rdd.resolution as TarballResolution).tarball ?? '') ? wantedDep.pref : undefined),
|
||||||
|
}, importer, {
|
||||||
nodeExecPath: wantedDep.nodeExecPath,
|
nodeExecPath: wantedDep.nodeExecPath,
|
||||||
pinnedVersion: wantedDep.pinnedVersion ?? importer.pinnedVersion ?? 'major',
|
pinnedVersion: wantedDep.pinnedVersion ?? importer.pinnedVersion ?? 'major',
|
||||||
preserveWorkspaceProtocol: opts.preserveWorkspaceProtocol,
|
preserveWorkspaceProtocol: opts.preserveWorkspaceProtocol,
|
||||||
|
|||||||
@@ -12,6 +12,9 @@
|
|||||||
{
|
{
|
||||||
"path": "../../config/pick-registry-for-package"
|
"path": "../../config/pick-registry-for-package"
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
"path": "../../fetching/pick-fetcher"
|
||||||
|
},
|
||||||
{
|
{
|
||||||
"path": "../../lockfile/lockfile-types"
|
"path": "../../lockfile/lockfile-types"
|
||||||
},
|
},
|
||||||
|
|||||||
768
pnpm-lock.yaml
generated
768
pnpm-lock.yaml
generated
File diff suppressed because it is too large
Load Diff
Reference in New Issue
Block a user