using System; using System.Collections.Generic; using System.Diagnostics.CodeAnalysis; using System.Reflection; using Octokit.Reflection; namespace Octokit.Internal { public class SimpleJsonSerializer : IJsonSerializer { readonly GitHubSerializerStrategy _serializationStrategy = new GitHubSerializerStrategy(); public string Serialize(object item) { return SimpleJson.SerializeObject(item, _serializationStrategy); } public T Deserialize(string json) { return SimpleJson.DeserializeObject(json, _serializationStrategy); } class GitHubSerializerStrategy : PocoJsonSerializerStrategy { protected override string MapClrMemberNameToJsonFieldName(string clrPropertyName) { var rubyCased = clrPropertyName.ToRubyCase(); if (rubyCased == "links") return "_links"; // Special case for GitHub API return rubyCased; } // This is overridden so that null values are omitted from serialized objects. [SuppressMessage("Microsoft.Design", "CA1007:UseGenericsWhereAppropriate", Justification = "Need to support .NET 2")] protected override bool TrySerializeUnknownTypes(object input, out object output) { Ensure.ArgumentNotNull(input, "input"); var type = input.GetType(); var jsonObject = new JsonObject(); var getters = GetCache[type]; foreach (var getter in getters) { if (getter.Value != null) { var value = getter.Value(input); if (value == null) { continue; // sometimes Octokit needs to send a null // so look for this attribute when serializing // XXX: we don't know which property we have at this point // so this reflection trick doesn't work // TODO: make this magic work //var property = type.GetProperty(getter.Key); //var attribute = property.GetCustomAttribute(); //if (attribute == null) //{ // continue; //} } jsonObject.Add(MapClrMemberNameToJsonFieldName(getter.Key), value); } } output = jsonObject; return true; } [SuppressMessage("Microsoft.Globalization", "CA1308:NormalizeStringsToUppercase", Justification = "The API expects lowercase values")] protected override object SerializeEnum(Enum p) { return p.ToString().ToLowerInvariant(); } // Overridden to handle enums. public override object DeserializeObject(object value, Type type) { var stringValue = value as string; if (stringValue != null) { if (ReflectionUtils.GetTypeInfo(type).IsEnum) { // remove '-' from values coming in to be able to enum utf-8 stringValue = stringValue.Replace("-", ""); return Enum.Parse(type, stringValue, ignoreCase: true); } if (ReflectionUtils.IsNullableType(type)) { var underlyingType = Nullable.GetUnderlyingType(type); if (ReflectionUtils.GetTypeInfo(underlyingType).IsEnum) { return Enum.Parse(underlyingType, stringValue, ignoreCase: true); } } } return base.DeserializeObject(value, type); } } } }