Skip to content

Commit 0b9ae80

Browse files
committed
Generating global.json.
1 parent 87b5cef commit 0b9ae80

File tree

7 files changed

+134
-38
lines changed

7 files changed

+134
-38
lines changed

src/PostSharp.Engineering.BuildTools/Build/BaseBuildSettings.cs

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -29,6 +29,10 @@ public BuildConfiguration BuildConfiguration
2929
set => this._resolvedConfiguration = value;
3030
}
3131

32+
[Description( "Overrides the .NET SDK version." )]
33+
[CommandOption( "--sdk-version" )]
34+
public string? SdkVersion { get; init; }
35+
3236
protected override void AppendSettings( StringBuilder stringBuilder )
3337
{
3438
base.AppendSettings( stringBuilder );
@@ -37,6 +41,11 @@ protected override void AppendSettings( StringBuilder stringBuilder )
3741
{
3842
stringBuilder.Append( $"-c {this._resolvedConfiguration} " );
3943
}
44+
45+
if ( !string.IsNullOrEmpty( this.SdkVersion ) )
46+
{
47+
stringBuilder.Append( $"--sdk-version {this.SdkVersion} " );
48+
}
4049
}
4150

4251
public override void Initialize( BuildContext context )
Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
// Copyright (c) SharpCrafters s.r.o. See the LICENSE.md file in the root directory of this repository root for details.
2+
3+
namespace PostSharp.Engineering.BuildTools.Build.Model;
4+
5+
public record GlobalJsonSettings
6+
{
7+
public RollForwardPolicy RollForward { get; init; } = RollForwardPolicy.Patch;
8+
9+
public bool AllowPrerelease { get; init; }
10+
11+
public string Version { get; init; } = "8.0";
12+
}

src/PostSharp.Engineering.BuildTools/Build/Model/Product.cs

Lines changed: 50 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -239,12 +239,24 @@ internal DockerSpec? DockerSpec
239239
public Pattern ConsumableDepsFiles { get; init; } = Pattern.Empty;
240240

241241
/// <summary>
242-
/// Gets or sets a value indicating whether the <c>prepare</c> should generate the <c>nuget.config</c> file.
242+
/// Gets or sets a value indicating whether the <c>prepare</c> command should generate the <c>nuget.config</c> file.
243243
/// </summary>
244244
public bool GenerateNuGetConfig { get; init; }
245245

246+
/// <summary>
247+
/// Gets or sets path patterns (accepting the <c>*</c> character) that
248+
/// match the name of NuGet packages generated by this product. This is used
249+
/// to generate package mapping settings when <see cref="GenerateNuGetConfig"/>
250+
/// is <c>true</c>.
251+
/// </summary>
246252
public string[] OwnPackagePatterns { get; init; } = [];
247253

254+
/// <summary>
255+
/// Gets or sets the content of the <c>global.json</c> file, if it must be generated by the <c>prepare</c> command. If this property is <c>null</c>,
256+
/// the <c>global.json</c> file is not generated.
257+
/// </summary>
258+
public GlobalJsonSettings? GlobalJson { get; init; }
259+
248260
public bool TryGetDependency( string name, [NotNullWhen( true )] out ParametrizedDependency? dependency )
249261
{
250262
dependency = this.ParametrizedDependencies.SingleOrDefault( d => d.Name == name );
@@ -1208,8 +1220,9 @@ public bool PrepareVersionsFile(
12081220
return false;
12091221
}
12101222

1211-
// Generate nuget.config.
1212-
if ( !this.TryGenerateNuGetConfig( context, dependenciesOverrideFile, settings.BuildConfiguration ) )
1223+
// Generate nuget.config and global.json.
1224+
if ( !this.TryGenerateNuGetConfig( context, dependenciesOverrideFile, settings.BuildConfiguration ) ||
1225+
!this.TryGenerateGlobalJson( context, settings.SdkVersion ) )
12131226
{
12141227
return false;
12151228
}
@@ -1390,13 +1403,44 @@ private bool TryComputeVersion(
13901403
return true;
13911404
}
13921405

1406+
internal bool TryGenerateGlobalJson( BuildContext context, string? overrideSdkVersion = null )
1407+
{
1408+
if ( this.GlobalJson == null )
1409+
{
1410+
if ( overrideSdkVersion != null )
1411+
{
1412+
context.Console.WriteError( $"The --sdk-version option was used, but the Product.GlobalJson property is not set." );
1413+
1414+
return false;
1415+
}
1416+
1417+
return true;
1418+
}
1419+
1420+
var globalJson =
1421+
$$"""
1422+
{
1423+
"sdk": {
1424+
"version": "{{overrideSdkVersion ?? this.GlobalJson.Version}}",
1425+
"rollForward": "{{this.GlobalJson.RollForward}}",
1426+
"allowPrerelease": "{{this.GlobalJson.AllowPrerelease}}"
1427+
},
1428+
"msbuild-sdks": {
1429+
"PostSharp.Engineering.Sdk": "{{VersionHelper.EngineeringVersion}}"
1430+
}
1431+
}
1432+
""";
1433+
1434+
TextFileHelper.WriteIfDifferent( Path.Combine( context.RepoDirectory, "global.json" ), globalJson, context );
1435+
}
1436+
13931437
internal bool TryGenerateNuGetConfig( BuildContext context, DependenciesOverrideFile dependenciesOverrideFile, BuildConfiguration configuration )
13941438
{
1395-
if ( !this.GenerateNuGetConfig )
1439+
if ( !this.GenerateNuGetConfig )
13961440
{
13971441
return true;
13981442
}
1399-
1443+
14001444
// Fetch to resolve the VersionFile properties.
14011445
if ( !dependenciesOverrideFile.Fetch( context ) )
14021446
{
@@ -1406,8 +1450,6 @@ internal bool TryGenerateNuGetConfig( BuildContext context, DependenciesOverride
14061450
var baseFilePath = Path.Combine( context.RepoDirectory, "nuget.base.config" );
14071451
var targetFilePath = Path.Combine( context.RepoDirectory, "nuget.config" );
14081452

1409-
context.Console.WriteMessage( $"Writing '{targetFilePath}'." );
1410-
14111453
XDocument document;
14121454
XElement rootElement;
14131455

@@ -1483,7 +1525,7 @@ internal bool TryGenerateNuGetConfig( BuildContext context, DependenciesOverride
14831525
}
14841526
}
14851527

1486-
document.Save( targetFilePath );
1528+
TextFileHelper.WriteIfDifferent( targetFilePath, document.ToString(), context );
14871529

14881530
return true;
14891531

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
// Copyright (c) SharpCrafters s.r.o. See the LICENSE.md file in the root directory of this repository root for details.
2+
3+
namespace PostSharp.Engineering.BuildTools.Build.Model;
4+
5+
public enum RollForwardPolicy
6+
{
7+
Default,
8+
Patch = Default,
9+
Disable,
10+
Feature,
11+
Minor,
12+
Major,
13+
LatestPatch,
14+
LatestFeature,
15+
LatestMinor,
16+
LatestMajor
17+
}

src/PostSharp.Engineering.BuildTools/Dependencies/ConfigureDependenciesCommand.cs

Lines changed: 22 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -15,19 +15,23 @@ public abstract class ConfigureDependenciesCommand<T> : BaseCommand<T>
1515
{
1616
protected override bool ExecuteCore( BuildContext context, T settings )
1717
{
18+
var console = context.Console;
19+
var product = context.Product;
20+
1821
// Validates the command line options.
19-
context.Console.WriteHeading( "Setting the local dependencies" );
2022

21-
if ( context.Product.ParametrizedDependencies is not { Length: > 0 } )
23+
console.WriteHeading( "Setting the local dependencies" );
24+
25+
if ( product.ParametrizedDependencies is not { Length: > 0 } )
2226
{
23-
context.Console.WriteError( "This product has no dependency." );
27+
console.WriteError( "This product has no dependency." );
2428

2529
return false;
2630
}
2731

2832
if ( settings.GetDependencies().Length == 0 && !settings.GetAllFlag() )
2933
{
30-
context.Console.WriteError( "No dependency was specified. Specify a dependency or use --all." );
34+
console.WriteError( "No dependency was specified. Specify a dependency or use --all." );
3135

3236
return false;
3337
}
@@ -50,7 +54,7 @@ protected override bool ExecuteCore( BuildContext context, T settings )
5054
}
5155

5256
// Iterate all matching dependencies.
53-
var dependencies = settings.GetAllFlag() ? context.Product.ParametrizedDependencies.Select( x => x.Name ) : settings.GetDependencies();
57+
var dependencies = settings.GetAllFlag() ? product.ParametrizedDependencies.Select( x => x.Name ) : settings.GetDependencies();
5458

5559
foreach ( var dependencyName in dependencies )
5660
{
@@ -60,22 +64,22 @@ protected override bool ExecuteCore( BuildContext context, T settings )
6064
{
6165
// The dependency was given by position.
6266

63-
if ( index < 1 || index > context.Product.ParametrizedDependencies.Length )
67+
if ( index < 1 || index > product.ParametrizedDependencies.Length )
6468
{
65-
context.Console.WriteError( $"'{index}' is not a valid dependency index. Use the 'dependencies list' command." );
69+
console.WriteError( $"'{index}' is not a valid dependency index. Use the 'dependencies list' command." );
6670

6771
return false;
6872
}
6973

70-
dependency = context.Product.ParametrizedDependencies[index - 1];
74+
dependency = product.ParametrizedDependencies[index - 1];
7175
}
7276
else
7377
{
7478
// The dependency was given by name.
7579

76-
if ( !context.Product.TryGetDependency( dependencyName, out dependency ) )
80+
if ( !product.TryGetDependency( dependencyName, out dependency ) )
7781
{
78-
context.Console.WriteError( $"'{dependencyName}' is not a valid dependency name for this product. Use the 'dependencies list' command." );
82+
console.WriteError( $"'{dependencyName}' is not a valid dependency name for this product. Use the 'dependencies list' command." );
7983

8084
return false;
8185
}
@@ -93,12 +97,12 @@ protected override bool ExecuteCore( BuildContext context, T settings )
9397
.Where( dependency => !defaultDependenciesOverrideFile.Dependencies.ContainsKey( dependency ) )
9498
.ToList() )
9599
{
96-
context.Console.WriteMessage( $"Resetting transitive dependency '{transitiveDependency}'." );
100+
console.WriteMessage( $"Resetting transitive dependency '{transitiveDependency}'." );
97101
dependenciesOverrideFile.Dependencies.Remove( transitiveDependency );
98102
}
99103

100104
// Updating dependencies.
101-
context.Console.WriteImportantMessage( "Updating dependencies" );
105+
console.WriteImportantMessage( "Updating dependencies" );
102106

103107
if ( !DependenciesHelper.UpdateOrFetchDependencies( context, configuration, dependenciesOverrideFile, true ) )
104108
{
@@ -112,19 +116,20 @@ protected override bool ExecuteCore( BuildContext context, T settings )
112116
}
113117

114118
// Writing the configurations neutral file.
115-
context.Product.PrepareConfigurationNeutralVersionsFile( context, settings, configuration );
116-
119+
product.PrepareConfigurationNeutralVersionsFile( context, settings, configuration );
120+
117121
// Generate nuget.config.
118-
if ( !context.Product.TryGenerateNuGetConfig( context, dependenciesOverrideFile, configuration ) )
122+
if ( !product.TryGenerateNuGetConfig( context, dependenciesOverrideFile, configuration ) ||
123+
!product.TryGenerateGlobalJson( context ) )
119124
{
120125
return false;
121126
}
122127

123-
context.Console.WriteLine();
128+
console.WriteLine();
124129

125130
dependenciesOverrideFile.Print( context );
126131

127-
context.Console.WriteSuccess( "Setting dependencies was successful." );
132+
console.WriteSuccess( "Setting dependencies was successful." );
128133

129134
return true;
130135
}

src/PostSharp.Engineering.BuildTools/Utilities/EmbeddedResourceHelper.cs

Lines changed: 2 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -16,7 +16,7 @@ public static void ExtractScript( BuildContext context, string fileName, string
1616
var replacements = new Dictionary<string, string>();
1717
replacements.Add( "<ENG_PATH>", product.EngineeringDirectory );
1818
replacements.Add( "<ENVIRONMENT_VARIABLES>", string.Join( ",", EnvironmentVariableNames.All.OrderBy( x => x ) ) );
19-
19+
2020
ExtractResource( context, fileName, targetDirectory, replacements );
2121
}
2222

@@ -42,17 +42,6 @@ public static void ExtractResource(
4242
}
4343
}
4444

45-
if ( !File.Exists( targetPath ) || File.ReadAllText( targetPath ) != text )
46-
{
47-
context.Console.WriteMessage( $"Writing '{targetPath}'." );
48-
49-
File.WriteAllText( targetPath, text );
50-
}
51-
52-
else
53-
54-
{
55-
context.Console.WriteMessage( $"File '{targetPath}' is up to date." );
56-
}
45+
TextFileHelper.WriteIfDifferent( targetPath, text, context );
5746
}
5847
}
Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
// Copyright (c) SharpCrafters s.r.o. See the LICENSE.md file in the root directory of this repository root for details.
2+
3+
using PostSharp.Engineering.BuildTools.Build;
4+
using System.IO;
5+
6+
namespace PostSharp.Engineering.BuildTools.Utilities;
7+
8+
internal static class TextFileHelper
9+
{
10+
public static void WriteIfDifferent( string path, string content, BuildContext context )
11+
{
12+
if ( File.Exists( path ) && content == File.ReadAllText( path ) )
13+
{
14+
context.Console.WriteMessage( $"The file '{path}' is up to date." );
15+
}
16+
else
17+
{
18+
context.Console.WriteMessage( $"Writing '{path}'." );
19+
File.WriteAllText( path, content );
20+
}
21+
}
22+
}

0 commit comments

Comments
 (0)