-
Notifications
You must be signed in to change notification settings - Fork 91
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Do not register local and link components in pnpm9 detector (#1331)
* Do not register local and link components in pnpm9 detector * Add filters for http and https
- Loading branch information
1 parent
8a744bf
commit 10c85b6
Showing
7 changed files
with
196 additions
and
17 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -17,6 +17,12 @@ public override DetectedComponent CreateDetectedComponentFromPnpmPath(string pnp | |
|
||
// Strip parenthesized suffices from package. These hold peed dep related information that is unneeded here. | ||
// An example of a dependency path with these: /[email protected]([email protected])([email protected])([email protected]) | ||
var (normalizedPackageName, packageVersion) = this.ExtractNameAndVersionFromPnpmPackagePath(pnpmPackagePath); | ||
return new DetectedComponent(new NpmComponent(normalizedPackageName, packageVersion)); | ||
} | ||
|
||
public override (string FullPackageName, string PackageVersion) ExtractNameAndVersionFromPnpmPackagePath(string pnpmPackagePath) | ||
{ | ||
var fullPackageNameAndVersion = pnpmPackagePath.Split("(")[0]; | ||
|
||
var packageNameParts = fullPackageNameAndVersion.Split("@"); | ||
|
@@ -37,6 +43,6 @@ public override DetectedComponent CreateDetectedComponentFromPnpmPath(string pnp | |
// It is unclear if real packages could have a name starting with `/`, so avoid `TrimStart` that just in case. | ||
var normalizedPackageName = fullPackageName[1..]; | ||
|
||
return new DetectedComponent(new NpmComponent(normalizedPackageName, packageVersion)); | ||
return (normalizedPackageName, packageVersion); | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -7,6 +7,23 @@ public class PnpmV9ParsingUtilities<T> : PnpmParsingUtilitiesBase<T> | |
where T : PnpmYaml | ||
{ | ||
public override DetectedComponent CreateDetectedComponentFromPnpmPath(string pnpmPackagePath) | ||
{ | ||
/* | ||
* The format is documented at https://github.com/pnpm/spec/blob/master/dependency-path.md. | ||
* At the writing it does not seem to reflect changes which were made in lock file format v9: | ||
* See https://github.com/pnpm/spec/issues/5. | ||
* In general, the spec sheet for the v9 lockfile is not published, so parsing of this lockfile was emperically determined. | ||
* see https://github.com/pnpm/spec/issues/6 | ||
*/ | ||
|
||
// Strip parenthesized suffices from package. These hold peed dep related information that is unneeded here. | ||
// An example of a dependency path with these: /[email protected]([email protected])([email protected])([email protected]) | ||
(var fullPackageName, var packageVersion) = this.ExtractNameAndVersionFromPnpmPackagePath(pnpmPackagePath); | ||
|
||
return new DetectedComponent(new NpmComponent(fullPackageName, packageVersion)); | ||
} | ||
|
||
public override (string FullPackageName, string PackageVersion) ExtractNameAndVersionFromPnpmPackagePath(string pnpmPackagePath) | ||
{ | ||
/* | ||
* The format is documented at https://github.com/pnpm/spec/blob/master/dependency-path.md. | ||
|
@@ -28,7 +45,7 @@ public override DetectedComponent CreateDetectedComponentFromPnpmPath(string pnp | |
// Version is section after last `@`. | ||
var packageVersion = packageNameParts[^1]; | ||
|
||
return new DetectedComponent(new NpmComponent(fullPackageName, packageVersion)); | ||
return (fullPackageName, packageVersion); | ||
} | ||
|
||
/// <summary> | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -783,6 +783,144 @@ public async Task TestPnpmDetector_V9_GoodLockVersion_SkipsFileAndLinkDependenci | |
parentComponent => parentComponent.Name == "sampleDependency"); | ||
} | ||
|
||
[TestMethod] | ||
public async Task TestPnpmDetector_V9_GoodLockVersion_FileAndLinkDependenciesAreNotRegistered() | ||
{ | ||
var yamlFile = @" | ||
lockfileVersion: '9.0' | ||
settings: | ||
autoInstallPeers: true | ||
excludeLinksFromLockfile: false | ||
importers: | ||
.: | ||
dependencies: | ||
sampleDependency: | ||
specifier: ^1.1.1 | ||
version: 1.1.1 | ||
sampleFileDependency: | ||
specifier: file:../test | ||
version: file:../test | ||
SampleLinkDependency: | ||
specifier: workspace:* | ||
version: link:SampleLinkDependency | ||
packages: | ||
[email protected]: | ||
resolution: {integrity: sha512-zRpUiDwd/xk6ADqPMATG8vc9VPrkck7T07OIx0gnjmJAnHnTVXNQG3vfvWNuiZIkwu9KrKdA1iJKfsfTVxE6NA==} | ||
[email protected]: | ||
resolution: {integrity: sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==} | ||
engines: {node: '>= 0.8'} | ||
[email protected]: | ||
resolution: {integrity: sha512-ZySD7Nf91aLB0RxL4KGrKHBXl7Eds1DAmEdcoVawXnLD7SDhpNgtuII2aAkg7a7QS41jxPSZ17p4VdGnMHk3MQ==} | ||
engines: {node: '>=0.4.0'} | ||
snapshots: | ||
[email protected]: | ||
dependencies: | ||
sampleIndirectDependency: 3.3.3 | ||
sampleIndirectDependency2: 2.2.2 | ||
'file://../sampleFile': 'link:../\\' | ||
[email protected]: {} | ||
[email protected]: {} | ||
sampleFileDependency@file:../test': {} | ||
"; | ||
|
||
var (scanResult, componentRecorder) = await this.DetectorTestUtility | ||
.WithFile("pnpm-lock.yaml", yamlFile) | ||
.ExecuteDetectorAsync(); | ||
|
||
scanResult.ResultCode.Should().Be(ProcessingResultCode.Success); | ||
|
||
var detectedComponents = componentRecorder.GetDetectedComponents(); | ||
detectedComponents.Should().HaveCount(3); | ||
var npmComponents = detectedComponents.Select(x => new { Component = x.Component as NpmComponent, DetectedComponent = x }); | ||
npmComponents.Should().Contain(x => x.Component.Name == "sampleDependency" && x.Component.Version == "1.1.1"); | ||
npmComponents.Should().Contain(x => x.Component.Name == "sampleIndirectDependency2" && x.Component.Version == "2.2.2"); | ||
npmComponents.Should().Contain(x => x.Component.Name == "sampleIndirectDependency" && x.Component.Version == "3.3.3"); | ||
|
||
var noDevDependencyComponent = npmComponents.First(x => x.Component.Name == "sampleDependency"); | ||
var indirectDependencyComponent2 = npmComponents.First(x => x.Component.Name == "sampleIndirectDependency2"); | ||
var indirectDependencyComponent = npmComponents.First(x => x.Component.Name == "sampleIndirectDependency"); | ||
|
||
componentRecorder.GetEffectiveDevDependencyValue(noDevDependencyComponent.Component.Id).Should().BeFalse(); | ||
componentRecorder.GetEffectiveDevDependencyValue(indirectDependencyComponent2.Component.Id).Should().BeFalse(); | ||
componentRecorder.GetEffectiveDevDependencyValue(indirectDependencyComponent.Component.Id).Should().BeFalse(); | ||
componentRecorder.AssertAllExplicitlyReferencedComponents<NpmComponent>( | ||
indirectDependencyComponent.Component.Id, | ||
parentComponent => parentComponent.Name == "sampleDependency"); | ||
componentRecorder.AssertAllExplicitlyReferencedComponents<NpmComponent>( | ||
indirectDependencyComponent2.Component.Id, | ||
parentComponent => parentComponent.Name == "sampleDependency"); | ||
} | ||
|
||
[TestMethod] | ||
public async Task TestPnpmDetector_V9_GoodLockVersion_HttpDependenciesAreNotRegistered() | ||
{ | ||
var yamlFile = @" | ||
lockfileVersion: '9.0' | ||
settings: | ||
autoInstallPeers: true | ||
excludeLinksFromLockfile: false | ||
importers: | ||
.: | ||
dependencies: | ||
sampleDependency: | ||
specifier: ^1.1.1 | ||
version: 1.1.1 | ||
sampleHttpDependency: | ||
specifier: https://samplePackage/tar.gz/32f550d3b3bdb1b781aabe100683311cd982c98e | ||
version: sample@https://samplePackage/tar.gz/32f550d3b3bdb1b781aabe100683311cd982c98e | ||
SampleLinkDependency: | ||
specifier: workspace:* | ||
version: link:SampleLinkDependency | ||
packages: | ||
[email protected]: | ||
resolution: {integrity: sha512-zRpUiDwd/xk6ADqPMATG8vc9VPrkck7T07OIx0gnjmJAnHnTVXNQG3vfvWNuiZIkwu9KrKdA1iJKfsfTVxE6NA==} | ||
[email protected]: | ||
resolution: {integrity: sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==} | ||
engines: {node: '>= 0.8'} | ||
[email protected]: | ||
resolution: {integrity: sha512-ZySD7Nf91aLB0RxL4KGrKHBXl7Eds1DAmEdcoVawXnLD7SDhpNgtuII2aAkg7a7QS41jxPSZ17p4VdGnMHk3MQ==} | ||
engines: {node: '>=0.4.0'} | ||
snapshots: | ||
[email protected]: | ||
dependencies: | ||
sampleIndirectDependency: 3.3.3 | ||
sampleIndirectDependency2: 2.2.2 | ||
'file://../sampleFile': 'link:../\\' | ||
[email protected]: {} | ||
[email protected]: {} | ||
sampleHttpDependency@https://samplePackage/tar.gz/32f550d3b3bdb1b781aabe100683311cd982c98e': {} | ||
"; | ||
|
||
var (scanResult, componentRecorder) = await this.DetectorTestUtility | ||
.WithFile("pnpm-lock.yaml", yamlFile) | ||
.ExecuteDetectorAsync(); | ||
|
||
scanResult.ResultCode.Should().Be(ProcessingResultCode.Success); | ||
|
||
var detectedComponents = componentRecorder.GetDetectedComponents(); | ||
detectedComponents.Should().HaveCount(3); | ||
var npmComponents = detectedComponents.Select(x => new { Component = x.Component as NpmComponent, DetectedComponent = x }); | ||
npmComponents.Should().Contain(x => x.Component.Name == "sampleDependency" && x.Component.Version == "1.1.1"); | ||
npmComponents.Should().Contain(x => x.Component.Name == "sampleIndirectDependency2" && x.Component.Version == "2.2.2"); | ||
npmComponents.Should().Contain(x => x.Component.Name == "sampleIndirectDependency" && x.Component.Version == "3.3.3"); | ||
|
||
var noDevDependencyComponent = npmComponents.First(x => x.Component.Name == "sampleDependency"); | ||
var indirectDependencyComponent2 = npmComponents.First(x => x.Component.Name == "sampleIndirectDependency2"); | ||
var indirectDependencyComponent = npmComponents.First(x => x.Component.Name == "sampleIndirectDependency"); | ||
|
||
componentRecorder.GetEffectiveDevDependencyValue(noDevDependencyComponent.Component.Id).Should().BeFalse(); | ||
componentRecorder.GetEffectiveDevDependencyValue(indirectDependencyComponent2.Component.Id).Should().BeFalse(); | ||
componentRecorder.GetEffectiveDevDependencyValue(indirectDependencyComponent.Component.Id).Should().BeFalse(); | ||
componentRecorder.AssertAllExplicitlyReferencedComponents<NpmComponent>( | ||
indirectDependencyComponent.Component.Id, | ||
parentComponent => parentComponent.Name == "sampleDependency"); | ||
componentRecorder.AssertAllExplicitlyReferencedComponents<NpmComponent>( | ||
indirectDependencyComponent2.Component.Id, | ||
parentComponent => parentComponent.Name == "sampleDependency"); | ||
} | ||
|
||
[TestMethod] | ||
public async Task TestPnpmDetector_V9_GoodLockVersion_MissingSnapshotsSuccess() | ||
{ | ||
|