Соглашение С# JSON.NET, которое следует соглашениям об именах свойств Ruby?

Я использую http://json.codeplex.com/ и общаюсь с Rest API на основе Ruby. Проблема в том, что большинство свойств имеют соглашение об именах с подчеркиванием ruby. Мне интересно, знает ли кто-нибудь способ, чтобы мне не приходилось добавлять много JsonProperty.

Например, я хочу избежать добавления атрибута JsonProperty и иметь соглашение, встроенное в настройки сериализатора, чтобы он знал, что нужно попытаться сопоставить свойства с символом подчеркивания в соглашении об именах .NET :)

public class Member
{
    [JsonProperty(PropertyName = "avatar_url")]
    public string AvatarUrl { get; set; }

    [JsonProperty(PropertyName = "twitter_screen_name")]
    public string TwitterScreenName { get; set; }

    [JsonProperty(PropertyName = "website_url")]
    public string WebSiteUrl { get; set; }
}

person superlogical    schedule 13.10.2010    source источник


Ответы (4)


Обновление – сентябрь 2016 г.:

Json.NET 9.0.1 имеет SnakeCaseNamingStrategy . Вы можете использовать это, чтобы автоматически получить свойства стиля twitter_screen_name.


Унаследуйте от DefaultContractResolver и переопределите ResolvePropertyName, чтобы отформатировать имена свойств по своему усмотрению.

CamelCasePropertyNamesContractResolver выполняет аналогичное глобальное изменение имен свойств.

person James Newton-King    schedule 15.10.2010
comment
Спасибо, Джеймс, я попробую и опубликую свои выводы здесь для других, которые могут столкнуться с этой ситуацией. - person superlogical; 15.10.2010
comment
К вашему сведению, у распознавателей контрактов со стратегиями именования в целом существует потенциально огромная проблема с производительностью. Массивное снижение пропускной способности при использовании одного (90TPS) по сравнению с отсутствием (600TPS). - person Triynko; 31.07.2018
comment
Повторно используйте преобразователь контракта. Создание нового каждый раз заставляет отражение происходить при каждой сериализации/десериализации. - person James Newton-King; 04.08.2018

Прочитайте это: http://nyqui.st/json-net-newtonsoft-json-lowercase-keys

public class UnderscoreMappingResolver : DefaultContractResolver 
    {
        protected override string ResolvePropertyName(string propertyName)
        {
            return System.Text.RegularExpressions.Regex.Replace(
                propertyName, @"([A-Z])([A-Z][a-z])|([a-z0-9])([A-Z])", "$1$3_$2$4").ToLower(); 
        }
    }
person Krlos    schedule 01.09.2011
comment
Это не работает для свойств с двумя последовательными заглавными буквами. ThisIsATest становится this_is_atest. - person vaindil; 22.08.2016

Начиная с версии 9 для этого существует новое свойство стратегии именования со встроенным SnakeCaseNamingStrategy. Используйте приведенный ниже код и зарегистрируйте contractResolver как SerializerSettings.ContractResolver.

var contractResolver = new DefaultContractResolver();
contractResolver.NamingStrategy = new SnakeCaseNamingStrategy();

Этот класс по умолчанию не включает словари и не переопределяет значения свойств, устанавливаемые вручную. Это два параметра, которые можно передать в перегрузке:

// true parameter forces handling of dictionaries
// false prevents the serializer from changing anything manually set by an attribute
contractResolver.NamingStrategy = new SnakeCaseNamingStrategy(true, false);
person vaindil    schedule 22.08.2016

Этот сработал для меня

var settings = new JsonSerializerSettings
{
    ContractResolver = new PascalCaseToUnderscoreContractResolver()
};
var rawJson = "{ test_property:'test' }"
var myObject = JsonConvert.DeserializeObject<MyObjectType>(rawJson, settings);

Использование функции Humanizer "Подчеркивание"

https://www.nuget.org/packages/Humanizer/1.37.7

http://humanizr.net/#underscore

public class PascalCaseToUnderscoreContractResolver : DefaultContractResolver
{
    protected override string ResolvePropertyName(string propertyName) => propertyName.Underscore();
}

Класс MyObjectType

public Class MyObjectType
{
    public string TestProperty {get;set;}
}
person Michael    schedule 14.04.2016