Сериализация Store C# класс в camelCase - PullRequest
0 голосов
/ 23 апреля 2020

Я храню данные в базе данных Firestore, используя. net. Я использую атрибуты FirestoreData и FirestoreProperty для управления тем, как объекты сериализуются в БД. C# свойства по умолчанию находятся в PascalCase, и я бы хотел, чтобы они были сериализованы в camelCase Я знаю, что могу задать имя, которое будет сериализовано свойством в атрибуте FirestoreProperty, но это действительно утомительная задача, способная вызвать ошибку. Есть ли способ настроить клиент Firestore. net по умолчанию для сериализации свойств в camelCase?

Спасибо

1 Ответ

2 голосов
/ 23 апреля 2020

FirestorePropertyAttribute определяет два конструктора. Можно добавить имя, указав параметр name:

Имя для использования в документе Firestore.

Таким образом, вы можете просто установить его для свойства как

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

Выполнение этого без вывода сообщений невозможно без изменения базового типа. Возможный подход заключается в реализации основанного на отражении конвертера документов , меняющего имена свойств во время выполнения. Вам нужно только определить конвертер один раз для каждого класса данных. Вот возможный подход:

//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()}");
    }
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...