Skip to content

Commit 09aa370

Browse files
authored
Add LocalPath property to RuntimeFile and ResourceAssembly for writing/reading deps.json (#118034)
- Add `LocalPath` property and constructors taking a local path to `RuntimeFile` and `ResourceAssembly` - Update JSON serialization/deserialization to handle the new property
1 parent c58b659 commit 09aa370

File tree

8 files changed

+351
-210
lines changed

8 files changed

+351
-210
lines changed

src/libraries/Microsoft.Extensions.DependencyModel/ref/Microsoft.Extensions.DependencyModel.cs

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -127,8 +127,10 @@ public Library(string type, string name, string version, string? hash, System.Co
127127
public partial class ResourceAssembly
128128
{
129129
public ResourceAssembly(string path, string locale) { }
130+
public ResourceAssembly(string path, string locale, string? localPath) { }
130131
public string Locale { get { throw null; } set { } }
131132
public string Path { get { throw null; } set { } }
133+
public string? LocalPath { get { throw null; } }
132134
}
133135
public partial class RuntimeAssembly
134136
{
@@ -156,9 +158,11 @@ public RuntimeFallbacks(string runtime, params string?[] fallbacks) { }
156158
public partial class RuntimeFile
157159
{
158160
public RuntimeFile(string path, string? assemblyVersion, string? fileVersion) { }
161+
public RuntimeFile(string path, string? assemblyVersion, string? fileVersion, string? localPath) { }
159162
public string? AssemblyVersion { get { throw null; } }
160163
public string? FileVersion { get { throw null; } }
161164
public string Path { get { throw null; } }
165+
public string? LocalPath { get { throw null; } }
162166
}
163167
public partial class RuntimeLibrary : Microsoft.Extensions.DependencyModel.Library
164168
{

src/libraries/Microsoft.Extensions.DependencyModel/src/DependencyContextJsonReader.cs

Lines changed: 18 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -507,6 +507,7 @@ private static List<RuntimeFile> ReadRuntimeFiles(ref Utf8JsonReader reader)
507507
{
508508
string? assemblyVersion = null;
509509
string? fileVersion = null;
510+
string? localPath = null;
510511

511512
string? path = reader.GetString();
512513

@@ -527,12 +528,15 @@ private static List<RuntimeFile> ReadRuntimeFiles(ref Utf8JsonReader reader)
527528
case DependencyContextStrings.FileVersionPropertyName:
528529
fileVersion = propertyValue;
529530
break;
531+
case DependencyContextStrings.LocalPathPropertyName:
532+
localPath = propertyValue;
533+
break;
530534
}
531535
}
532536

533537
reader.CheckEndObject();
534538

535-
runtimeFiles.Add(new RuntimeFile(path, assemblyVersion, fileVersion));
539+
runtimeFiles.Add(new RuntimeFile(path, assemblyVersion, fileVersion, localPath));
536540
}
537541

538542
reader.CheckEndObject();
@@ -578,6 +582,9 @@ private List<RuntimeTargetEntryStub> ReadTargetLibraryRuntimeTargets(ref Utf8Jso
578582
case DependencyContextStrings.FileVersionPropertyName:
579583
runtimeTarget.FileVersion = propertyValue;
580584
break;
585+
case DependencyContextStrings.LocalPathPropertyName:
586+
runtimeTarget.LocalPath = propertyValue;
587+
break;
581588
}
582589
}
583590

@@ -607,6 +614,7 @@ private List<ResourceAssembly> ReadTargetLibraryResources(ref Utf8JsonReader rea
607614
}
608615

609616
string? locale = null;
617+
string? localPath = null;
610618

611619
reader.ReadStartObject();
612620

@@ -616,13 +624,17 @@ private List<ResourceAssembly> ReadTargetLibraryResources(ref Utf8JsonReader rea
616624
{
617625
locale = propertyValue;
618626
}
627+
else if (propertyName == DependencyContextStrings.LocalPathPropertyName)
628+
{
629+
localPath = propertyValue;
630+
}
619631
}
620632

621633
reader.CheckEndObject();
622634

623635
if (locale != null)
624636
{
625-
resources.Add(new ResourceAssembly(path, Pool(locale)));
637+
resources.Add(new ResourceAssembly(path, Pool(locale), localPath));
626638
}
627639
}
628640

@@ -786,7 +798,7 @@ IEnumerable<Library> CreateLibrariesNotNull(IEnumerable<TargetLibrary> libraries
786798
{
787799
RuntimeFile[] groupRuntimeAssemblies = ridGroup
788800
.Where(e => e.Type == DependencyContextStrings.RuntimeAssetType)
789-
.Select(e => new RuntimeFile(e.Path, e.AssemblyVersion, e.FileVersion))
801+
.Select(e => new RuntimeFile(e.Path, e.AssemblyVersion, e.FileVersion, e.LocalPath))
790802
.ToArray();
791803

792804
if (groupRuntimeAssemblies.Length != 0)
@@ -798,7 +810,7 @@ IEnumerable<Library> CreateLibrariesNotNull(IEnumerable<TargetLibrary> libraries
798810

799811
RuntimeFile[] groupNativeLibraries = ridGroup
800812
.Where(e => e.Type == DependencyContextStrings.NativeAssetType)
801-
.Select(e => new RuntimeFile(e.Path, e.AssemblyVersion, e.FileVersion))
813+
.Select(e => new RuntimeFile(e.Path, e.AssemblyVersion, e.FileVersion, e.LocalPath))
802814
.ToArray();
803815

804816
if (groupNativeLibraries.Length != 0)
@@ -909,6 +921,8 @@ private struct RuntimeTargetEntryStub
909921
public string? AssemblyVersion;
910922

911923
public string? FileVersion;
924+
925+
public string? LocalPath;
912926
}
913927

914928
private struct LibraryStub

src/libraries/Microsoft.Extensions.DependencyModel/src/DependencyContextStrings.cs

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -86,5 +86,7 @@ internal static class DependencyContextStrings
8686
internal const string AssemblyVersionPropertyName = "assemblyVersion";
8787

8888
internal const string FileVersionPropertyName = "fileVersion";
89+
90+
internal const string LocalPathPropertyName = "localPath";
8991
}
9092
}

src/libraries/Microsoft.Extensions.DependencyModel/src/DependencyContextWriter.cs

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -222,6 +222,11 @@ private static void AddResourceAssemblies(IReadOnlyList<ResourceAssembly> resour
222222
ResourceAssembly resourceAssembly = resourceAssemblies[i];
223223
jsonWriter.WriteStartObject(NormalizePath(resourceAssembly.Path));
224224
jsonWriter.WriteString(DependencyContextStrings.LocalePropertyName, resourceAssembly.Locale);
225+
if (resourceAssembly.LocalPath != null)
226+
{
227+
jsonWriter.WriteString(DependencyContextStrings.LocalPathPropertyName, NormalizePath(resourceAssembly.LocalPath));
228+
}
229+
225230
jsonWriter.WriteEndObject();
226231
}
227232
jsonWriter.WriteEndObject();
@@ -363,6 +368,11 @@ private static void AddRuntimeSpecificAssets(IEnumerable<RuntimeFile> assets, st
363368
jsonWriter.WriteString(DependencyContextStrings.FileVersionPropertyName, asset.FileVersion);
364369
}
365370

371+
if (asset.LocalPath != null)
372+
{
373+
jsonWriter.WriteString(DependencyContextStrings.LocalPathPropertyName, NormalizePath(asset.LocalPath));
374+
}
375+
366376
jsonWriter.WriteEndObject();
367377
}
368378
}
@@ -396,6 +406,11 @@ private static void WriteAssetList(string key, IEnumerable<RuntimeFile> runtimeF
396406
jsonWriter.WriteString(DependencyContextStrings.FileVersionPropertyName, runtimeFile.FileVersion);
397407
}
398408

409+
if (runtimeFile.LocalPath != null)
410+
{
411+
jsonWriter.WriteString(DependencyContextStrings.LocalPathPropertyName, NormalizePath(runtimeFile.LocalPath));
412+
}
413+
399414
jsonWriter.WriteEndObject();
400415
}
401416

src/libraries/Microsoft.Extensions.DependencyModel/src/ResourceAssembly.cs

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,10 @@ namespace Microsoft.Extensions.DependencyModel
88
public class ResourceAssembly
99
{
1010
public ResourceAssembly(string path, string locale)
11+
: this(path, locale, null)
12+
{ }
13+
14+
public ResourceAssembly(string path, string locale, string? localPath)
1115
{
1216
if (string.IsNullOrEmpty(path))
1317
{
@@ -19,11 +23,16 @@ public ResourceAssembly(string path, string locale)
1923
}
2024
Locale = locale;
2125
Path = path;
26+
LocalPath = localPath;
2227
}
2328

2429
public string Locale { get; set; }
2530

31+
// Depending on the source of the resource assembly, this path may be relative to the
32+
// a referenced NuGet package's root or to the app/component root.
2633
public string Path { get; set; }
2734

35+
// Path relative to the app/component represented by the dependency context
36+
public string? LocalPath { get; }
2837
}
2938
}

src/libraries/Microsoft.Extensions.DependencyModel/src/RuntimeFile.cs

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,10 @@ namespace Microsoft.Extensions.DependencyModel
88
public class RuntimeFile
99
{
1010
public RuntimeFile(string path, string? assemblyVersion, string? fileVersion)
11+
: this(path, assemblyVersion, fileVersion, null)
12+
{ }
13+
14+
public RuntimeFile(string path, string? assemblyVersion, string? fileVersion, string? localPath)
1115
{
1216
if (string.IsNullOrEmpty(path))
1317
{
@@ -17,12 +21,18 @@ public RuntimeFile(string path, string? assemblyVersion, string? fileVersion)
1721
Path = path;
1822
AssemblyVersion = assemblyVersion;
1923
FileVersion = fileVersion;
24+
LocalPath = localPath;
2025
}
2126

27+
// Depending on the source of the runtime file, this path may be relative to the
28+
// a referenced NuGet package's root or to the app/component root.
2229
public string Path { get; }
2330

2431
public string? AssemblyVersion { get; }
2532

2633
public string? FileVersion { get; }
34+
35+
// Path relative to the app/component represented by the dependency context
36+
public string? LocalPath { get; }
2737
}
2838
}

src/libraries/Microsoft.Extensions.DependencyModel/tests/DependencyContextJsonReaderTest.cs

Lines changed: 118 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -835,5 +835,123 @@ public void FailsToReadEmptyLibraryType()
835835
}
836836
"));
837837
}
838+
839+
[Fact]
840+
public void ReadsRuntimeFilesWithLocalPath()
841+
{
842+
var context = Read(
843+
@"{
844+
""targets"": {
845+
"".NETCoreApp,Version=v5.0"": {
846+
""System.Banana/1.0.0"": {
847+
""runtime"": {
848+
""lib/System.Banana.dll"": {
849+
""assemblyVersion"": ""1.2.3"",
850+
""fileVersion"": ""4.5.6"",
851+
""localPath"": ""local/path/System.Banana.dll""
852+
}
853+
}
854+
}
855+
}
856+
},
857+
""libraries"": {
858+
""System.Banana/1.0.0"": {
859+
""type"": ""package"",
860+
""serviceable"": false,
861+
""sha512"": ""HASH-System.Banana""
862+
}
863+
}
864+
}");
865+
866+
var runtimeLibrary = context.RuntimeLibraries.Should().ContainSingle().Subject;
867+
var runtimeFile = runtimeLibrary.RuntimeAssemblyGroups.GetDefaultRuntimeFileAssets().Single();
868+
869+
Assert.Equal("lib/System.Banana.dll", runtimeFile.Path);
870+
Assert.Equal("1.2.3", runtimeFile.AssemblyVersion);
871+
Assert.Equal("4.5.6", runtimeFile.FileVersion);
872+
Assert.Equal("local/path/System.Banana.dll", runtimeFile.LocalPath);
873+
}
874+
875+
[Fact]
876+
public void ReadsRuntimeTargetsWithLocalPath()
877+
{
878+
var context = Read(
879+
@"{
880+
""targets"": {
881+
"".NETCoreApp,Version=v5.0/unix"": {
882+
""System.Banana/1.0.0"": {
883+
""runtimeTargets"": {
884+
""runtimes/unix/lib/System.Banana.dll"": {
885+
""rid"": ""unix"",
886+
""assetType"": ""runtime"",
887+
""assemblyVersion"": ""1.2.3"",
888+
""fileVersion"": ""4.5.6"",
889+
""localPath"": ""unix/custom/System.Banana.dll""
890+
},
891+
""runtimes/linux-x64/native/native.so"": {
892+
""rid"": ""linux-x64"",
893+
""assetType"": ""native"",
894+
""assemblyVersion"": ""1.2.3"",
895+
""fileVersion"": ""4.5.6"",
896+
""localPath"": ""local/path/linux-x64/native.so""
897+
}
898+
}
899+
}
900+
}
901+
},
902+
""libraries"": {
903+
""System.Banana/1.0.0"": {
904+
""type"": ""package"",
905+
""serviceable"": false,
906+
""sha512"": ""HASH-System.Banana""
907+
}
908+
}
909+
}");
910+
911+
var runtimeLibrary = context.RuntimeLibraries.Should().ContainSingle().Subject;
912+
var runtimeFile = runtimeLibrary.RuntimeAssemblyGroups.GetRuntimeFileAssets("unix").Single();
913+
Assert.Equal("runtimes/unix/lib/System.Banana.dll", runtimeFile.Path);
914+
Assert.Equal("1.2.3", runtimeFile.AssemblyVersion);
915+
Assert.Equal("4.5.6", runtimeFile.FileVersion);
916+
Assert.Equal("unix/custom/System.Banana.dll", runtimeFile.LocalPath);
917+
918+
runtimeFile = runtimeLibrary.NativeLibraryGroups.GetRuntimeFileAssets("linux-x64").Single();
919+
Assert.Equal("runtimes/linux-x64/native/native.so", runtimeFile.Path);
920+
Assert.Equal("local/path/linux-x64/native.so", runtimeFile.LocalPath);
921+
}
922+
923+
[Fact]
924+
public void ReadsResourceAssembliesWithLocalPath()
925+
{
926+
var context = Read(
927+
@"{
928+
""targets"": {
929+
"".NETCoreApp,Version=v5.0"": {
930+
""System.Banana/1.0.0"": {
931+
""resources"": {
932+
""fr/System.Banana.resources.dll"": {
933+
""locale"": ""fr"",
934+
""localPath"": ""local/path/fr/System.Banana.resources.dll""
935+
}
936+
}
937+
}
938+
}
939+
},
940+
""libraries"": {
941+
""System.Banana/1.0.0"": {
942+
""type"": ""package"",
943+
""serviceable"": false,
944+
""sha512"": ""HASH-System.Banana""
945+
}
946+
}
947+
}");
948+
949+
var runtimeLibrary = context.RuntimeLibraries.Should().ContainSingle().Subject;
950+
var resourceAssembly = runtimeLibrary.ResourceAssemblies.Single();
951+
952+
Assert.Equal("fr/System.Banana.resources.dll", resourceAssembly.Path);
953+
Assert.Equal("fr", resourceAssembly.Locale);
954+
Assert.Equal("local/path/fr/System.Banana.resources.dll", resourceAssembly.LocalPath);
955+
}
838956
}
839957
}

0 commit comments

Comments
 (0)