@@ -12,7 +12,7 @@ import {
1212 type FetchOptions ,
1313 type FetchResult ,
1414} from '@pnpm/fetcher-base'
15- import { type Cafs , type PackageFilesResponse } from '@pnpm/cafs-types'
15+ import { type Cafs } from '@pnpm/cafs-types'
1616import gfs from '@pnpm/graceful-fs'
1717import { logger } from '@pnpm/logger'
1818import { packageIsInstallable } from '@pnpm/package-is-installable'
@@ -139,18 +139,12 @@ export function createPackageRequester (
139139 virtualStoreDirMaxLength : opts . virtualStoreDirMaxLength ,
140140 strictStorePkgContentCheck : opts . strictStorePkgContentCheck ,
141141 } )
142- const peekPackageFromStore = peekFromStore . bind ( null , {
143- getIndexFilePathInCafs,
144- readPkgFromCafs,
145- fetchingLockerForPeek : new Map ( ) ,
146- } )
147142 const requestPackage = resolveAndFetch . bind ( null , {
148143 engineStrict : opts . engineStrict ,
149144 nodeVersion : opts . nodeVersion ,
150145 pnpmVersion : opts . pnpmVersion ,
151146 force : opts . force ,
152147 fetchPackageToStore,
153- peekPackageFromStore,
154148 requestsQueue,
155149 resolve : opts . resolve ,
156150 storeDir : opts . storeDir ,
@@ -176,113 +170,57 @@ async function resolveAndFetch (
176170 requestsQueue : { add : < T > ( fn : ( ) => Promise < T > , opts : { priority : number } ) => Promise < T > }
177171 resolve : ResolveFunction
178172 fetchPackageToStore : FetchPackageToStoreFunction
179- peekPackageFromStore : ( pkg : PkgNameVersion & {
180- id : string
181- resolution : Resolution
182- } ) => Promise < PeekFromStoreResult | undefined >
183173 storeDir : string
184174 } ,
185175 wantedDependency : WantedDependency & { optional ?: boolean } ,
186176 options : RequestPackageOptions
187177) : Promise < PackageResponse > {
188- let latest : string | undefined
189- let manifest : DependencyManifest | undefined
190- let normalizedBareSpecifier : string | undefined
191- let alias : string | undefined
192178 let resolution = options . currentPkg ?. resolution as Resolution
193179 let pkgId = options . currentPkg ?. id
194- const skipResolution = resolution && ! options . update
195- let forceFetch = false
196- let updated = false
197- let resolvedVia : string | undefined
198- let publishedAt : string | undefined
199-
200- async function performResolution ( ) {
201- // When skipResolution is set but a resolution is still performed due to
202- // options.skipFetch, it's necessary to make sure the resolution doesn't
203- // accidentally return a newer version of the package. When skipFetch is
204- // set, the resolved package shouldn't be different. This is done by
205- // overriding the preferredVersions object to only contain the current
206- // package's version.
207- //
208- // A naive approach would be to change the bare specifier to be the exact
209- // version of the current pkg if the bare specifier is a range, but this
210- // would cause the version returned for calcSpecifier to be different.
211- const preferredVersions : PreferredVersions = ( skipResolution && options . currentPkg ?. name != null && options . currentPkg ?. version != null )
212- ? {
213- ...options . preferredVersions ,
214- [ options . currentPkg . name ] : { [ options . currentPkg . version ] : 'version' } ,
215- }
216- : options . preferredVersions
217-
218- const resolveResult = await ctx . requestsQueue . add < ResolveResult > ( async ( ) => ctx . resolve ( wantedDependency , {
219- alwaysTryWorkspacePackages : options . alwaysTryWorkspacePackages ,
220- defaultTag : options . defaultTag ,
221- trustPolicy : options . trustPolicy ,
222- trustPolicyExclude : options . trustPolicyExclude ,
223- trustPolicyIgnoreAfter : options . trustPolicyIgnoreAfter ,
224- publishedBy : options . publishedBy ,
225- publishedByExclude : options . publishedByExclude ,
226- pickLowestVersion : options . pickLowestVersion ,
227- lockfileDir : options . lockfileDir ,
228- preferredVersions,
229- preferWorkspacePackages : options . preferWorkspacePackages ,
230- projectDir : options . projectDir ,
231- workspacePackages : options . workspacePackages ,
232- update : options . update ,
233- injectWorkspacePackages : options . injectWorkspacePackages ,
234- calcSpecifier : options . calcSpecifier ,
235- pinnedVersion : options . pinnedVersion ,
236- } ) , { priority : options . downloadPriority } )
237-
238- manifest = resolveResult . manifest
239- latest = resolveResult . latest
240- resolvedVia = resolveResult . resolvedVia
241- publishedAt = resolveResult . publishedAt
242-
243- // If the integrity of a local tarball dependency has changed,
244- // the local tarball should be unpacked, so a fetch to the store should be forced
245- forceFetch = Boolean (
246- ( ( options . currentPkg ?. resolution ) != null ) &&
247- pkgId ?. startsWith ( 'file:' ) &&
248- ( options . currentPkg ?. resolution as TarballResolution ) . integrity !== ( resolveResult . resolution as TarballResolution ) . integrity
249- )
250-
251- updated = pkgId !== resolveResult . id || ! resolution || forceFetch
252- resolution = resolveResult . resolution
253- pkgId = resolveResult . id
254- normalizedBareSpecifier = resolveResult . normalizedBareSpecifier
255- alias = resolveResult . alias
256- }
257180
258- // When fetching is skipped, we still need the package's manifest for
259- // lockfile-only installs.
181+ // When we have a currentPkg but a resolution is still performed due to
182+ // options.skipFetch, it's necessary to make sure the resolution doesn't
183+ // accidentally return a newer version of the package. When skipFetch is
184+ // set, the resolved package shouldn't be different. This is done by
185+ // overriding the preferredVersions object to only contain the current
186+ // package's version.
260187 //
261- // The package manifest could be retrieved from CAFS if the package has been
262- // fetched previously. Otherwise we'll need to perform a resolution.
263- //
264- // The resolution step is never skipped for local dependencies.
265- if ( ! skipResolution || options . skipFetch === true || Boolean ( pkgId ?. startsWith ( 'file:' ) ) || wantedDependency . optional === true ) {
266- // If the manifest for this package is in the store, retrieving it from the
267- // Content-Addressable File Store will be significantly faster than fetching
268- // it from metadata. This is because package metadata contains the
269- // package.json contents of a package across all of its versions, which
270- // takes a long time to parse.
271- if ( skipResolution && ! pkgId ?. startsWith ( 'file:' ) && wantedDependency . optional !== true && pkgId != null ) {
272- const pkg = await ctx . peekPackageFromStore ( {
273- ...options . expectedPkg ,
274- id : pkgId ,
275- resolution,
276- } )
277- manifest = pkg ?. bundledManifest
188+ // A naive approach would be to change the bare specifier to be the exact
189+ // version of the current pkg if the bare specifier is a range, but this
190+ // would cause the version returned for calcSpecifier to be different.
191+ const preferredVersions : PreferredVersions = ( resolution && ! options . update && options . currentPkg ?. name != null && options . currentPkg ?. version != null )
192+ ? {
193+ ...options . preferredVersions ,
194+ [ options . currentPkg . name ] : { [ options . currentPkg . version ] : 'version' } ,
278195 }
196+ : options . preferredVersions
279197
280- // However, if the optimization above isn't possible or the package has
281- // never been added to the CAFS, we'll need to perform a resolution.
282- if ( manifest == null ) {
283- await performResolution ( )
284- }
285- }
198+ const resolveResult = await ctx . requestsQueue . add < ResolveResult > ( async ( ) => ctx . resolve ( wantedDependency , {
199+ ...options ,
200+ preferredVersions,
201+ currentPkg : ( options . currentPkg ?. id && options . currentPkg ?. resolution )
202+ ? {
203+ id : options . currentPkg . id ,
204+ name : options . currentPkg . name ,
205+ version : options . currentPkg . version ,
206+ resolution : options . currentPkg . resolution ,
207+ }
208+ : undefined ,
209+ } ) , { priority : options . downloadPriority } )
210+
211+ let { manifest } = resolveResult
212+ const {
213+ latest,
214+ resolvedVia,
215+ publishedAt,
216+ normalizedBareSpecifier,
217+ alias,
218+ forceFetch,
219+ } = resolveResult
220+
221+ const updated = pkgId !== resolveResult . id || ! resolution || forceFetch === true
222+ resolution = resolveResult . resolution
223+ pkgId = resolveResult . id
286224
287225 const id = pkgId !
288226
@@ -319,8 +257,9 @@ async function resolveAndFetch (
319257 )
320258 )
321259 // We can skip fetching the package only if the manifest
322- // is present after resolution
323- if ( ( options . skipFetch === true || isInstallable === false ) && ( manifest != null ) ) {
260+ // is present after resolution AND we're not forcing a fetch
261+ // (forceFetch is set by resolvers when package content may have changed)
262+ if ( ( options . skipFetch === true || isInstallable === false ) && ! forceFetch && ( manifest != null ) ) {
324263 return {
325264 body : {
326265 id,
@@ -342,7 +281,7 @@ async function resolveAndFetch (
342281 const fetchResult = ctx . fetchPackageToStore ( {
343282 allowBuild : options . allowBuild ,
344283 fetchRawManifest : true ,
345- force : forceFetch ,
284+ force : forceFetch === true ,
346285 ignoreScripts : options . ignoreScripts ,
347286 lockfileDir : options . lockfileDir ,
348287 pkg : {
@@ -673,69 +612,6 @@ function fetchToStore (
673612 }
674613}
675614
676- interface PeekFromStoreResult {
677- readonly bundledManifest ?: BundledManifest
678- readonly files : PackageFilesResponse
679- }
680-
681- /**
682- * Look up requests from the store without mutating it. This is related to
683- * {@link fetchToStore}, but does not perform a fetch if the lookup was not
684- * found.
685- *
686- * This function will return undefined if the package was found in the store,
687- * but fails integrity checks.
688- */
689- async function peekFromStore (
690- ctx : {
691- readPkgFromCafs : (
692- filesIndexFile : string ,
693- opts ?: ReadPkgFromCafsOptions
694- ) => Promise < ReadPkgFromCafsResult >
695- getIndexFilePathInCafs : ( integrity : string , pkgId : string ) => string
696- fetchingLockerForPeek : Map < string , Promise < PeekFromStoreResult | undefined > >
697- } ,
698- pkg : PkgNameVersion & {
699- id : string
700- resolution : Resolution
701- }
702- ) : Promise < PeekFromStoreResult | undefined > {
703- // This function only supports TarballResolution requests with a present
704- // integrity.
705- if ( pkg . resolution . type != null || pkg . resolution . integrity == null ) {
706- return undefined
707- }
708-
709- const indexFilePathInCafs = ctx . getIndexFilePathInCafs ( pkg . resolution . integrity , pkg . id )
710- const existingRequest = ctx . fetchingLockerForPeek . get ( indexFilePathInCafs )
711-
712- if ( existingRequest != null ) {
713- return existingRequest
714- }
715-
716- const request = ctx . readPkgFromCafs ( indexFilePathInCafs , {
717- readManifest : true ,
718- expectedPkg : pkg ,
719- } )
720- . then ( ( { files, manifest, verified } ) : PeekFromStoreResult | undefined => {
721- // If the files in the store are corrupted or out of date, it's better to
722- // fail the peek result and allow the caller to fall back to a resolution
723- // or proper fetch.
724- if ( ! verified ) {
725- return undefined
726- }
727-
728- return {
729- files,
730- bundledManifest : manifest == null ? manifest : normalizeBundledManifest ( manifest ) ,
731- }
732- } )
733-
734- ctx . fetchingLockerForPeek . set ( indexFilePathInCafs , request )
735-
736- return request
737- }
738-
739615async function readBundledManifest ( pkgJsonPath : string ) : Promise < BundledManifest > {
740616 return pickBundledManifest ( await readPackageJson ( pkgJsonPath ) as DependencyManifest )
741617}
0 commit comments