diff --git a/.github/workflows/compile.yml b/.github/workflows/compile.yml index a79c4b8f..aefa8ed0 100644 --- a/.github/workflows/compile.yml +++ b/.github/workflows/compile.yml @@ -18,7 +18,8 @@ jobs: semver: ${{ steps.gitversion.outputs.semver }} LicenseClearingTool: ${{ steps.packageBuildResults.outputs.LicenseClearingTool }} nupkg-LicenseClearingTool: ${{ steps.createNupkg.outputs.nupkg-LicenseClearingTool }} - + docker-LicenseClearingTool: ${{ steps.builddocker.outputs.docker-LicenseClearingTool }} + steps: - name: Checkout uses: actions/checkout@v3 @@ -149,11 +150,12 @@ jobs: *.nupkg - name: Build the Docker image + id: builddocker #if: ${{ false }} # disable for now run: | docker build . --file Dockerfile --tag ${{ github.repository }}:continuous-clearing-v3.1.1 docker save ${{ github.repository }}:continuous-clearing-v3.1.1 -o continuous-clearing-v3.1.1.tar - + Write-Host "::set-output name=docker-LicenseClearingTool::continuous-clearing-v3.1.1.tar" - name: Archive docker image #if: ${{ false }} # disable for now @@ -179,6 +181,11 @@ jobs: with: name: nuget-continuous-clearing + - name: Download Docker image + uses: actions/download-artifact@v2 + with: + name: docker-continuous-clearing + - name: Debug run: | tree @@ -216,7 +223,17 @@ jobs: asset_path: ./${{ needs.build.outputs.nupkg-LicenseClearingTool }} asset_name: ${{ needs.build.outputs.nupkg-LicenseClearingTool }} asset_content_type: application/zip - + + - name: Upload Nupkg + uses: actions/upload-release-asset@v1 + env: + GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} + with: + upload_url: ${{ steps.create_release.outputs.upload_url }} + asset_path: ./${{ needs.build.outputs.docker-LicenseClearingTool }} + asset_name: ${{ needs.build.outputs.docker-LicenseClearingTool }} + asset_content_type: application/zip + - name: Upload ReadmeOSS_nupkg file uses: actions/upload-release-asset@v1 env: diff --git a/CA.nuspec b/CA.nuspec index 41ac3920..ea91a605 100644 --- a/CA.nuspec +++ b/CA.nuspec @@ -4,7 +4,7 @@ continuous-clearing - 3.1.1 + 3.1.2 Siemens AG continuous-clearing contributors https://github.com/siemens/continuous-clearing diff --git a/doc/UsageDoc/CA_UsageDocument.md b/doc/UsageDoc/CA_UsageDocument.md index c2ef958c..7c27f0ce 100644 --- a/doc/UsageDoc/CA_UsageDocument.md +++ b/doc/UsageDoc/CA_UsageDocument.md @@ -178,8 +178,7 @@ Continuous Clearing Tool reduces the effort in creating components in SW360 and #### **Method 1 (Recommended)** Copy the below content and create new `appSettings.json` file in `Continuous Clearing tool Config` directory. - - + Below is the list of settings can be made in `appSettings.json` file. _`Sample appSettings.json file`_ @@ -273,12 +272,13 @@ Description for the settings in `appSettings.json` file | 19 | --jfrogmavendestreponame | The destination folder name for the Maven package to be copied to | Yes | | | 20 | --timeout | SW360 response timeout value | No | | + #### **Method 2** You can also pass the above mentioned arguments in the command line. `Note: If the second approach is followed then make sure you provide all the settings mentioned in the appsettings.json in the command line` - + #### Exclude Component or Folders : In order to exclude any components ,it can be configured in the "appSettings.json" by providing the package name and version as specified above in the *_ExcludedComponents_* field. diff --git a/src/ArtifactoryUploader/PackageUploadHelper.cs b/src/ArtifactoryUploader/PackageUploadHelper.cs index ace589b7..664df95b 100644 --- a/src/ArtifactoryUploader/PackageUploadHelper.cs +++ b/src/ArtifactoryUploader/PackageUploadHelper.cs @@ -246,7 +246,7 @@ private static async Task PackageUploadToArtifactory(UploaderKpiData uploaderKpi else { uploaderKpiData.PackagesUploadedToJfrog++; - Logger.Warn($"Package {item.Name}-{item.Version} is already uploaded to {item.DestRepoName}"); + Logger.Info($"Package {item.Name}-{item.Version} is already uploaded to {item.DestRepoName}"); } } diff --git a/src/LCT.Common/appSettings.json b/src/LCT.Common/appSettings.json index 9d21527d..6f3f3166 100644 --- a/src/LCT.Common/appSettings.json +++ b/src/LCT.Common/appSettings.json @@ -4,7 +4,7 @@ // SPDX-License-Identifier: MIT // -------------------------------------------------------------------------------------------------------------------- { - "CaVersion": "3.1.1", + "CaVersion": "3.1.2", "TimeOut": 200, "ProjectType": "", "SW360ProjectName": "", diff --git a/src/LCT.PackageIdentifier.UTest/NugetParserTests.cs b/src/LCT.PackageIdentifier.UTest/NugetParserTests.cs index 83cb93da..97de4054 100644 --- a/src/LCT.PackageIdentifier.UTest/NugetParserTests.cs +++ b/src/LCT.PackageIdentifier.UTest/NugetParserTests.cs @@ -18,6 +18,7 @@ using LCT.APICommunications.Model.AQL; using CycloneDX.Models; using System.Threading.Tasks; +using System.Linq; namespace PackageIdentifier.UTest { @@ -234,7 +235,7 @@ public async Task IdentificationOfInternalComponents_Nuget_ReturnsComponentData_ AqlResult aqlResult = new() { - Name = "animations-1.0.0.tgz", + Name = "animations-1.0.0.nupkg", Path = "@siemens-gds/saap-api-node/-/@siemens-gds", Repo = "energy-dev-npm-egll" }; @@ -271,7 +272,7 @@ public async Task IdentificationOfInternalComponents_Nuget_ReturnsComponentData2 AqlResult aqlResult = new() { - Name = "animations-common_license-1.0.0.tgz", + Name = "animations-common_license-1.0.0.nupkg", Path = "@siemens-gds/saap-api-node/-/@siemens-gds", Repo = "energy-dev-npm-egll" }; @@ -309,7 +310,7 @@ public async Task IdentificationOfInternalComponents_ReturnsComponentData3_Succe AqlResult aqlResult = new() { - Name = "animations-common-1.0.0.tgz", + Name = "animations-common-1.0.0.nupkg", Path = "@siemens-gds/saap-api-node/-/@siemens-gds", Repo = "energy-dev-npm-egll" }; @@ -347,7 +348,7 @@ public async Task GetJfrogRepoDetailsOfAComponent_ReturnsWithData_SuccessFully() appSettings.Nuget = new LCT.Common.Model.Config() { JfrogNugetRepoList = reooListArr }; AqlResult aqlResult = new() { - Name = "animations-common-1.0.0.tgz", + Name = "animations-common-1.0.0.nupkg", Path = "@siemens-gds/saap-api-node/-/@siemens-gds", Repo = "siparty-release-npm-egll" }; @@ -383,10 +384,10 @@ public async Task GetJfrogRepoDetailsOfAComponent_Nuget_ReturnsWithData2_Success var components = new List() { component1 }; string[] reooListArr = { "siparty-release-npm-egll", "org1-npmjs-npm-remote-cache" }; CommonAppSettings appSettings = new(); - appSettings.Nuget = new LCT.Common.Model.Config() { JfrogNugetRepoList = reooListArr }; + appSettings.Nuget = new Config() { JfrogNugetRepoList = reooListArr }; AqlResult aqlResult = new() { - Name = "animations-common-1.0.0.tgz", + Name = "animations-common-1.0.0.nupkg", Path = "@siemens-gds/saap-api-node/-/@siemens-gds", Repo = "siparty-release-npm-egll" }; @@ -407,5 +408,162 @@ public async Task GetJfrogRepoDetailsOfAComponent_Nuget_ReturnsWithData2_Success // Assert Assert.That(actual, Is.Not.Null); } + + [Test] + public async Task GetArtifactoryRepoName_Nuget_ReturnsRepoName_SuccessFully() + { + // Arrange + Component component1 = new() + { + Name = "animations-common", + Group = "", + Description = string.Empty, + Version = "1.0.0" + }; + var components = new List() { component1 }; + string[] reooListArr = { "siparty-release-npm-egll", "org1-npmjs-npm-remote-cache" }; + CommonAppSettings appSettings = new(); + appSettings.Nuget = new Config() { JfrogNugetRepoList = reooListArr }; + AqlResult aqlResult = new() + { + Name = "animations-common-1.0.0.nupkg", + Path = "@siemens-gds/saap-api-node/-/@siemens-gds", + Repo = "siparty-release-npm-egll" + }; + + List results = new List() { aqlResult }; + + Mock mockJfrogService = new Mock(); + Mock mockBomHelper = new Mock(); + mockBomHelper.Setup(m => m.GetListOfComponentsFromRepo(It.IsAny(), It.IsAny())) + .ReturnsAsync(results); + mockBomHelper.Setup(m => m.GetFullNameOfComponent(It.IsAny())).Returns("animations"); + + // Act + NugetProcessor nugetProcessor = new NugetProcessor(); + var actual = await nugetProcessor.GetJfrogRepoDetailsOfAComponent( + components, appSettings, mockJfrogService.Object, mockBomHelper.Object); + + var reponameActual = actual.First(x => x.Properties[0].Name == "internal:siemens:clearing:repo-url").Properties[0].Value; + + Assert.That(reponameActual, Is.EqualTo(aqlResult.Repo)); + } + [Test] + public async Task GetArtifactoryRepoName_Nuget_ReturnsRepoName_ReturnsFailure() + { + // Arrange + Component component1 = new() + { + Name = "animations-common", + Group = "", + Description = string.Empty, + Version = "1.0.0" + }; + var components = new List() { component1 }; + string[] reooListArr = { "siparty-release-npm-egll", "org1-npmjs-npm-remote-cache" }; + CommonAppSettings appSettings = new(); + appSettings.Nuget = new Config() { JfrogNugetRepoList = reooListArr }; + AqlResult aqlResult = new() + { + Name = "animation-test-1.0.0.nupkg", + Path = "@siemens-gds/saap-api-node/-/@siemens-gds", + Repo = "siparty-release-npm-egll" + }; + + List results = new () { aqlResult }; + + Mock mockJfrogService = new Mock(); + Mock mockBomHelper = new Mock(); + mockBomHelper.Setup(m => m.GetListOfComponentsFromRepo(It.IsAny(), It.IsAny())) + .ReturnsAsync(results); + mockBomHelper.Setup(m => m.GetFullNameOfComponent(It.IsAny())).Returns("animations"); + + // Act + NugetProcessor nugetProcessor = new NugetProcessor(); + var actual = await nugetProcessor.GetJfrogRepoDetailsOfAComponent( + components, appSettings, mockJfrogService.Object, mockBomHelper.Object); + + var reponameActual = actual.First(x => x.Properties[0].Name == "internal:siemens:clearing:repo-url").Properties[0].Value; + + Assert.That("Not Found in JFrogRepo", Is.EqualTo(reponameActual)); + } + [Test] + public async Task GetArtifactoryRepoName_Nuget_ReturnsRepoName_ReturnsSuccess() + { + // Arrange + Component component1 = new() + { + Name = "animations-common", + Group = "", + Description = string.Empty, + Version = "1.0.0" + }; + var components = new List() { component1 }; + string[] reooListArr = { "siparty-release-npm-egll", "org1-npmjs-npm-remote-cache" }; + CommonAppSettings appSettings = new(); + appSettings.Nuget = new Config() { JfrogNugetRepoList = reooListArr }; + AqlResult aqlResult = new() + { + Name = "animations-common.1.0.0.nupkg", + Path = "@siemens-gds/saap-api-node/-/@siemens-gds", + Repo = "siparty-release-npm-egll" + }; + + List results = new() { aqlResult }; + + Mock mockJfrogService = new Mock(); + Mock mockBomHelper = new Mock(); + mockBomHelper.Setup(m => m.GetListOfComponentsFromRepo(It.IsAny(), It.IsAny())) + .ReturnsAsync(results); + mockBomHelper.Setup(m => m.GetFullNameOfComponent(It.IsAny())).Returns("animations"); + + // Act + NugetProcessor nugetProcessor = new NugetProcessor(); + var actual = await nugetProcessor.GetJfrogRepoDetailsOfAComponent( + components, appSettings, mockJfrogService.Object, mockBomHelper.Object); + + var reponameActual = actual.First(x => x.Properties[0].Name == "internal:siemens:clearing:repo-url").Properties[0].Value; + + Assert.That("siparty-release-npm-egll", Is.EqualTo(reponameActual)); + } + [Test] + public async Task GetArtifactoryRepoName_Nuget_ReturnsNotFound_ReturnsFailure() + { + // Arrange + Component component1 = new() + { + Name = "animations-common", + Group = "", + Description = string.Empty, + Version = "1.0.0" + }; + var components = new List() { component1 }; + string[] reooListArr = { "siparty-release-npm-egll", "org1-npmjs-npm-remote-cache" }; + CommonAppSettings appSettings = new(); + appSettings.Nuget = new Config() { JfrogNugetRepoList = reooListArr }; + AqlResult aqlResult = new() + { + Name = "animation-common.1.0.0.nupkg", + Path = "@siemens-gds/saap-api-node/-/@siemens-gds", + Repo = "siparty-release-npm-egll" + }; + + List results = new() { aqlResult }; + + Mock mockJfrogService = new Mock(); + Mock mockBomHelper = new Mock(); + mockBomHelper.Setup(m => m.GetListOfComponentsFromRepo(It.IsAny(), It.IsAny())) + .ReturnsAsync(results); + mockBomHelper.Setup(m => m.GetFullNameOfComponent(It.IsAny())).Returns("animations"); + + // Act + NugetProcessor nugetProcessor = new NugetProcessor(); + var actual = await nugetProcessor.GetJfrogRepoDetailsOfAComponent( + components, appSettings, mockJfrogService.Object, mockBomHelper.Object); + + var reponameActual = actual.First(x => x.Properties[0].Name == "internal:siemens:clearing:repo-url").Properties[0].Value; + + Assert.That("Not Found in JFrogRepo", Is.EqualTo(reponameActual)); + } } } diff --git a/src/LCT.PackageIdentifier/NugetProcessor.cs b/src/LCT.PackageIdentifier/NugetProcessor.cs index 181759c1..8e1a28b0 100644 --- a/src/LCT.PackageIdentifier/NugetProcessor.cs +++ b/src/LCT.PackageIdentifier/NugetProcessor.cs @@ -296,13 +296,13 @@ public async Task> GetJfrogRepoDetailsOfAComponent(List aqlResultList, Component component, IBomHelper bomHelper) { - string jfrogcomponentName = $"{component.Name}-{component.Version}.tgz"; + string jfrogcomponentName = $"{component.Name}-{component.Version}.nupkg"; string repoName = aqlResultList.Find(x => x.Name.Equals( jfrogcomponentName, StringComparison.OrdinalIgnoreCase))?.Repo ?? NotFoundInRepo; string fullName = bomHelper.GetFullNameOfComponent(component); - string fullNameVersion = $"{fullName}-{component.Version}.tgz"; + string fullNameVersion = $"{fullName}-{component.Version}.nupkg"; if (!fullNameVersion.Equals(jfrogcomponentName, StringComparison.OrdinalIgnoreCase) && repoName.Equals(NotFoundInRepo, StringComparison.OrdinalIgnoreCase)) @@ -310,6 +310,13 @@ private static string GetArtifactoryRepoName(List aqlResultList, Comp repoName = aqlResultList.Find(x => x.Name.Equals( fullNameVersion, StringComparison.OrdinalIgnoreCase))?.Repo ?? NotFoundInRepo; } + if (repoName == NotFoundInRepo) + { + jfrogcomponentName = $"{component.Name}.{component.Version}.nupkg"; + repoName = aqlResultList.Find(x => x.Name.Equals( + jfrogcomponentName, StringComparison.OrdinalIgnoreCase))?.Repo ?? NotFoundInRepo; + + } return repoName; } @@ -363,7 +370,7 @@ private static bool IsInternalNugetComponent(List aqlResultList, Comp string fullName = bomHelper.GetFullNameOfComponent(component); string fullNameVersion = $"{fullName}.{component.Version}.nupkg"; - if (!fullNameVersion.Equals(jfrogcomponentName, StringComparison.OrdinalIgnoreCase) + if (!fullNameVersion.Equals(jfrogcomponentName, StringComparison.OrdinalIgnoreCase) && aqlResultList.Exists( x => x.Name.Equals(fullNameVersion, StringComparison.OrdinalIgnoreCase))) {