Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

dotnet pack doesn't choose the right version for ProjectReferences #6209

Closed
livarcocc opened this issue Nov 21, 2017 · 12 comments
Closed

dotnet pack doesn't choose the right version for ProjectReferences #6209

livarcocc opened this issue Nov 21, 2017 · 12 comments

Comments

@livarcocc
Copy link

From @MangelMaxime on November 21, 2017 13:0

Hello, I have a problem with dotnet pack command and ProjectReferences resolve version. It was working on dotnet 2.0.0

cc @forki

Steps to reproduce

Repo used: /~https://github.com/MangelMaxime/Fulma

  • git clone git@github.com:MangelMaxime/Fulma.git
  • git checkout repro_nuspec_bug
  • .\build.cmd
  • cd src
  • cd Fulma.Extensions
  • dotnet pack -c Release /p:Version=0.1.0-beta-007 /p:PackageReleaseNotes="* DOT NOT PUBLISH THIS VERSION IS A TEST FOR NUSPEC BUG REPRODUCTION"

Expected behavior

In the nuspec file:
<dependency id="Fulma" version="1.0.0-beta-005" exclude="Build,Analyzers" />

Actual behavior

In the nuspec file:
<dependency id="Fulma" version="0.1.0-beta-007" exclude="Build,Analyzers" />

Environment data

dotnet --info output:

Machine 1:

Outils en ligne de commande .NET (2.0.2)

Product Information:
 Version:            2.0.2
 Commit SHA-1 hash:  a04b4bf512

Runtime Environment:
 OS Name:     Windows
 OS Version:  10.0.15063
 OS Platform: Windows
 RID:         win10-x64
 Base Path:   C:\Program Files\dotnet\sdk\2.0.2\

Microsoft .NET Core Shared Framework Host

  Version  : 2.0.0
  Build    : e8b8861ac7faf042c87a5c2f9f2d04c98b69f28d

Machine 2:

.NET-Befehlszeilentools (2.0.3)

Product Information:
Version: 2.0.3
Commit SHA-1 hash: 12f0c7efcc

Runtime Environment:
OS Name: Windows
OS Version: 10.0.10586
OS Platform: Windows
RID: win10-x64
Base Path: C:\Program Files\dotnet\sdk\2.0.3\

Microsoft .NET Core Shared Framework Host

Version : 2.0.3
Build : a9190d4a75f4a982ae4b4fa8d1a24526566c69df

This is also failing on my computer under Linux. I don't have access to it ATM.

Edit: Add the repo url

Copied from original issue: dotnet/cli#8073

@emgarten
Copy link
Member

Passing /p:Version=0.1.0-beta-007 applies the property globally to MSBuild and all projects read. dotnet pack is calling restore and build implicitly, and during those commands MSBuild is reporting the version of Fulma as 0.1.0-beta-007, the global value.

This is a common scenario that we are looking to improve for pack, it is confusing that these properties impact dependency projects in scenarios like this.

The workaround for this is to set the version of the project using a property that is unique to that project, that will keep dependency projects from using the same version.

Example:

<PropertyGroup>
  <Version Condition=" '$(ProjectAVersion)' != '' ">$(ProjectAVersion)</Version>
</PropertyGroup>

@MangelMaxime
Copy link

@emgarten Hum, I am not sure to understand if I need to had this PropertyGroup to all my fsproj. And should I keep using calling dotnet pack with /p:Version=0.1.0-beta-007 ?

Also what confused me is that it was working before with dotnet 2.0.0 for example.

@emgarten
Copy link
Member

if I need to had this PropertyGroup to all my fsproj

No, this property group would be specific to a single project. Think hardcoding the right value into that specific fsproj and leaving the others unchanged. You want a property that only overrides a single fsproj's version property.

Also what confused me is that it was working before with dotnet 2.0.0 for example.

This should be all basic MSBuild that is setting and reading the property. Possibly if something else in your build changed how restore is called to make it skip the restore for the fulma this could happen.

//cc @rohit21agrawal for pack

@dasMulli
Copy link

Also what confused me is that it was working before with dotnet 2.0.0 for example.

Because before 2.0.0, the CLI did not perform an implicit restore. You should get the same behavior by passing --no-restore to dotnet pack. Since dependency versions are set during restore, they will not be affected (as long as there was any other implicitly restoring command or dotnet restore run before without a global version property set).
However, there is an ongoing ask (and probably plan?) to re-evaluate referenced projects during pack which would cause your issue again.

Another workaround would be to explicitly set the version property in the reference project and tell msbuild to take the local property over the global one:

So Fulma.fsproj could be changed to

<Project Sdk="Microsoft.NET.Sdk" TreatAsLocalProperty="Version">

However this also means that you can no longer use /p:Version=… on Fulma.csproj directly.

@MangelMaxime
Copy link

I didn't really understand all this change related to fsproj. Like I don't know how to set $(ProjectAVersion) value for example.

From your answers, I understand that's the problems is coming from /p:Version argument as it's a "global version". So I decided to remove it, and instead of updating the version in my fsproj after a successful push. I decided to update them before packaging and pushing.

Old build.fsx:

  1. dotnet pack with /p:Version
  2. dotnet nuget push
  3. Update the version in the fsproj

New build.fsx

  1. Update the version in the fsproj
  2. dotnet pack without /p:Version
  3. dotnet nuget push

This seems to be working, I just don't know if there will be any draws back.

Thanks for your answers.

@dasMulli
Copy link

dasMulli commented Nov 22, 2017

Like I don't know how to set $(ProjectAVersion) value for example.

The idea is that you change for instance Fulma.fsproj to

<Version>1.0.0-beta-005</Version>
<Version Condition="'$(FulmaVersion)' != ''">$(FulmaVersion)</Version>

and Fulma.Extensions.fsproj to

<Version>1.0.0-beta-007</Version>
<Version Condition="'$(FulmaExtensionsVersion)'' != ''">$(FulmaExtensionsVersion)</Version>

this will allow you to build from any command on any project safely by calling dotnet pack /p:FulmaVersion=1.2.3 /p:FulmaExtensionsVersion=4.5.6 (you could run this even on a solution file). You could even set those two properties as environment variables in the build script and the projects will respect them for any build or restore related command.

@dasMulli
Copy link

dasMulli commented Nov 22, 2017

Btw I was about to suggest adding UndefineProperties="Version" to the ProjectReference item which is honoured by msbuild but it seems like NuGet doesn't respect this metadata during its walk - is this intentional? ( @emgarten @rohit21agrawal maybe? )

EDIT: changed to UndefineProperties instead of GlobalPropertiesToRemove since I got the wrong metadata. same effect though, the actual build doesn't forward the global property but the restore project walk does.

@MangelMaxime
Copy link

@dasMulli Thanks for the clarification.

@jainaashish
Copy link

It should be fixed with another PR to choose the right version for project references. It will be available as part of Visual Studio 2017 15.6 preview3 release.

@MirzaMerdovic
Copy link

MirzaMerdovic commented Jan 17, 2019

This is still an issue. This package: ProjectReferences.Common.Services -Version 1.0.2 was packed using:
dotnet pack -c Configuration --no-restore -p:Version=1.0.2

and it behaves as described by the reporter.

The solution structure can be reviewed in this repo

Note: Behavior is the same if the target framework is netstandard2.0

Since the workaround that was suggested by @dasMulli doesn't really suite my need, the only thing that's left is to use Nuget references instead of project references although the projects are the part of the same solution.

Is anyone aware for a solution/different workaround so that the version is only appended to the project that is being published?

@MirzaMerdovic
Copy link

Hack-around I am using currently is:

  <ItemGroup Condition="$(Configuration) == Debug">
    <ProjectReference Include="..\Common\Common.Service.csproj" />
  </ItemGroup>
  
  <ItemGroup Condition="$(Configuration) != Debug">
    <PackageReference Include="ProjectReferences.Common.Services" Version="1.*" />
  </ItemGroup>

I haven't figured out the reason why in this case Version="1.*" is not getting overridden, because if I try this:

<ItemGroup>
    <PackageReference Include="ProjectReferences.Common.Services" Version="1.*" />
</ItemGroup>

Common.Services package version would be overridden by what ever is specified in dotnet pack -p:Version, or in the current project Version tag (e.g. <Version>1.0.32</Version>).

Note:

Once you upgrade the major version the "1.*" will not work so you will need to update the constraint to "2.*" or whatever the new major version is. I had to use this pattern since 1* is not supported yet

@M3LiNdRu
Copy link

Any update on this? Does anyone know if Microsoft is going to release a change?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

8 participants