Skip to content

dotnet nbgv set-version modifies root version.json when executed in inherited version.json context #1257

@julealgon

Description

@julealgon

Problem

In a parent-child version.json structure, when running nbgv set-version X, it always updates the parent version.json file even when executed in the context of the child version.json one.

This not only causes values to be updated in the wrong place (messing the root file), but it also causes future commands to crash because it incorrectly sets inherited: true on the base file, causing the following exception on subsequent commands (such as nbgv get-version):

dotnet nbgv get-version
Unhandled exception: System.InvalidOperationException: "C:\git\affinitiv\dotnet-extensions\version.json" inherits from a parent directory version.json file but none exists.
   at Nerdbank.GitVersioning.VersionFile.GetWorkingCopyVersion(String startingDirectory, String& actualDirectory) in D:\a\1\s\src\NerdBank.GitVersioning\VersionFile.cs:line 228

Context

I have a requirement to manually set the version of my project in Github actions. This project is one of many in a monorepo where there is a root version.json file with basic settings such as publicReleaseRefSpec and cloudBuild settings, and separate inherited version.json files per "component" folder, where I store the version of each component in the repo.

My structure is like this:

├── version.json
├── src/
     ├── Component1/
     │      └── version.json
     └── Component2/
            └── version.json
      ...

The issue occurs no matter how I provide the component folder context:

  • If I navigate to src/Component1, then run nbgv set-version X
  • If nbgv set-version X --project src/Component1 directly in the root

Technical Details

I grabbed the repo to debug the issue to understand what was going on.

Because the config exists, it always lands on the first if block here and persists the settings to actualDirectory, which always seems to return the base file path no matter how the action is called:

VersionOptions existingOptions = context.VersionFile.GetVersion(out string actualDirectory);
string versionJsonPath;
if (existingOptions is not null)
{
existingOptions.Version = semver;
versionJsonPath = context.VersionFile.SetVersion(actualDirectory, existingOptions);
}
else if (string.IsNullOrEmpty(project))
{
if (!context.IsRepository)
{
Console.Error.WriteLine("No version file and no git repo found at or above: \"{0}\"", searchPath);
return Task.FromResult((int)ExitCodes.NoGitRepo);
}
versionJsonPath = context.VersionFile.SetVersion(context.WorkingTreePath, defaultOptions);
}
else
{
versionJsonPath = context.VersionFile.SetVersion(project, defaultOptions);
}

Image

Workaround

The only thing that comes to mind right now is to just avoid using inherited version.json files and replicate the common configuration across all component-specific version.json, which is obviously less than ideal considering the main purpose of the shared root file today is to avoid the duplication of settings.

Metadata

Metadata

Assignees

Labels

Type

No type

Projects

No projects

Milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions