I have a bunch of classes that will be serialized to JSON at some point and for the sake of following both C# conventions on the back-end and JavaScript conventions on the f
Better to use the new CamelCaseNamingStrategy (since 9.0.1):
new JsonSerializerSettings()
{
ContractResolver = new DefaultContractResolver
{
NamingStrategy = new CamelCaseNamingStrategy()
}
};
It does not override custom names set by JsonPropert('Name')
by default. (You can change the behaviour by CamelCaseNamingStrategy(bool, bool)
ctor.) So, does not need to create custom class like @Matt Burland's answer.
You can use the provided class Newtonsoft.Json.Serialization.CamelCasePropertyNamesContractResolver:
var serializer = new JsonSerializer
{
ContractResolver = new CamelCasePropertyNamesContractResolver()
};
var jobj = JObject.FromObject(request, serializer);
In other words, you don't have to create a custom resolver yourself.
public static JsonSerializer FormattingData()
{
var jsonSerializersettings = new JsonSerializer {
ContractResolver = new CamelCasePropertyNamesContractResolver() };
return jsonSerializersettings;
}
public static JObject CamelCaseData(JObject jObject)
{
var expandoConverter = new ExpandoObjectConverter();
dynamic camelCaseData =
JsonConvert.DeserializeObject(jObject.ToString(),
expandoConverter);
return JObject.FromObject(camelCaseData, FormattingData());
}
Since the accepted answer is link-only, I'm adding the actual code I ended up using (in case the link dies). It's largely the same as what was in the link:
// Automatic camel casing because I'm bored of putting [JsonProperty] on everything
// See: http://harald-muehlhoff.de/post/2013/05/10/Automatic-camelCase-naming-with-JsonNET-and-Microsoft-Web-API.aspx#.Uv43fvldWCl
public class CamelCase : CamelCasePropertyNamesContractResolver
{
protected override JsonProperty CreateProperty(MemberInfo member,
MemberSerialization memberSerialization)
{
var res = base.CreateProperty(member, memberSerialization);
var attrs = member.GetCustomAttributes(typeof(JsonPropertyAttribute), true);
if (attrs.Any())
{
var attr = (attrs[0] as JsonPropertyAttribute);
if (res.PropertyName != null && attr.PropertyName != null)
res.PropertyName = attr.PropertyName;
}
return res;
}
}
The only change I made was the addition of attr.PropertyName != null
to the if clause because of the case where I had added something like:
[JsonProperty(NullValueHandling = NullValueHandling.Ignore)]
public string SomeProperty { get; set; }
And didn't want to specify the PropertyName
(so it's null). The above will be serialized in JSON as someProperty
.
JObject.FromObject
uses default settings from JsonConvert
defaults.
There is a func property that you can assign like this:
JsonConvert.DefaultSettings = () => new JsonSerializerSettings()
{
ContractResolver = new CamelCasePropertyNamesContractResolver()
};
and whenever you call Jobject.FromObject
, it will use this func to construct settings.
You can use a custom contract resolver:
class MyContractResolver : DefaultContractResolver
{
protected override IList<JsonProperty> CreateProperties(Type type, MemberSerialization memberSerialization)
{
var properties = base.CreateProperties(type, memberSerialization);
foreach (var property in properties)
{
property.PropertyName = char.ToLower(property.PropertyName[0]) + string.Join("", property.PropertyName.Skip(1));
}
return properties;
}
}
And use it like:
class MyClass
{
public int MyProperty { get; set; }
public int MyProperty2 { get; set; }
}
var json = JsonConvert.SerializeObject(new MyClass(),
Formatting.Indented,
new JsonSerializerSettings { ContractResolver = new MyContractResolver() });