Files
octokit.net/Octokit/Http/JsonHttpPipeline.cs
2015-12-16 21:23:36 +02:00

72 lines
2.7 KiB
C#

using System;
using System.Collections;
using System.IO;
using System.Net.Http;
namespace Octokit.Internal
{
/// <summary>
/// Responsible for serializing the request and response as JSON and
/// adding the proper JSON response header.
/// </summary>
public class JsonHttpPipeline
{
private const string v3ApiVersion = "application/vnd.github.quicksilver-preview+json; charset=utf-8, application/vnd.github.v3+json; charset=utf-8";
readonly IJsonSerializer _serializer;
public JsonHttpPipeline() : this(new SimpleJsonSerializer())
{
}
public JsonHttpPipeline(IJsonSerializer serializer)
{
Ensure.ArgumentNotNull(serializer, "serializer");
_serializer = serializer;
}
public void SerializeRequest(IRequest request)
{
Ensure.ArgumentNotNull(request, "request");
if (!request.Headers.ContainsKey("Accept"))
{
request.Headers["Accept"] = v3ApiVersion;
}
if (request.Method == HttpMethod.Get || request.Body == null) return;
if (request.Body is string || request.Body is Stream || request.Body is HttpContent) return;
request.Body = _serializer.Serialize(request.Body);
}
public IApiResponse<T> DeserializeResponse<T>(IResponse response)
{
Ensure.ArgumentNotNull(response, "response");
if (response.ContentType != null && response.ContentType.Equals("application/json", StringComparison.Ordinal))
{
var body = response.Body as string;
// simple json does not support the root node being empty. Will submit a pr but in the mean time....
if (!string.IsNullOrEmpty(body) && body != "{}")
{
var typeIsDictionary = typeof(IDictionary).IsAssignableFrom(typeof(T));
var typeIsEnumerable = typeof(IEnumerable).IsAssignableFrom(typeof(T));
var responseIsObject = body.StartsWith("{", StringComparison.Ordinal);
// If we're expecting an array, but we get a single object, just wrap it.
// This supports an api that dynamically changes the return type based on the content.
if (!typeIsDictionary && typeIsEnumerable && responseIsObject)
{
body = "[" + body + "]";
}
var json = _serializer.Deserialize<T>(body);
return new ApiResponse<T>(response, json);
}
}
return new ApiResponse<T>(response);
}
}
}