【问题标题】:Serialize Store C# class in camelCase在camelCase中序列化存储C#类
【发布时间】:2020-04-25 15:33:16
【问题描述】:

我正在使用 .net 将数据存储在 Firestore 数据库中。我正在使用 FirestoreData 和 FirestoreProperty 属性来控制对象如何序列化到数据库。默认情况下,C# 属性在 PascalCase 中,我希望它们在 camelCase 中序列化。我知道我可以在 FirestoreProperty 属性中设置将要序列化的属性的名称,但这是一项非常乏味且容易出错的任务。有没有办法将 Firestore .net 客户端配置为默认序列化 camelCase 中的属性?

谢谢

【问题讨论】:

    标签: c# google-cloud-firestore


    【解决方案1】:

    FirestorePropertyAttribute 定义了两个构造函数。一个允许通过提供参数name来添加名称:

    在 Firestore 文档中使用的名称。

    所以你可以简单地为一个属性设置它

    [FireStoreProperty("anyCase")]
    public string AnyCase{ get; set; }
    

    如果不修改底层类型,则无法以静默方式执行此操作。一种可能的方法是实现基于反射的Document converter,在运行时更改属性名称。您只需为每个数据类定义一次转换器。这是一种可能的方法:

    //Sample data class
    [FirestoreData(ConverterType = typeof(CamelCaseConverter<CustomCity>))]
    public class CustomCity
    {
        public string Name { get; set;  }
        public string Country { get; set; }
        public long Population { get; set; }
    }
    
    //Sample data class
    [FirestoreData(ConverterType = typeof(CamelCaseConverter<CustomPerson>))]
    public class CustomPerson
    {
        public string Name { get; set;  }
        public uint Age { get; set; }
    }
    
    //Conversion of camelCase and PascalCase
    public class CamelCaseConverter<T> : IFirestoreConverter<T> where T : new()
    {
        public object ToFirestore(T value)
        {
            dynamic camelCased = new ExpandoObject();
            foreach (PropertyInfo property in typeof(T).GetProperties())
            {
                string camelCaseName =
                    char.ToLowerInvariant(property.Name[0]) + property.Name.Substring(1);
                ((IDictionary<string, object>)camelCased)[camelCaseName] = property.GetValue(value);
            }
            return camelCased;
        }
    
        public T FromFirestore(object value)
        {
            if (value is IDictionary<string, object> map)
            {
                T pascalCased = new T();
                foreach (PropertyInfo property in typeof(T).GetProperties())
                {
                    string camelCaseName =
                        char.ToLowerInvariant(property.Name[0]) + property.Name.Substring(1);
                    property.SetValue(pascalCased, map[camelCaseName]);
                }
    
                return pascalCased;
            }
            throw new ArgumentException($"Unexpected data: {value.GetType()}");
        }
    

    【讨论】:

    • 我正在寻找一种默默地做到这一点的方法。必须为每个属性设置驼峰式属性名称真的很乏味且容易出错
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2022-01-02
    • 1970-01-01
    • 2013-02-09
    • 2017-05-22
    • 1970-01-01
    • 2023-03-30
    • 2020-11-08
    相关资源
    最近更新 更多