c# - 为什么 Json.NET 无法序列化 X509Certificate2?

标签 c# json.net

每当我尝试使用 Json.NET 序列化 X509Certificate2 实例(不使用其 ISerializable 实现,但选择忽略它)时,Json.NET 会引发异常。

异常消息是“名称为‘CertContext’的成员已存在于‘System.Security.Cryptography.X509Certificates.X509Certificate2’上。使用 JsonPropertyAttribute 指定另一个名称。”

我写了一个重现它的程序:

using System.Reflection;
using System.Security.Cryptography.X509Certificates;
using Newtonsoft.Json;
using Newtonsoft.Json.Serialization;

internal class Program
{
    private static void Main(string[] args)
    {
        var resolver = new DefaultContractResolver
        {
            IgnoreSerializableInterface = true,
            DefaultMembersSearchFlags =
                BindingFlags.Instance | BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.GetProperty
        };

        JsonConvert.SerializeObject(new X509Certificate2(), new JsonSerializerSettings {ContractResolver = resolver});
    }
}

经过调查,我注意到 X509Certificate2 实现了一个名为“CertContext”的属性,该属性在其基类 X509Certificate 中隐藏了一个同名方法。我如何告诉 Json.NET 只采用最派生的属性,就像通常那样?

最佳答案

我最近发现需要序列化 ​​X509Certificate2 的实例,以便比较两个行为不同的假定相同环境的差异。我能够通过以下 JsonSerializerSettings 实现序列化:

new JsonSerializerSettings {
    Error = (s, a) => a.ErrorContext.Handled = true,
    ContractResolver = new DefaultContractResolver {
        IgnoreSerializableInterface = true
    }
}

这是一个完整的工作示例,其中 JSON 序列化本地机器存储中的第一个证书并打开它:

namespace ConsoleApp1
{
    using System.Diagnostics;
    using System.IO;
    using System.Security.Cryptography.X509Certificates;

    using Newtonsoft.Json;
    using Newtonsoft.Json.Serialization;

    class Program
    {
        static void Main(string[] args)
        {
            var store = new X509Store(StoreName.My, StoreLocation.LocalMachine);

            try
            {
                store.Open(OpenFlags.ReadOnly);

                var cert = store.Certificates[0];

                var path = Path.GetTempFileName();

                File.WriteAllText(
                    path,
                    JsonConvert.SerializeObject(
                        cert, new JsonSerializerSettings {
                            Formatting = Formatting.Indented,
                            // Ignore serializtion errors
                            Error = (s, a) => a.ErrorContext.Handled = true,
                            ContractResolver = new DefaultContractResolver {
                                // Ensures all properties are serialized
                                IgnoreSerializableInterface = true
                            }
                        }
                    )
                );

                Process.Start(path);
            }
            finally
            {
                store.Close();
            }
        }
    }
}

关于c# - 为什么 Json.NET 无法序列化 X509Certificate2?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/21684184/

相关文章:

c# - 如何从 json 字符串中获取对象列表 c# Newtonsoft.json

c# - Unity如何使用从json字符串加载的变量作为更新部分的输入

c# - 使用 x :Static 向 xaml 中的数组添加值

c# - Visual Studio Code : "Program has more than one entry point defined"

c# - Arch linux 启动应用程序(脚本)Raspberry Pi

c# - 为什么 HttpResponseMessage 不显示其内容?

json - 是否有与 JSON.NET(服务器端)良好集成并支持 "preserve references"功能的 JavaScript(客户端)JSON 库?

c# - json.net反序列化 "flat"json数据

c# - 如何向用户公开我的流的子部分

C# - 根据一些匹配值将列表项合并为一项