Merge pull request #3153 from crobibero/api-json-enum

Fix Json Enum conversion, map all JsonDefaults properties to API
This commit is contained in:
Cody Robibero 2020-06-02 11:15:08 -06:00 committed by GitHub
commit 93bca7ab50
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
6 changed files with 55 additions and 64 deletions

View File

@ -1,12 +1,12 @@
#nullable enable
using System.Text.Json;
using System.Threading.Tasks;
using Jellyfin.Api.Constants;
using Jellyfin.Api.Models.ConfigurationDtos;
using MediaBrowser.Controller.Configuration;
using MediaBrowser.Controller.MediaEncoding;
using MediaBrowser.Model.Configuration;
using MediaBrowser.Model.Serialization;
using Microsoft.AspNetCore.Authorization;
using Microsoft.AspNetCore.Http;
using Microsoft.AspNetCore.Mvc;
@ -23,22 +23,18 @@ namespace Jellyfin.Api.Controllers
{
private readonly IServerConfigurationManager _configurationManager;
private readonly IMediaEncoder _mediaEncoder;
private readonly IJsonSerializer _jsonSerializer;
/// <summary>
/// Initializes a new instance of the <see cref="ConfigurationController"/> class.
/// </summary>
/// <param name="configurationManager">Instance of the <see cref="IServerConfigurationManager"/> interface.</param>
/// <param name="mediaEncoder">Instance of the <see cref="IMediaEncoder"/> interface.</param>
/// <param name="jsonSerializer">Instance of the <see cref="IJsonSerializer"/> interface.</param>
public ConfigurationController(
IServerConfigurationManager configurationManager,
IMediaEncoder mediaEncoder,
IJsonSerializer jsonSerializer)
IMediaEncoder mediaEncoder)
{
_configurationManager = configurationManager;
_mediaEncoder = mediaEncoder;
_jsonSerializer = jsonSerializer;
}
/// <summary>
@ -93,13 +89,7 @@ namespace Jellyfin.Api.Controllers
public async Task<ActionResult> UpdateNamedConfiguration([FromRoute] string key)
{
var configurationType = _configurationManager.GetConfigurationType(key);
/*
// TODO switch to System.Text.Json when https://github.com/dotnet/runtime/issues/30255 is fixed.
var configuration = await JsonSerializer.DeserializeAsync(Request.Body, configurationType);
*/
var configuration = await _jsonSerializer.DeserializeFromStreamAsync(Request.Body, configurationType)
.ConfigureAwait(false);
_configurationManager.SaveConfiguration(key, configuration);
return Ok();
}

View File

@ -1,9 +1,6 @@
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Reflection;
using System.Text.Json.Serialization;
using Jellyfin.Api;
using Jellyfin.Api.Auth;
using Jellyfin.Api.Auth.FirstTimeSetupOrElevatedPolicy;
@ -11,6 +8,7 @@ using Jellyfin.Api.Auth.RequiresElevationPolicy;
using Jellyfin.Api.Constants;
using Jellyfin.Api.Controllers;
using Jellyfin.Server.Formatters;
using MediaBrowser.Common.Json;
using Microsoft.AspNetCore.Authentication;
using Microsoft.AspNetCore.Authorization;
using Microsoft.Extensions.DependencyInjection;
@ -83,8 +81,20 @@ namespace Jellyfin.Server.Extensions
.AddApplicationPart(typeof(StartupController).Assembly)
.AddJsonOptions(options =>
{
// Setting the naming policy to null leaves the property names as-is when serializing objects to JSON.
options.JsonSerializerOptions.PropertyNamingPolicy = null;
// Update all properties that are set in JsonDefaults
var jsonOptions = JsonDefaults.PascalCase;
// From JsonDefaults
options.JsonSerializerOptions.ReadCommentHandling = jsonOptions.ReadCommentHandling;
options.JsonSerializerOptions.WriteIndented = jsonOptions.WriteIndented;
options.JsonSerializerOptions.Converters.Clear();
foreach (var converter in jsonOptions.Converters)
{
options.JsonSerializerOptions.Converters.Add(converter);
}
// From JsonDefaults.PascalCase
options.JsonSerializerOptions.PropertyNamingPolicy = jsonOptions.PropertyNamingPolicy;
})
.AddControllersAsServices();
}
@ -98,7 +108,7 @@ namespace Jellyfin.Server.Extensions
{
return serviceCollection.AddSwaggerGen(c =>
{
c.SwaggerDoc("api-docs", new OpenApiInfo { Title = "Jellyfin API" });
c.SwaggerDoc("api-docs", new OpenApiInfo { Title = "Jellyfin API", Version = "v1" });
// Add all xml doc files to swagger generator.
var xmlFiles = Directory.GetFiles(

View File

@ -1,4 +1,4 @@
using Jellyfin.Server.Models;
using MediaBrowser.Common.Json;
using Microsoft.AspNetCore.Mvc.Formatters;
using Microsoft.Net.Http.Headers;
@ -12,7 +12,7 @@ namespace Jellyfin.Server.Formatters
/// <summary>
/// Initializes a new instance of the <see cref="CamelCaseJsonProfileFormatter"/> class.
/// </summary>
public CamelCaseJsonProfileFormatter() : base(JsonOptions.CamelCase)
public CamelCaseJsonProfileFormatter() : base(JsonDefaults.CamelCase)
{
SupportedMediaTypes.Clear();
SupportedMediaTypes.Add(MediaTypeHeaderValue.Parse("application/json;profile=\"CamelCase\""));

View File

@ -1,4 +1,4 @@
using Jellyfin.Server.Models;
using MediaBrowser.Common.Json;
using Microsoft.AspNetCore.Mvc.Formatters;
using Microsoft.Net.Http.Headers;
@ -12,7 +12,7 @@ namespace Jellyfin.Server.Formatters
/// <summary>
/// Initializes a new instance of the <see cref="PascalCaseJsonProfileFormatter"/> class.
/// </summary>
public PascalCaseJsonProfileFormatter() : base(JsonOptions.PascalCase)
public PascalCaseJsonProfileFormatter() : base(JsonDefaults.PascalCase)
{
SupportedMediaTypes.Clear();
// Add application/json for default formatter

View File

@ -1,41 +0,0 @@
using System.Text.Json;
namespace Jellyfin.Server.Models
{
/// <summary>
/// Json Options.
/// </summary>
public static class JsonOptions
{
/// <summary>
/// Gets CamelCase json options.
/// </summary>
public static JsonSerializerOptions CamelCase
{
get
{
var options = DefaultJsonOptions;
options.PropertyNamingPolicy = JsonNamingPolicy.CamelCase;
return options;
}
}
/// <summary>
/// Gets PascalCase json options.
/// </summary>
public static JsonSerializerOptions PascalCase
{
get
{
var options = DefaultJsonOptions;
options.PropertyNamingPolicy = null;
return options;
}
}
/// <summary>
/// Gets base Json Serializer Options.
/// </summary>
private static JsonSerializerOptions DefaultJsonOptions => new JsonSerializerOptions();
}
}

View File

@ -12,10 +12,16 @@ namespace MediaBrowser.Common.Json
/// <summary>
/// Gets the default <see cref="JsonSerializerOptions" /> options.
/// </summary>
/// <remarks>
/// When changing these options, update
/// Jellyfin.Server/Extensions/ApiServiceCollectionExtensions.cs
/// -> AddJellyfinApi
/// -> AddJsonOptions
/// </remarks>
/// <returns>The default <see cref="JsonSerializerOptions" /> options.</returns>
public static JsonSerializerOptions GetOptions()
{
var options = new JsonSerializerOptions()
var options = new JsonSerializerOptions
{
ReadCommentHandling = JsonCommentHandling.Disallow,
WriteIndented = false
@ -26,5 +32,31 @@ namespace MediaBrowser.Common.Json
return options;
}
/// <summary>
/// Gets CamelCase json options.
/// </summary>
public static JsonSerializerOptions CamelCase
{
get
{
var options = GetOptions();
options.PropertyNamingPolicy = JsonNamingPolicy.CamelCase;
return options;
}
}
/// <summary>
/// Gets PascalCase json options.
/// </summary>
public static JsonSerializerOptions PascalCase
{
get
{
var options = GetOptions();
options.PropertyNamingPolicy = null;
return options;
}
}
}
}