diff --git a/packages/core/src/getPeerDependencyIssues.ts b/packages/core/src/getPeerDependencyIssues.ts index 2099ff43a33..9b6bde7fd5d 100644 --- a/packages/core/src/getPeerDependencyIssues.ts +++ b/packages/core/src/getPeerDependencyIssues.ts @@ -48,6 +48,7 @@ export async function getPeerDependencyIssues ( projectsToResolve, { currentLockfile: ctx.currentLockfile, + allowedDeprecatedVersions: {}, defaultUpdateDepth: -1, dryRun: true, engineStrict: false, diff --git a/packages/core/src/install/extendInstallOptions.ts b/packages/core/src/install/extendInstallOptions.ts index fb000b01f81..18c316df14d 100644 --- a/packages/core/src/install/extendInstallOptions.ts +++ b/packages/core/src/install/extendInstallOptions.ts @@ -7,6 +7,7 @@ import normalizeRegistries, { DEFAULT_REGISTRIES } from '@pnpm/normalize-registr import { WorkspacePackages } from '@pnpm/resolver-base' import { StoreController } from '@pnpm/store-controller-types' import { + AllowedDeprecatedVersions, PackageExtension, PeerDependencyRules, ReadPackageHook, @@ -86,6 +87,7 @@ export interface StrictInstallOptions { enableModulesDir: boolean modulesCacheMaxAge: number peerDependencyRules: PeerDependencyRules + allowedDeprecatedVersions: AllowedDeprecatedVersions publicHoistPattern: string[] | undefined hoistPattern: string[] | undefined @@ -108,6 +110,7 @@ const defaults = async (opts: InstallOptions) => { version: pnpmPkgJson.version, } return { + allowedDeprecatedVersions: {}, autoInstallPeers: false, childConcurrency: 5, depth: 0, diff --git a/packages/core/src/install/index.ts b/packages/core/src/install/index.ts index 878d40e5943..dad5eac8595 100644 --- a/packages/core/src/install/index.ts +++ b/packages/core/src/install/index.ts @@ -740,6 +740,7 @@ const _installInContext: InstallFunction = async (projects, ctx, opts) => { projects, { allowBuild: createAllowBuildFunction(opts), + allowedDeprecatedVersions: opts.allowedDeprecatedVersions, autoInstallPeers: opts.autoInstallPeers, currentLockfile: ctx.currentLockfile, defaultUpdateDepth: (opts.update || (opts.updateMatching != null)) ? opts.depth : -1, diff --git a/packages/plugin-commands-installation/src/getOptionsFromRootManifest.ts b/packages/plugin-commands-installation/src/getOptionsFromRootManifest.ts index 24f7b38d994..d2052d00ca1 100644 --- a/packages/plugin-commands-installation/src/getOptionsFromRootManifest.ts +++ b/packages/plugin-commands-installation/src/getOptionsFromRootManifest.ts @@ -1,10 +1,12 @@ import { + AllowedDeprecatedVersions, PackageExtension, PeerDependencyRules, ProjectManifest, } from '@pnpm/types' export default function getOptionsFromRootManifest (manifest: ProjectManifest): { + allowedDeprecatedVersions?: AllowedDeprecatedVersions overrides?: Record neverBuiltDependencies?: string[] onlyBuiltDependencies?: string[] @@ -19,7 +21,9 @@ export default function getOptionsFromRootManifest (manifest: ProjectManifest): const onlyBuiltDependencies = manifest.pnpm?.onlyBuiltDependencies const packageExtensions = manifest.pnpm?.packageExtensions const peerDependencyRules = manifest.pnpm?.peerDependencyRules + const allowedDeprecatedVersions = manifest.pnpm?.allowedDeprecatedVersions return { + allowedDeprecatedVersions, overrides, neverBuiltDependencies, onlyBuiltDependencies, diff --git a/packages/resolve-dependencies/src/resolveDependencies.ts b/packages/resolve-dependencies/src/resolveDependencies.ts index 2a4def14f71..71dc00f1c00 100644 --- a/packages/resolve-dependencies/src/resolveDependencies.ts +++ b/packages/resolve-dependencies/src/resolveDependencies.ts @@ -29,6 +29,7 @@ import { StoreController, } from '@pnpm/store-controller-types' import { + AllowedDeprecatedVersions, Dependencies, DependencyManifest, PackageManifest, @@ -119,6 +120,7 @@ export interface ChildrenByParentDepPath { export interface ResolutionContext { autoInstallPeers: boolean allowBuild?: (pkgName: string) => boolean + allowedDeprecatedVersions: AllowedDeprecatedVersions updatedSet: Set defaultTag: string dryRun: boolean @@ -889,7 +891,10 @@ async function resolveDependency ( const isNew = !ctx.resolvedPackagesByDepPath[depPath] if (isNew) { - if (pkg.deprecated) { + if ( + pkg.deprecated && + (!ctx.allowedDeprecatedVersions[pkg.name] || !semver.satisfies(pkg.version, ctx.allowedDeprecatedVersions[pkg.name])) + ) { // Report deprecated packages only on first occurrence. deprecationLogger.debug({ deprecated: pkg.deprecated, diff --git a/packages/resolve-dependencies/src/resolveDependencyTree.ts b/packages/resolve-dependencies/src/resolveDependencyTree.ts index 0335efc8c11..a6a3cd6dd25 100644 --- a/packages/resolve-dependencies/src/resolveDependencyTree.ts +++ b/packages/resolve-dependencies/src/resolveDependencyTree.ts @@ -2,6 +2,7 @@ import { Lockfile } from '@pnpm/lockfile-types' import { PreferredVersions, Resolution, WorkspacePackages } from '@pnpm/resolver-base' import { StoreController } from '@pnpm/store-controller-types' import { + AllowedDeprecatedVersions, ProjectManifest, ReadPackageHook, Registries, @@ -55,6 +56,7 @@ export interface ImporterToResolveGeneric extends Importer { export interface ResolveDependenciesOptions { autoInstallPeers?: boolean allowBuild?: (pkgName: string) => boolean + allowedDeprecatedVersions: AllowedDeprecatedVersions currentLockfile: Lockfile dryRun: boolean engineStrict: boolean @@ -88,6 +90,7 @@ export default async function ( const ctx = { autoInstallPeers: opts.autoInstallPeers === true, allowBuild: opts.allowBuild, + allowedDeprecatedVersions: opts.allowedDeprecatedVersions, childrenByParentDepPath: {} as ChildrenByParentDepPath, currentLockfile: opts.currentLockfile, defaultTag: opts.tag, diff --git a/packages/types/src/package.ts b/packages/types/src/package.ts index 4d1bb00b41c..6dfdd64107b 100644 --- a/packages/types/src/package.ts +++ b/packages/types/src/package.ts @@ -115,6 +115,8 @@ export interface PeerDependencyRules { allowedVersions?: Record } +export type AllowedDeprecatedVersions = Record + export type ProjectManifest = BaseManifest & { pnpm?: { neverBuiltDependencies?: string[] @@ -122,6 +124,7 @@ export type ProjectManifest = BaseManifest & { overrides?: Record packageExtensions?: Record peerDependencyRules?: PeerDependencyRules + allowedDeprecatedVersions?: AllowedDeprecatedVersions } private?: boolean resolutions?: Record