Skip to content

Commit b210484

Browse files
author
William Li
committed
Generate target platform assembly attributes
1 parent ee99bb9 commit b210484

File tree

2 files changed

+196
-0
lines changed

2 files changed

+196
-0
lines changed

src/Tasks/Microsoft.NET.Build.Tasks/targets/Microsoft.NET.GenerateAssemblyInfo.targets

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -109,6 +109,13 @@ Copyright (c) .NET Foundation. All rights reserved.
109109
<_Parameter2>%(AssemblyMetadata.Value)</_Parameter2>
110110
</AssemblyAttribute>
111111
</ItemGroup>
112+
113+
<ItemGroup Condition="'$(TargetPlatformIdentifier)' != '' and '$(OSMinimumVersion)' != ''">
114+
<AssemblyAttribute Include="System.Runtime.Versioning.AddedInOSPlatformVersionAttribute">
115+
<_Parameter1>$(TargetPlatformIdentifier)</_Parameter1>
116+
<_Parameter2>$(OSMinimumVersion)</_Parameter2>
117+
</AssemblyAttribute>
118+
</ItemGroup>
112119
</Target>
113120

114121
<!--
Lines changed: 189 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,189 @@
1+
// Copyright (c) .NET Foundation and contributors. All rights reserved.
2+
// Licensed under the MIT license. See LICENSE file in the project root for full license information.
3+
4+
using System.IO;
5+
using Microsoft.NET.TestFramework;
6+
using Microsoft.NET.TestFramework.Assertions;
7+
using Microsoft.NET.TestFramework.Commands;
8+
using Xunit;
9+
using FluentAssertions;
10+
using Xunit.Abstractions;
11+
using Microsoft.NET.TestFramework.ProjectConstruction;
12+
13+
namespace Microsoft.NET.Build.Tests
14+
{
15+
public class GivenThatWeWantToBuildALibraryWithOSMinimumVersion : SdkTest
16+
{
17+
public GivenThatWeWantToBuildALibraryWithOSMinimumVersion(ITestOutputHelper log) : base(log)
18+
{
19+
}
20+
21+
[Fact]
22+
public void WhenPropertiesAreNotSetItShouldNotGenerateAddedInOSPlatformVersionAttribute()
23+
{
24+
TestProject testProject = new TestProject()
25+
{
26+
Name = "Project",
27+
IsSdkProject = true,
28+
IsExe = true,
29+
TargetFrameworks = "net5.0",
30+
};
31+
32+
testProject.SourceFiles[$"AttributeIsNotDefinedYetWorkaround.cs"] = _attributeIsNotDefinedYetWorkaround;
33+
testProject.SourceFiles[$"PrintAttribute.cs"] = _printAttribute;
34+
35+
var testAsset = _testAssetsManager.CreateTestProject(testProject);
36+
37+
var runCommand = new DotnetCommand(Log, "run");
38+
runCommand.WorkingDirectory = Path.Combine(testAsset.TestRoot, testProject.Name);
39+
runCommand.Execute()
40+
.Should()
41+
.Pass().And.HaveStdOutContaining("NO ATTRIBUTE");
42+
}
43+
44+
[Fact]
45+
public void WhenPropertiesAreSetItCanGenerateAddedInOSPlatformVersionAttribute()
46+
{
47+
TestProject testProject = new TestProject()
48+
{
49+
Name = "Project",
50+
IsSdkProject = true,
51+
IsExe = true,
52+
TargetFrameworks = "net5.0",
53+
};
54+
55+
var targetPlatformIdentifier = "iOS";
56+
testProject.AdditionalProperties["TargetPlatformIdentifier"] = targetPlatformIdentifier;
57+
testProject.AdditionalProperties["OSMinimumVersion"] = "14.0.0.0";
58+
59+
testProject.SourceFiles[$"AttributeIsNotDefinedYetWorkaround.cs"] = _attributeIsNotDefinedYetWorkaround;
60+
testProject.SourceFiles[$"PrintAttribute.cs"] = _printAttribute;
61+
62+
var testAsset = _testAssetsManager.CreateTestProject(testProject);
63+
64+
var runCommand = new DotnetCommand(Log, "run");
65+
runCommand.WorkingDirectory = Path.Combine(testAsset.TestRoot, testProject.Name);
66+
runCommand.Execute()
67+
.Should()
68+
.Pass().And.HaveStdOutContaining($"PlatformIdentifier:{targetPlatformIdentifier};Major:14;Minor:0;Build:0;Revision:0;");
69+
}
70+
71+
private static readonly string _printAttribute = @"
72+
using System;
73+
using System.Runtime.Versioning;
74+
75+
namespace CustomAttributesTestApp
76+
{
77+
internal static class CustomAttributesTestApp
78+
{
79+
public static void Main()
80+
{
81+
var assembly = typeof(CustomAttributesTestApp).Assembly;
82+
object[] attributes = assembly.GetCustomAttributes(typeof(AddedInOSPlatformVersionAttribute), false);
83+
if (attributes.Length > 0)
84+
{
85+
var attribute = attributes[0] as AddedInOSPlatformVersionAttribute;
86+
Console.WriteLine($""PlatformIdentifier:{attribute.PlatformIdentifier};Major:{attribute.Major};Minor:{attribute.Minor};Build:{attribute.Build};Revision:{attribute.Revision};"");
87+
}
88+
else
89+
{
90+
Console.WriteLine(""NO ATTRIBUTE"");
91+
}
92+
}
93+
}
94+
}
95+
";
96+
97+
private static readonly string _attributeIsNotDefinedYetWorkaround = @"
98+
using System;
99+
100+
namespace System.Runtime.Versioning
101+
{
102+
public abstract class OSPlatformVersionAttribute : Attribute
103+
{
104+
protected OSPlatformVersionAttribute(string osPlatform,
105+
int major,
106+
int minor,
107+
int build,
108+
int revision)
109+
{ }
110+
111+
protected OSPlatformVersionAttribute(string osPlatform,
112+
string version)
113+
{
114+
var parsedVersion = Version.Parse(version);
115+
PlatformIdentifier = osPlatform;
116+
Major = parsedVersion.Major;
117+
Minor = parsedVersion.Minor;
118+
Build = parsedVersion.Build;
119+
Revision = parsedVersion.Revision;
120+
}
121+
public string PlatformIdentifier { get; }
122+
public int Major { get; }
123+
public int Minor { get; }
124+
public int Build { get; }
125+
public int Revision { get; }
126+
}
127+
128+
[AttributeUsage(AttributeTargets.Assembly |
129+
AttributeTargets.Class |
130+
AttributeTargets.Constructor |
131+
AttributeTargets.Event |
132+
AttributeTargets.Method |
133+
AttributeTargets.Module |
134+
AttributeTargets.Property |
135+
AttributeTargets.Struct,
136+
AllowMultiple=false, Inherited=true)]
137+
public sealed class AddedInOSPlatformVersionAttribute : OSPlatformVersionAttribute
138+
{
139+
public AddedInOSPlatformVersionAttribute(string osPlatform,
140+
int major,
141+
int minor,
142+
int build,
143+
int revision) : base(osPlatform, major, minor, build, revision) { }
144+
145+
public AddedInOSPlatformVersionAttribute(string osPlatform,
146+
string version) : base(osPlatform, version) { }
147+
148+
}
149+
150+
[AttributeUsage(AttributeTargets.Assembly |
151+
AttributeTargets.Class |
152+
AttributeTargets.Constructor |
153+
AttributeTargets.Event |
154+
AttributeTargets.Method |
155+
AttributeTargets.Module |
156+
AttributeTargets.Property |
157+
AttributeTargets.Struct,
158+
AllowMultiple=false, Inherited=true)]
159+
public sealed class RemovedInOSPlatformVersionAttribute : OSPlatformVersionAttribute
160+
{
161+
public RemovedInOSPlatformVersionAttribute (string osPlatform,
162+
int major,
163+
int minor,
164+
int build,
165+
int revision) : base(osPlatform, major, minor, build, revision) { }
166+
}
167+
168+
[AttributeUsage(AttributeTargets.Assembly |
169+
AttributeTargets.Class |
170+
AttributeTargets.Constructor |
171+
AttributeTargets.Event |
172+
AttributeTargets.Method |
173+
AttributeTargets.Module |
174+
AttributeTargets.Property |
175+
AttributeTargets.Struct,
176+
AllowMultiple=false, Inherited=true)]
177+
public sealed class ObsoletedInOSPlatformVersionAttribute : OSPlatformVersionAttribute
178+
{
179+
public ObsoletedInOSPlatformVersionAttribute (string osPlatform,
180+
int major,
181+
int minor,
182+
int build,
183+
int revision) : base(osPlatform, major, minor, build, revision) { }
184+
public string Url { get; set; }
185+
}
186+
}
187+
";
188+
}
189+
}

0 commit comments

Comments
 (0)