Nuget restore not working with artifact feed in Azure Devops - .net-core

NuGet restore fails 404 from feed on another project in same organization.
When using nuget restore from a pipeline the feed inside a different project is not found.

After searching for a long time, these are the steps necessary to make it work consistently:
Setup permissions
Make sure to add Build Service of the consuming project to the permissions of the feed
Make sure the consuming project has these two settings disabled
Project settings (bottom left) --> Pipelines --> Settings
Limit job authorization scope to current project for non-release pipelines
Limit job authorization scope to current project for release pipelines
Setup build pipeline
Use the .Net Core CLI Task
Ideally you would use a nuget.config file and make sure to check it in
Set the feedsToUse to 'config'
azure-pipelines.yml
- task: DotNetCoreCLI#2
displayName: DotNetCore-Restore
inputs:
command: 'restore'
projects: '$(PathToSolution)'
feedsToUse: 'config'
nugetConfigPath: '$(PathToNugetConfig)/nuget.config'
includeNuGetOrg: true
nuget.config
<?xml version="1.0" encoding="utf-8"?>
<configuration>
<packageSources>
<clear />
<add key="feed_name" value="feed_url" />
</packageSources>
</configuration>
There is no need to add an authenticate task to the pipeline as the dotnet command does this by itself... However:
Most dotnet commands, including build, publish, and test include an
implicit restore step. This will fail against authenticated feeds,
even if you ran a successful dotnet restore in an earlier step,
because the earlier step will have cleaned up the credentials it used.
Source (.NET Core CLI task docs)

You can refer to this doc to setup Azure Artifacts Credential Provider for usage across various tooling.

Related

Strange behavior restore package from local feed in azure devops pipeline

I've a strange problem. I try to restore a .net core application with dotnet restore command in Azure pipeline. One of my package is on my local feed (repo and feed are in same azure devops project).
With classic editor (UI editor) I've no problem but with yaml file restore is unable. I've the error : error NU1301: Unable to load the service index for source
I export yaml from classic editor and copy it in a new yaml pipeline file but build faild also... The configuration of restore task is the same but it doesn't work with yaml.
What is stranger is that the restore task worked friday (with yaml) but fail since yesterday without changes...
I'don't undersand anything... Who would have an idea ?
Thanks
(The agent is an azure agent)
The content of yaml file :
jobs:
- job: Job_1
displayName: Agent job 1
pool:
vmImage: windows-2019
steps:
- checkout: self
fetchDepth: 1
- task: DotNetCoreCLI#2
displayName: "dotnet restore"
inputs:
command: restore
projects: '**\*.sln'
vstsFeed: "afcdef6a-5c72-4a0e-90c5-33d9e751869c/ab1da1d1-3562-4a0a-9781-4f4d80de93ba"
For Classic pipeline, your Build job authorization scope may be Project Scope(Current project)
Classic Pipeline Options
When you use yaml pipeline, the Build job authorization scope is defined by
Project setting->Limit job authorization scope to current project for non-release pipelines
Project Settings
If it is off, the build job authorization scope is Organization Scope (Project Collection)
If it is on, the build job authorization scope is Project Scope (Current project)
You could try to add Project Collection Build Service (OrgName) to Feed setting->Permissions.
Feed settings

.net core 3.1 pack dll with Azure Devops

Im trying to pack a web api i made in .net core 3.1 with Azure Pipeline.
- task: DotNetCoreCLI#2
displayName: Package NuGet
inputs:
command: 'pack'
projects: '**/*.csproj'
arguments: '--configuration $(BuildConfiguration)'
outputDir: '$(Build.ArtifactStagingDirectory)/packages'
Thats the task i used, i found it from another post on stack overflow.
My only issue with that is that it gives a number of .nupkg files, instead of one, and that the web api packages doesn't have the dependencies dll.
Also i created a .nuspec file, but i don't seem to manage to use it correctly with Azure Pipeline
I've tried what's explained here : https://learn.microsoft.com/fr-fr/nuget/reference/msbuild-targets#packing-using-a-nuspec
or just by targeting the .nuspec file like it is explained on the tooltipe of pipeline
If anybody could put me on the right path that would be greatly appreciated :)
EDIT:
I want to pack everything in a nupkg to then deploy it for an IIS site.
This is my nuspec file :
<?xml version="1.0"?>
<package xmlns="http://schemas.microsoft.com/packaging/2010/07/nuspec.xsd">
<metadata>
<id>WebAPI</id>
<version>1.0.0</version>
<authors>Kevin Pinero</authors>
<requireLicenseAcceptance>false</requireLicenseAcceptance>
<description>WebAPI</description>
</metadata>
<files>
<file src=".\bin\Release\*\*.dll" target="lib" />
<file src=".\bin\Release\*\*.exe" target="lib" />
<file src=".\bin\Release\*\*.json" target="lib" />
<!-- <file src=".\bin\Release\*\Properties\*.json" target="lib" /> -->
<file src=".\bin\Release\*\*.pdb" target="lib" />
<file src=".\bin\Release\*\*.config" target="lib" />
</files>
</package>
And this the error i get on the pipeline :
error MSB4068: The element is unrecognized, or not supported
in this context.
Using this task :
- task: DotNetCoreCLI#2
inputs:
command: 'pack'
packagesToPack: '**/*API.nuspec'
nobuild: true
versioningScheme: 'off'
I know on microsoft website I could potentially use this command too
dotnet pack ~/projects/app1/project.csproj -p:NuspecFile=~/projects/app1/project.nuspec -p:NuspecBasePath=~/projects/app1/nuget
But i'm not sure how to translate it in AZ pipeline ...
EDIT Solution adopted:
I've decide to resolve my issues this way :
- task: DotNetCoreCLI#2
displayName: Build at solution level
inputs:
command: 'build'
projects: $(solution)
arguments: '--no-restore --configuration $(buildConfiguration)'
- task: DotNetCoreCLI#2
displayName: Execute tests
inputs:
command: 'test'
projects: $(testProjects)
arguments: '--no-build --configuration $(buildConfiguration)'
- task: DotNetCoreCLI#2
displayName: Pack project
inputs:
command: publish
projects: '**/projectName.csproj'
publishWebProjects: False
arguments: '--no-build --configuration $(BuildConfiguration) --output $(Build.ArtifactStagingDirectory)
zipAfterPublish: False
- task: PublishBuildArtifacts#1
displayName: Publish
inputs:
pathtoPublish: '$(Build.ArtifactStagingDirectory)'
artifactName: 'artefact name'
I would recommend to use the Azure DevOps online pipeline editor. It is great to use and get up to speed (auto-completion, syntaxic review, direct commit/push).
What you try to achieve can be done with the steps:
dotnet build
dotnet pack -> specify the right projects to be packed here
- task: DotNetCoreCLI#2
displayName: 'Create packed NuGet files'
inputs:
command: 'pack'
packagesToPack: '**/*Api.csproj;!**/*Tests.csproj'
versioningScheme: 'off'
nuget push
No need for a nuspec file as long as you add some fields in your csproj.
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<TargetFramework>netstandard2.1</TargetFramework>
<AssemblyName>Withywoods.Selenium</AssemblyName>
<RootNamespace>Withywoods.Selenium</RootNamespace>
<ProjectGuid>{08D9DDB8-BF5B-4E45-8E0C-D9AC85ABF020}</ProjectGuid>
<Authors>devprofr</Authors>
<Description>Library to ease the use of Selenium web driver and provide testing best practices.</Description>
<RepositoryUrl>https://github.com/devpro/withywoods</RepositoryUrl>
<PackageProjectUrl>https://github.com/devpro/withywoods</PackageProjectUrl>
</PropertyGroup>
I have a short example here if you want: pkg.yml
.NET Core and Azure DevOps is a great combination, feel free to comment if you have any issues!
(On my side, I pack library projects but not Api, I do dotnet publish on Api to use them as artifact in release pipelines.)
My only issue with that is that it gives a number of .nupkg files,
instead of one, and that the web api packages doesn't have the
dependencies dll.
I assume you have more than one projects in same solution. Let's call the Web Api project A, other projects B, C and D...
1.So if you only want to pack A into nuget package, instead of using projects: '**/*.csproj', we can use something like projects: '**/A.csproj'. Then it won't pack a number of nuget packages any more.
2.For the dependencies dll, I think you mean the project references like Josh Gust said above. For this, it's still one open issue about dotnet pack command. You can track that issue there to get notifications if there's any update.
For now, we have to make changes to A.csproj to use msbuild magics as workaround. You can try Martin's or zvirja's workarounds there. In my opinion, they both helps for your issue.
Hope all above helps :)
Update1:
For your edit, if you want to translate it in AZ pipeline, you can use the custom command to call the pack. Something like this:
- task: DotNetCoreCLI#2
displayName: 'dotnet custom'
inputs:
command: custom
projects: '**/ProjectName.csproj'
custom: pack
arguments: '-p:NuspecFile=~/projects/app1/project.nuspec -p:NuspecBasePath=~/projects/app1/nuget'
You can check the log to confirm it actually ran the command: "C:\Program Files\dotnet\dotnet.exe" pack D:\a\1\s\xxx\xxx.csproj -p:NuspecFile=~/projects/app1/project.nuspec -p:NuspecBasePath=~/projects/app1/nuget. Hope that's what you need.
And I'm not certainly sure that we can use ~ in that command, but if it works locally, then you can translate it in Azure Devops Pipeline using my way...
UPDATE
Because you are trying to package a Web API project for delivery to IIS, you should stop trying to use nuget as that mechanism, and instead use the dotnet publish command. If you want to continue to use the DotNetCoreCLI#2 task (as opposed to using the script shortcut to call the dotnet cli directly), then I would point you to the documentation to Build, Test and Deploy .Net Core Apps.
This documentation is not written specifically for Web API projects, but is a set of generic guidelines for operating with .Net Core Apps is Azure DevOps Pipelines. An example is quoted below (emphasis mine):
After you've built and tested your app (not web api specifically), you can upload the build output to Azure Pipelines or TFS, create and publish a NuGet package, or package the build output into a .zip file to be deployed to a web application.
When you read in the Package and Deliver your Code section that publish to a NuGet feed is a valid option for delivering code, it is. However this method of delivery should be used for library type deliverables. The dotnet publish command is what is designed to package a web api project and all its dependencies into a .zip (or folder if you specify that option) in preparation for Web Deploy commands against an IIS instance.
Original Answer
Without getting into the details of why you want to create a .nupkg from your API project.
You mention:
My only issue with that is that it gives a number of .nupkg files, instead of one, and that the web api packages doesn't have the dependencies dll
This has been the MO of dotnet pack for a while now as regards project-to-project (P2P) references.
The documentation for dotnet pack states this behavior.
NuGet dependencies of the packed project are added to the .nuspec file, so they're properly resolved when the package is installed. Project-to-project references aren't packaged inside the project. Currently, you must have a package per project if you have project-to-project dependencies.
If you want to have more control over the files that are included in your .nupkg then you will want to author a .nuspec file manually and provide it to the dotnet pack command as indicated in the last Example on the documentation page.
Using the Azure DevOps task for the dotnet core cli DotNetCoreCLI#2 should allow you to simply put the path to the .nuspec file in the input. More information will be necessary in your question if this isn't working for you.

How to use publish profile options from Visual Studio in azure pipelines?

I have an ASP.NET project and I want to implement CI-CD using Azure pipelines, to deploy to custom server (IIS).
Currently, when using Visual Studio(2019) to publish web application manually, I am using these options for publish profile:
<PropertyGroup>
<WebPublishMethod>FileSystem</WebPublishMethod>
<PublishProvider>FileSystem</PublishProvider>
<LastUsedBuildConfiguration>Release</LastUsedBuildConfiguration>
<LastUsedPlatform>Any CPU</LastUsedPlatform>
<SiteUrlToLaunchAfterPublish />
<LaunchSiteAfterPublish>True</LaunchSiteAfterPublish>
<ExcludeApp_Data>True</ExcludeApp_Data>
<publishUrl>C:\Test</publishUrl>
<DeleteExistingFiles>True</DeleteExistingFiles>
<PrecompileBeforePublish>True</PrecompileBeforePublish>
<EnableUpdateable>False</EnableUpdateable>
<DebugSymbols>False</DebugSymbols>
<WDPMergeOption>MergeEachIndividualFolder</WDPMergeOption>
<UseMerge>True</UseMerge>
</PropertyGroup>
The main thing that I want to achieve, is implementing <WDPMergeOption>MergeEachIndividualFolder</WDPMergeOption> when deploying using build and release pipeline.
For release pipeline, I am using IIS Web Deployment.
For build pipeline agent sepcification, I am using vs2017-win2016
For build solution task, I am using latest version of visual stidio
Things I've tried:
1. Passing configuration arguments to msbuild, for Build Solution task in azure build pipeline:
/p:PackageAsSingleFile=true /p:PackageLocation="$(build.artifactstagingdirectory) /p:OutputPath=bin
/p:DeployOnBuild=true /p:WebPublishMethod=FileSystem /p:PrecompileBeforePublish=true
/p:EnableUpdateable=false /p:DebugSymbols=true /p:UseMerge=true /p:DeleteAppCodeCompiledFiles=True
/p:DeleteExistingFiles=True /p:WDPMergeOption=MergeEachIndividualFolder /p:UseFixedNames=true\\"
2. Uploading FolderProfile.pubxml , and passing arguments to msbuild to read from that file
It all builds and releases fine, but doesn't merge assemblies in release, as configured with merge options, it seems like msbuild ignores these additional merge arguments.
How can this be done, the main question is how can I use MergeEachIndividualFolder option when deploying with azure pipeline?
I've also searched a lot, but non of the questions seems to cover the solution.
Azure DevOps Build - publish doesn't create .compiled files in bin folder on publish
MSBuild commandline seems to ignore publish properties
The recommendation from Cece Dong - MSFT worked in my instance of using a publish profile.
Snippet below YML
- task: VSBuild#1
inputs:
solution: 'Path\MySolution.sln'
vsVersion: '16.0'
msbuildArgs: '/p:DeployOnBuild=true /p:PublishProfile=myProfile.pubxml'
configuration: 'Release'
Then in the output the build you can see it having the desired effect:
WebFileSystemPublish:
Creating directory "C:\MyPublishPath".
Copying obj\Release\Package\PackageTmp\File1.ext to C:\MyPublishPath\File1.ext.
Copying obj\Release\Package\PackageTmp\File2.ext to C:\MyPublishPath\File2.ext.
Copying obj\Release\Package\PackageTmp\bin\File3.ext to C:\MyPublishPath\bin\File3.ext.
Copying obj\Release\Package\PackageTmp\bin\File4.ext to C:\MyPublishPath\bin\File4.ext.
... all other files included in the publish

Dotnet build in Azure DevOps with private package source cannot restore from private nuget feed

Our project references packages in our private artifact source in Azure DevOps. When building the project in Azure DevOps the dotnet restore completes fine but dotnet build also tries to restore the packages and fails with
Unable to load the service index for source https://myazdevops.pkgs.visualstudio.com/_packaging/OurPackages/nuget/v3/index.json
The work around is adding --no-restore to both the dotnet build and dotnet publish tasks.
Is there some way to have the build and publish start working without there parameters?
I think your workaround is the solution, in the official docs written:
Starting with .NET Core 2.0 SDK, dotnet restore runs implicitly when
you run dotnet build. If you want to disable implicit restore when
running the build command, you can pass the --no-restore option.
You can't disable this behavior unless you add --no-restore.
See also this question & answer.
I had similar issues with our internal NuGet feed.
I resolved it by adding nuget.config file in repository that contains both NuGet.org and our internal NuGet repository.
<configuration>
<packageSources>
<add key="nuget.org" value="https://api.nuget.org/v3/index.json" />
<add key="internal" value="URL_TO_INTERNAL_FEED" />
</packageSources>
</configuration>
Then just specify in your Restore step Path to NuGet.config to this file.
Hope it will help.
We have opened the source code in Github, you can refer to the code of dotnet build command. This is a compile command, so we did not make script in the task to set the authinfo additionally. Also, as you know, the dotnet restore runs implicitly while the dotnet build running only after .net core 2.0. In fact, this dotnet restore which runs implicitly is not a necessary part if you have been run dotnet restore before the dotnet build. That's why we offered the workaround - add --no-restore - to avoid this implicitly command.
This is a very convenient method which can make your compile process very concise. But if you still don't want this argument, you need do another configuration job to authorized with credential.
Configure the Azure Artifacts Credential Provider, then pass in the credentials with the VSS_NUGET_EXTERNAL_FEED_ENDPOINTS environment variable. VSS_NUGET_EXTERNAL_FEED_ENDPOINTS contain the endpoint credentials for any feed that you need to authenticate against with a JSON Format.

Deploying ASP.net Core 2.0 to Azure

I have upgraded an ASP.net Core 1.1 app to ASP.net Core 2.0 with the following steps:
Changed the Target Framework to 2.0
Upgraded all Nugget Packages
Now my auto deployment from git runs and says it is successful but the app does not run. I get the following error:
HTTP Error 502.5 - Process Failure
I also added a separate web app deployment slot and tried deploying it there and still get the same result. I have also tried deploying it manually to the slow and no change.
The accepted answer did not fix the problem for me.
Steps Required:
Launch Azure Console within the app and delete the contents of the wwwroot folder then redeploy.
RMDIR wwwroot /S /Q
Also, if you have installed the Application Insights Extension within your app. When the app starts you will receive an exception stating that it can't be found.
To fix this error reinstall the Application Insights Extension from the Extensions blade and restart the app.
The problem with the wwwroot folder is that the old Core 1.1 files are not overwritten. Removing the contents of the directory resolves the problem.
I had the same problem, which was caused by files leftover from a previous .NET Core 1.1 deployment. The easiest way to fix this is to check the "Remove additional files at destination" under the File Publish Options in your Publish Settings when publishing to Azure from VS.
I had to add the following to all the .csproj files in the solution
<ItemGroup>
<DotNetCliToolReference Include="Microsoft.VisualStudio.Web.CodeGeneration.Tools" Version="2.0.0" />
</ItemGroup>
This problem also happens when using DevOps Pipeline for the code targeted to dotnet core 2.1. This is because as of today 10/2, Azure is using DotNetCore 3.0 as default runtime (at least that's what it looks to be). To resolve this problem in devops pipeline, you must install the SDK
Yaml Code:
steps:
- task: UseDotNet#2
displayName: 'Install Core 2.1'
inputs:
version: 2.2.104
PS: This tells me that you've to install SDK on destination machine too, for dotnet to compile in correct version. (Azure or Windows Server whichever is your destination)

Resources