Where is the nuget executable for dotnet core - .net-core

Where does dotnet core look for a nuget executable when running restore commands?
Is there a separate executable, or are the nuget functions built directly into the cli tools?
If I already have a nuget executable on my path, can dotnet be configured to use this?

NuGet is no longer an executable that runs for a restore operation, it has become an integrated part of the build tooling and the dotnet CLI.
NuGet operations have been turned into MSBuild tasks which are run during a build. This task would then load some NuGet libraries as needed. There are other tasks that use some NuGet components as well - such as the Pack target or some tasks used to determine framework compatibility (because NuGet knows which net* / netcoreapp* / netstandard* "frameworks" are compatible with another).
The dotnet CLI also uses some library functions of NuGet to execute commands such as dotnet add package or the dotnet nuget commands.
So instead of a single nuget.exe, you will find some NuGet related DLL files inside the SDK's directory and various components used during the build or command line operations will use functionality of these.
This also means that you can't easily replace them with any nuget.exe you have on your PATH.

Related

How to pack .NET Core projects recursively without running pack on the entire solution?

I have a solution of a hundred plus .NET Core projects. Not all of them needs to be packed, but only those which are transitive dependencies of a few special projects.
However, when I run dotnet pack it attempts to pack all kinds of projects that it should not and there are errors here and there. I would like instead to run pack on the special projects only in a recursive fashion, so that only them and their transitive dependencies (project references, of course) are packed.
I figured I can implement it by scripting around the dotnet list reference command, but it does not sound right. There must be a better way to do it.
EDIT 1
The solution must work on the command line where we have dotnet and msbuild and possibly nuget, but no VS IDE.
You can modify your project settings to generate *.nupkg file during dotnet build, without explicit dotnet pack call. And as soon as dependencies get builded automatically when "parent" project builds - you will receive nuget packages prepared for all dependencies too when you run dotnet build for "parent" project only.
For each project that should produce nuget package add this lines into csproj file:
<PropertyGroup>
<GeneratePackageOnBuild>true</GeneratePackageOnBuild>
</PropertyGroup>
Or, instead, you may enable checkbox "Generate NuGet package on build" from Visual Studio, in project properties ("Package" tab) - this will add same line into project file.

Restoring NuGet packages to the cache

I have a .net-core application that works on my machine but when I deploy it on another one, it complains about missing packages and points me to the TheApp.deps.json.
My theory is that on my machine the app looks for packages in some NuGet cache where they were probably installed by the IDE during development because the app's output-dir contains only a couple of internal dlls so the other nuget.org dependecies are definitely missing.
I'm building the app with
<PropertyGroup>
<OutputType>Exe</OutputType>
<TargetFramework>netcoreapp2.2</TargetFramework>
<RuntimeIdentifier>win10-x64</RuntimeIdentifier>
</PropertyGroup>
and then xcopy it to the other machine.
Question
Is there a way to restore or install the missing packages to the cache on the target machine based on the *.deps.json file?
dotnet build (and the F5/Build function in Visual Studio) simply build the code that you have provided via your source files (i.e cs, fs, vb, etc.).
Whereas dotnet publish (and the Build > Publish function in Visual Studio) does a full package restore, builds your source code, and resolves any external dependencies before moving the output to a specific directory ready for publishing to another machine.
The description on the dotnet publish command documentation states:
dotnet publish compiles the application, reads through its dependencies specified in the project file, and publishes the resulting set of files to a directory. The output includes the following assets:
Intermediate Language (IL) code in an assembly with a dll extension.
.deps.json file that includes all of the dependencies of the project.
.runtime.config.json file that specifies the shared runtime that the application expects, as well as other configuration options for the runtime (for example, garbage collection type).
The application's dependencies, which are copied from the NuGet cache into the output folder.
dotnet build is only really useful for building on your development machine, and when used in conjunction with dotnet run against a project file.

dotnet publish sln having projects with multiple target frameworks fails

I have a solution with many projects. Some target frameworknetcoreapp2.1, some other target framework netstandard2.0 and one project has a double target framework
<TargetFrameworks>netstandard2.0;net471</TargetFrameworks>
I'd want to have a artifact for win10 with a single command:
dotnet publish MySolution.sln -c Release -o "targetFolder" -r win10-x64
With this command I have this error while building the project with double target framework. Here's the errors:
C:\Program Files\dotnet\sdk\2.1.402\Sdks\Microsoft.NET.Sdk\targets\Microsoft.NET.Sdk.CrossTargeting.targets(31,5) error : The 'Publish' target is not supported without specifying a target framework. The current project targets multiple frameworks, please specify the framework for the published application.
The error is clear. At the end I find that dll compiled in the output directory and it seems like it is a netstandard2.0 dll because my application still works.
I don't like dirty things so, how can I solve my problem?
I would avoid to call N times the "dotnet publish" command if possible.
Don't use dotnet publish with the same output directory on a solution. Especially not with the "-r" argument.
It is dangerous because:
libraries don't have the right trimming behaviour for netstandard facade packages
libraries may have odd behaviour when publishing with "-r", especially for netstandard<2.0 dependencies. (they'd end up copying the .NET Core 1.0/1.1 implementation(!) assemblies)
you may end up with different NuGet dependencies in the output (transitive dependencies)
Copy-to-output/publish-directory items may end up overwriting each other, it may even lead to build failures
Call it individually for all application (console app, web app) projects or create an MSBuild file that publishes these applications.

VSTS - Asp.Net Build with Project Dependencies and Git Repositories

Since VSTS has sought to bend to the popular Git source control, I have yet to see a good description of building .Net projects located in Git repositories, having project dependencies on one another.
For instance, in Visual Studio, I build a solution that includes projects with dependencies on each other. Then, in VSTS each of those .Net projects are versioned in separate Git repositories.
How, then, do you get a build on VSTS? How do you get the artifacts (read: DLLs) from one project into the project of the other?
UPDATE: 12/18/17
I took #VonC's suggestion and followed-through on a VSTS (Visual Studio Team Services) hosted Nuget package. I was able to make this work. This process makes .Net solution files and project dependencies OBSOLETE.
If you want to reuse a library, you can save the binaries as a NuGet package.
In the downstream project, you simply assign the VSTS url reference to the Nuget package to get the Nuget Restore to find/place the binaries in your build project.
You will have to download and install a Credentials tool that will allow you to push your binaries to VSTS's package location. Additionally, tell your admin to add the Packages functionality from the VSTS Marketplace.
Thanks, #VonC for the great suggestion!
Here are some helpful links:
Create and Publish the Private Nuget Package here
VSTS Marketplace Package Manager here
The idea is, for binary dependencies (DLLs) to not involve a source control tool (like Git) but a binary referential one (like Nuget)
See for instance:
"Package: NuGet"
"NuGet is now fully integrated into MSBuild"
With Visual Studio 2017 and .NET Core, we have improved the NuGet package management experience by introducing the PackageReference feature in MSBuild.
PackageReference brings new and improved capabilities such as deep MSBuild integration, improved performance for everyday tasks such as install and restore, multi-targeting and more.
First, it’s unnecessary to manage the build artifacts (such as dlls) in source control since they're the output files from the source code.
Then to add dependencies (dlls) from other repos to the parent (main) repo’s project, there usually has below options:
Option 1: manage the build artifacts as packages
As Vonc mentioned, you can manage the dlls as nuget packages, and then add nuget packages to your main repo’s project.
Option 2: git submodules
You can also treat other repos as the submodules for the main repo, and both build the projects from the submodules repos and the main repo in the build, then the main repo project can get the dependencies from the submodule repos’ build artifacts.
Commands to add a submodule for the main repo:
# In local main repo
git submodule add <URL for a submodule repo>
git commit -m 'add a submodule'
git push
Note: in VSTS build definition, you should select checkout submodules in Get Sources step.
Details about git submodules, you can refer Submodules.
Option 3: git subree (alternative way for git submodules)
Treat a branch from another repo as a subtree (a folder) in the main repo. Then build the projects both in the main repo and the subtrees, and get dependencies from subtrees for the main repo’s project.
Commands to add a subtree in the main repo:
git submodule add --prefix=submodule1 <URL for sub repo> master
git push
Then it will add a folder submodule1 with the files in the sub repo master branch, and commit the changes in the main repo.
Details about git subtree, you can refer
Git subtree: the alternative to Git submodule.
At any time, if your branch has working code with any version of dependent assemblies, I can't see any reason you need to do anything.
For example of dependencies here:
You can set dependencies in project like:
Also you can add dependencies in solution like :
You can set build order in solution too if your project has multiple project with dependencies.
As long as your current code in branch from which you are build is working (with any version of different assemblies, e.g. Classlibrary1 has version 1.0.0.0, Classlibrary2 has version 1.2.2.1 & so on but is working fine with each other after referencing) this approach will work.
Project dependencies exist for ages in Visual Studio & .Net. As long those project exist in same TFS branch You can add project dependency right in dependent project. Also you can manage Project build order in Solution.
For more complex scenarios like different repositories or branch dependencies you need to modify build workflow but it is also quite possible.
You can also refer
http://dailydotnettips.com/2015/11/25/how-to-identify-the-project-dependencies-in-visual-studio/
what I saw long time ago when I created same sample for test.

Where is the default output folder for dotnet restore?

I tried to create a simple .net core using commandline
dotnew new
in a certain folder called netcoreExample and I could see that there are two files created which are program.cs and project.json. Then I add Microsoft.EntityFrameworkCore to dependencies entry in project.json
When I try to run the command
dotnet restore
it shows the package is restores successfully. However, when I inspect the folder where I run dotnet restore from, I didn't see the "packages" folder which is usually created when with the old C# projects running Nuget restore.
I wonder where the dotnet restore output all of the dependencies to.
On Windows by default its %userprofile%\.nuget\packages. I wish dotnet restore -verbosity <verbosity-level> printed out where it was restoring to.
On other OSes its like <HOME-environment-variable-location>/.nuget/packages

Resources