Skip to content

Commit 5150c42

Browse files
committed
Fix deserialization of enums
1 parent 6a87013 commit 5150c42

File tree

2 files changed

+39
-2
lines changed

2 files changed

+39
-2
lines changed
Lines changed: 36 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,36 @@
1+
using System;
2+
using System.Collections.Generic;
3+
using System.Linq;
4+
using System.Reflection;
5+
using System.Runtime.Serialization;
6+
using System.Text.Json;
7+
using System.Text.Json.Serialization;
8+
9+
namespace Docker.DotNet;
10+
11+
// Adapted from https://github.com/dotnet/runtime/issues/74385#issuecomment-1705083109
12+
internal sealed class JsonEnumMemberConverter<TEnum> : JsonStringEnumConverter<TEnum> where TEnum : struct, Enum
13+
{
14+
public JsonEnumMemberConverter() : base(namingPolicy: ResolveNamingPolicy())
15+
{
16+
}
17+
18+
private static JsonNamingPolicy ResolveNamingPolicy()
19+
{
20+
var map = typeof(TEnum).GetFields(BindingFlags.Public | BindingFlags.Static)
21+
.Select(f => (f.Name, AttributeName: f.GetCustomAttribute<EnumMemberAttribute>()?.Value))
22+
.Where(pair => pair.AttributeName != null)
23+
.ToDictionary(e => e.Name, e => e.AttributeName);
24+
25+
return map.Count > 0 ? new EnumMemberNamingPolicy(map) : null;
26+
}
27+
28+
private sealed class EnumMemberNamingPolicy : JsonNamingPolicy
29+
{
30+
private readonly IReadOnlyDictionary<string, string> _map;
31+
32+
public EnumMemberNamingPolicy(IReadOnlyDictionary<string, string> map) => _map = map;
33+
34+
public override string ConvertName(string name) => _map.TryGetValue(name, out var newName) ? newName : name;
35+
}
36+
}

src/Docker.DotNet/JsonSerializer.cs

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -6,9 +6,9 @@
66
using System.Net.Http.Json;
77
using System.Runtime.CompilerServices;
88
using System.Text.Json;
9-
using System.Text.Json.Serialization;
109
using System.Threading;
1110
using System.Threading.Tasks;
11+
using Docker.DotNet.Models;
1212

1313
namespace Docker.DotNet
1414
{
@@ -21,9 +21,10 @@ internal class JsonSerializer
2121
{
2222
Converters =
2323
{
24+
new JsonEnumMemberConverter<TaskState>(),
25+
new JsonEnumMemberConverter<RestartPolicyKind>(),
2426
new JsonDateTimeConverter(),
2527
new JsonNullableDateTimeConverter(),
26-
new JsonStringEnumConverter(),
2728
new JsonBase64Converter(),
2829
},
2930
};

0 commit comments

Comments
 (0)