From cdc66c5f98f73f0763573db4274b6763fbc6788d Mon Sep 17 00:00:00 2001 From: Pranav K Date: Mon, 17 Dec 2018 07:32:15 +0530 Subject: [PATCH] Move JSON.NET specific features to a separate assembly --- build/artifacts.props | 2 +- eng/ProjectReferences.props | 2 +- src/Framework/Microsoft.AspNetCore.App.props | 1 - src/Identity/build.cmd | 2 +- .../Identity.DefaultUI.WebSite.csproj | 1 + .../NoIdentityStartup.cs | 3 +- .../PocoUserStartup.cs | 3 +- .../Identity.DefaultUI.WebSite/StartupBase.cs | 5 +- .../appsettings.Development.json | 4 +- src/Mvc/Mvc.sln | 4 +- .../benchmarkapps/BasicApi/BasicApi.csproj | 2 +- src/Mvc/benchmarkapps/BasicApi/Startup.cs | 2 +- ...ft.AspNetCore.Mvc.Performance.Views.csproj | 2 - src/Mvc/samples/MvcSandbox/MvcSandbox.csproj | 7 +- .../Properties/AssemblyInfo.cs | 2 - .../ApplicationAssembliesProvider.cs | 2 +- .../JsonResult.cs | 24 +- .../ProblemDetails.cs | 7 - .../Properties/AssemblyInfo.cs | 2 - .../Properties/Resources.Designer.cs | 14 + .../Resources.resx | 3 + .../ValidationProblemDetails.cs | 2 - .../MvcJsonMvcBuilderExtensions.cs | 37 - .../MvcJsonMvcCoreBuilderExtensions.cs | 85 -- .../Properties/Resources.Designer.cs | 58 -- .../baseline.netcore.json | 910 ------------------ .../AnnotatedProblemDetails.cs | 63 ++ .../BsonTempDataSerializer.cs} | 20 +- .../MvcNewtonsoftJsonOptionsExtensions.cs} | 16 +- .../NewtonosftJsonMvcOptionsSetup.cs} | 21 +- .../NewtonsoftJsonMvcBuilderExtensions.cs | 56 ++ .../NewtonsoftJsonMvcCoreBuilderExtensions.cs | 110 +++ .../JsonArrayPool.cs | 2 +- .../JsonHelperExtensions.cs | 60 ++ .../JsonPatchExtensions.cs | 0 .../JsonPatchOperationsArrayProvider.cs | 8 +- .../JsonResultExecutor.cs | 36 +- .../JsonSerializerObjectPolicy.cs | 2 +- .../JsonSerializerSettingsProvider.cs | 10 +- .../MediaTypeHeaderValues.cs | 2 +- ...soft.AspNetCore.Mvc.NewtonsoftJson.csproj} | 11 +- .../MvcNewtonsoftJsonOptions.cs} | 5 +- .../NewtonsoftJsonHelper.cs} | 18 +- .../NewtonsoftJsonInputFormatter.cs} | 37 +- .../NewtonsoftJsonLoggerExtensions.cs} | 6 +- .../NewtonsoftJsonOutputFormatter.cs} | 13 +- .../NewtonsoftJsonPatchInputFormatter.cs} | 33 +- .../ProblemDetailsConverter.cs | 50 + .../Properties/AssemblyInfo.cs | 2 +- .../Properties/Resources.Designer.cs | 128 +++ .../Resources.resx | 69 +- .../ValidationProblemDetailsConverter.cs | 81 ++ ...pDataFilterPageApplicationModelProvider.cs | 10 +- .../Controller.cs | 8 +- .../CookieTempDataProvider.cs | 7 +- ...MvcViewFeaturesMvcCoreBuilderExtensions.cs | 13 +- .../Filters/SaveTempDataPropertyFilterBase.cs | 22 +- .../TempDataApplicationModelProvider.cs | 10 +- .../DefaultTempDataSerializer.cs | 32 + .../Infrastructure/TempDataSerializer.cs | 39 + ...crosoft.AspNetCore.Mvc.ViewFeatures.csproj | 2 - .../Properties/AssemblyInfo.cs | 1 + .../Properties/Resources.Designer.cs | 98 +- .../Rendering/DefaultJsonHelper.cs | 24 + .../Rendering/IJsonHelper.cs | 11 - .../Resources.resx | 21 +- .../SessionStateTempDataProvider.cs | 6 +- .../Microsoft.AspNetCore.Mvc.csproj | 1 - .../MvcServiceCollectionExtensions.cs | 3 - ...oft.AspNetCore.Mvc.ApiExplorer.Test.csproj | 2 +- .../CreatedAtActionResultTests.cs | 2 +- .../CreatedAtRouteResultTests.cs | 3 +- .../CreatedResultTests.cs | 3 +- .../Formatters/FormatFilterTest.cs | 3 +- .../HttpNotFoundObjectResultTest.cs | 3 +- .../HttpOkObjectResultTest.cs | 3 +- .../JsonResultTest.cs | 32 + .../Microsoft.AspNetCore.Mvc.Core.Test.csproj | 2 +- .../Binders/BodyModelBinderTests.cs | 9 +- .../ApiBehaviorTest.cs | 22 +- .../ApiExplorerTest.cs | 30 +- .../BasicTests.cs | 4 +- .../JsonOutputFormatterTests.cs | 1 + .../TempDataPropertyTest.cs | 4 +- .../BodyValidationIntegrationTests.cs | 4 +- ...oft.AspNetCore.Mvc.IntegrationTests.csproj | 1 + .../ModelBindingTestHelper.cs | 3 +- .../ServicesModelBinderIntegrationTest.cs | 26 +- .../TestMvcOptions.cs | 4 +- .../BsonTempDataSerializerTest.cs} | 18 +- ...MvcNewtonsoftJsonOptionsExtensionsTest.cs} | 19 +- .../NewtonsoftJsonMvcBuilderExtensionsTest.cs | 30 + ...tonsoftJsonMvcCoreBuilderExtensionsTest.cs | 63 ++ .../JsonHelperTest.cs | 10 +- .../JsonPatchExtensionsTest.cs | 0 .../JsonPatchOperationsArrayProviderTests.cs | 2 +- .../JsonResultExecutorTest.cs | 4 +- .../JsonResultTest.cs | 8 +- ...AspNetCore.Mvc.NewtonsoftJson.Test.csproj} | 3 +- .../NewtonsoftJsonInputFormatterTest.cs} | 34 +- .../NewtonsoftJsonOutputFormatterTest.cs} | 21 +- .../NewtonsoftJsonPatchInputFormatterTest.cs} | 32 +- .../RazorPageCreateTagHelperTest.cs | 4 +- ...aFilterPageApplicationModelProviderTest.cs | 24 +- .../ApplicationAssembliesProviderTest.cs | 1 + .../MvcOptionsSetupTest.cs | 18 +- .../MvcServiceCollectionExtensionsTest.cs | 20 - .../ControllerTest.cs | 4 +- .../ControllerUnitTestabilityTests.cs | 5 +- .../CookieTempDataProviderTest.cs | 294 +----- .../TempDataApplicationModelProviderTest.cs | 23 +- .../PartialViewResultExecutorTest.cs | 2 +- .../PartialViewResultTest.cs | 2 +- .../SessionStateTempDataProviderTest.cs | 252 +---- .../TempDataDictionaryFactoryTest.cs | 3 +- .../TempDataDictionaryTest.cs | 26 +- .../ViewComponentResultTest.cs | 5 +- .../ViewComponentTests.cs | 3 +- .../ContentViewComponentResultTest.cs | 2 +- .../HtmlContentViewComponentResultTest.cs | 2 +- .../ViewComponentContextTest.cs | 5 +- .../ViewViewComponentResultTest.cs | 4 +- .../ViewExecutorTest.cs | 4 +- .../ViewResultExecutorTest.cs | 2 +- .../ViewResultTest.cs | 2 +- .../ApiExplorerWebSite.csproj | 1 + .../WebSites/ApiExplorerWebSite/Startup.cs | 4 +- .../RemoteAttribute_VerifyController.cs | 2 +- .../RemoteAttribute_VerifyController.cs | 2 +- .../WebSites/BasicWebSite/BasicWebSite.csproj | 1 + .../FallbackOnTypeBasedMatchController.cs | 4 +- .../ContentNegotiation/NormalController.cs | 5 +- .../Controllers/HomeController.cs | 2 +- .../Controllers/JsonResultController.cs | 10 +- .../RemoteAttribute_VerifyController.cs | 2 +- .../RequestFormLimitsController.cs | 16 +- .../Controllers/RequestSizeLimitController.cs | 10 +- .../Controllers/RoutingController.cs | 4 +- src/Mvc/test/WebSites/BasicWebSite/Startup.cs | 1 + .../BasicWebSite/StartupRequestLimitSize.cs | 1 + ...hCookieTempDataProviderAndCookieConsent.cs | 1 + ...artupWithCustomInvalidModelStateFactory.cs | 1 + .../StartupWithEndpointRouting.cs | 1 + .../Home/JsonHelperWithSettingsInView.cshtml | 5 +- .../WebSites/Common/TestResponseGenerator.cs | 4 +- .../Inventory.cs | 4 +- .../AnotherController.cs | 4 +- .../WebSites/CorsWebSite/CorsWebSite.csproj | 1 + src/Mvc/test/WebSites/CorsWebSite/Startup.cs | 1 + .../Controllers/UploadFilesController.cs | 8 +- .../WebSites/FilesWebSite/FilesWebSite.csproj | 1 + src/Mvc/test/WebSites/FilesWebSite/Startup.cs | 1 + .../Controllers/JsonFormatterController.cs | 5 +- .../Controllers/ValidationController.cs | 8 +- .../FormatterWebSite/FormatterWebSite.csproj | 1 + .../test/WebSites/FormatterWebSite/Startup.cs | 3 +- .../StartupWithRespectBrowserAcceptHeader.cs | 3 +- .../HtmlGenerationWebSite.csproj | 1 + .../WebSites/HtmlGenerationWebSite/Startup.cs | 1 + .../RazorPagesWebSite.csproj | 1 + .../WebSites/RazorPagesWebSite/Startup.cs | 1 + .../Controllers/RoutingController.cs | 4 +- .../RoutingWebSite/RoutingWebSite.csproj | 1 + .../test/WebSites/RoutingWebSite/Startup.cs | 3 +- .../RoutingWebSite/StartupForLinkGenerator.cs | 1 + .../SimpleWebSite/SimpleWebSite.csproj | 1 + .../test/WebSites/SimpleWebSite/Startup.cs | 2 +- .../Controllers/RoutingController.cs | 4 +- .../WebSites/VersioningWebSite/Startup.cs | 1 + .../VersioningWebSite.csproj | 1 + 170 files changed, 1457 insertions(+), 2147 deletions(-) rename src/Mvc/src/{Microsoft.AspNetCore.Mvc.Formatters.Json => Microsoft.AspNetCore.Mvc.Core}/JsonResult.cs (72%) delete mode 100644 src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/DependencyInjection/MvcJsonMvcBuilderExtensions.cs delete mode 100644 src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/DependencyInjection/MvcJsonMvcCoreBuilderExtensions.cs delete mode 100644 src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/Properties/Resources.Designer.cs delete mode 100644 src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/baseline.netcore.json create mode 100644 src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/AnnotatedProblemDetails.cs rename src/Mvc/src/{Microsoft.AspNetCore.Mvc.ViewFeatures/Filters/TempDataSerializer.cs => Microsoft.AspNetCore.Mvc.NewtonsoftJson/BsonTempDataSerializer.cs} (93%) rename src/Mvc/src/{Microsoft.AspNetCore.Mvc.Formatters.Json/DependencyInjection/MvcJsonOptionsExtensions.cs => Microsoft.AspNetCore.Mvc.NewtonsoftJson/DependencyInjection/MvcNewtonsoftJsonOptionsExtensions.cs} (82%) rename src/Mvc/src/{Microsoft.AspNetCore.Mvc.Formatters.Json/DependencyInjection/MvcJsonMvcOptionsSetup.cs => Microsoft.AspNetCore.Mvc.NewtonsoftJson/DependencyInjection/NewtonosftJsonMvcOptionsSetup.cs} (80%) create mode 100644 src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/DependencyInjection/NewtonsoftJsonMvcBuilderExtensions.cs create mode 100644 src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/DependencyInjection/NewtonsoftJsonMvcCoreBuilderExtensions.cs rename src/Mvc/src/{Microsoft.AspNetCore.Mvc.Formatters.Json => Microsoft.AspNetCore.Mvc.NewtonsoftJson}/JsonArrayPool.cs (94%) create mode 100644 src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/JsonHelperExtensions.cs rename src/Mvc/src/{Microsoft.AspNetCore.Mvc.Formatters.Json => Microsoft.AspNetCore.Mvc.NewtonsoftJson}/JsonPatchExtensions.cs (100%) rename src/Mvc/src/{Microsoft.AspNetCore.Mvc.Formatters.Json => Microsoft.AspNetCore.Mvc.NewtonsoftJson}/JsonPatchOperationsArrayProvider.cs (92%) rename src/Mvc/src/{Microsoft.AspNetCore.Mvc.Formatters.Json => Microsoft.AspNetCore.Mvc.NewtonsoftJson}/JsonResultExecutor.cs (78%) rename src/Mvc/src/{Microsoft.AspNetCore.Mvc.Formatters.Json => Microsoft.AspNetCore.Mvc.NewtonsoftJson}/JsonSerializerObjectPolicy.cs (95%) rename src/Mvc/src/{Microsoft.AspNetCore.Mvc.Formatters.Json => Microsoft.AspNetCore.Mvc.NewtonsoftJson}/JsonSerializerSettingsProvider.cs (81%) rename src/Mvc/src/{Microsoft.AspNetCore.Mvc.Formatters.Json => Microsoft.AspNetCore.Mvc.NewtonsoftJson}/MediaTypeHeaderValues.cs (94%) rename src/Mvc/src/{Microsoft.AspNetCore.Mvc.Formatters.Json/Microsoft.AspNetCore.Mvc.Formatters.Json.csproj => Microsoft.AspNetCore.Mvc.NewtonsoftJson/Microsoft.AspNetCore.Mvc.NewtonsoftJson.csproj} (53%) rename src/Mvc/src/{Microsoft.AspNetCore.Mvc.Formatters.Json/MvcJsonOptions.cs => Microsoft.AspNetCore.Mvc.NewtonsoftJson/MvcNewtonsoftJsonOptions.cs} (88%) rename src/Mvc/src/{Microsoft.AspNetCore.Mvc.ViewFeatures/JsonHelper.cs => Microsoft.AspNetCore.Mvc.NewtonsoftJson/NewtonsoftJsonHelper.cs} (82%) rename src/Mvc/src/{Microsoft.AspNetCore.Mvc.Formatters.Json/JsonInputFormatter.cs => Microsoft.AspNetCore.Mvc.NewtonsoftJson/NewtonsoftJsonInputFormatter.cs} (93%) rename src/Mvc/src/{Microsoft.AspNetCore.Mvc.Formatters.Json/MvcJsonLoggerExtensions.cs => Microsoft.AspNetCore.Mvc.NewtonsoftJson/NewtonsoftJsonLoggerExtensions.cs} (89%) rename src/Mvc/src/{Microsoft.AspNetCore.Mvc.Formatters.Json/JsonOutputFormatter.cs => Microsoft.AspNetCore.Mvc.NewtonsoftJson/NewtonsoftJsonOutputFormatter.cs} (90%) rename src/Mvc/src/{Microsoft.AspNetCore.Mvc.Formatters.Json/JsonPatchInputFormatter.cs => Microsoft.AspNetCore.Mvc.NewtonsoftJson/NewtonsoftJsonPatchInputFormatter.cs} (85%) create mode 100644 src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/ProblemDetailsConverter.cs rename src/Mvc/src/{Microsoft.AspNetCore.Mvc.Formatters.Json => Microsoft.AspNetCore.Mvc.NewtonsoftJson}/Properties/AssemblyInfo.cs (71%) create mode 100644 src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/Properties/Resources.Designer.cs rename src/Mvc/src/{Microsoft.AspNetCore.Mvc.Formatters.Json => Microsoft.AspNetCore.Mvc.NewtonsoftJson}/Resources.resx (81%) create mode 100644 src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/ValidationProblemDetailsConverter.cs create mode 100644 src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Infrastructure/DefaultTempDataSerializer.cs create mode 100644 src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Infrastructure/TempDataSerializer.cs create mode 100644 src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Rendering/DefaultJsonHelper.cs create mode 100644 src/Mvc/test/Microsoft.AspNetCore.Mvc.Core.Test/JsonResultTest.cs rename src/Mvc/test/{Microsoft.AspNetCore.Mvc.ViewFeatures.Test/Filters/TempDataSerializerTest.cs => Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/BsonTempDataSerializerTest.cs} (87%) rename src/Mvc/test/{Microsoft.AspNetCore.Mvc.Formatters.Json.Test/MvcJsonOptionsExtensionsTests.cs => Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/DependencyInjection/MvcNewtonsoftJsonOptionsExtensionsTest.cs} (94%) create mode 100644 src/Mvc/test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/DependencyInjection/NewtonsoftJsonMvcBuilderExtensionsTest.cs create mode 100644 src/Mvc/test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/DependencyInjection/NewtonsoftJsonMvcCoreBuilderExtensionsTest.cs rename src/Mvc/test/{Microsoft.AspNetCore.Mvc.ViewFeatures.Test => Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test}/JsonHelperTest.cs (85%) rename src/Mvc/test/{Microsoft.AspNetCore.Mvc.Test => Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test}/JsonPatchExtensionsTest.cs (100%) rename src/Mvc/test/{Microsoft.AspNetCore.Mvc.Formatters.Json.Test => Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test}/JsonPatchOperationsArrayProviderTests.cs (97%) rename src/Mvc/test/{Microsoft.AspNetCore.Mvc.Formatters.Json.Test => Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test}/JsonResultExecutorTest.cs (99%) rename src/Mvc/test/{Microsoft.AspNetCore.Mvc.Formatters.Json.Test => Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test}/JsonResultTest.cs (90%) rename src/Mvc/test/{Microsoft.AspNetCore.Mvc.Formatters.Json.Test/Microsoft.AspNetCore.Mvc.Formatters.Json.Test.csproj => Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test.csproj} (71%) rename src/Mvc/test/{Microsoft.AspNetCore.Mvc.Formatters.Json.Test/JsonInputFormatterTest.cs => Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/NewtonsoftJsonInputFormatterTest.cs} (96%) rename src/Mvc/test/{Microsoft.AspNetCore.Mvc.Formatters.Json.Test/JsonOutputFormatterTests.cs => Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/NewtonsoftJsonOutputFormatterTest.cs} (95%) rename src/Mvc/test/{Microsoft.AspNetCore.Mvc.Formatters.Json.Test/JsonPatchInputFormatterTest.cs => Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/NewtonsoftJsonPatchInputFormatterTest.cs} (94%) diff --git a/build/artifacts.props b/build/artifacts.props index 8a5ed73567..64358ab186 100644 --- a/build/artifacts.props +++ b/build/artifacts.props @@ -136,9 +136,9 @@ This can be done once #4246 is complete, and done in conjunction with converting - + diff --git a/eng/ProjectReferences.props b/eng/ProjectReferences.props index 6bb2293088..d6597e0ddb 100644 --- a/eng/ProjectReferences.props +++ b/eng/ProjectReferences.props @@ -99,9 +99,9 @@ - + diff --git a/src/Framework/Microsoft.AspNetCore.App.props b/src/Framework/Microsoft.AspNetCore.App.props index fbf6bdd275..d7ecd1ec2c 100644 --- a/src/Framework/Microsoft.AspNetCore.App.props +++ b/src/Framework/Microsoft.AspNetCore.App.props @@ -54,7 +54,6 @@ - diff --git a/src/Identity/build.cmd b/src/Identity/build.cmd index f22573197f..033fe6f614 100644 --- a/src/Identity/build.cmd +++ b/src/Identity/build.cmd @@ -1,3 +1,3 @@ @ECHO OFF SET RepoRoot=%~dp0..\.. -%RepoRoot%\build.cmd -LockFile %RepoRoot%\korebuild-lock.txt -projects %~dp0**\*.*proj %* +%RepoRoot%\build.cmd -projects %~dp0\**\*.*proj %* diff --git a/src/Identity/testassets/Identity.DefaultUI.WebSite/Identity.DefaultUI.WebSite.csproj b/src/Identity/testassets/Identity.DefaultUI.WebSite/Identity.DefaultUI.WebSite.csproj index 65f21e44cb..45574a14ac 100644 --- a/src/Identity/testassets/Identity.DefaultUI.WebSite/Identity.DefaultUI.WebSite.csproj +++ b/src/Identity/testassets/Identity.DefaultUI.WebSite/Identity.DefaultUI.WebSite.csproj @@ -25,6 +25,7 @@ + diff --git a/src/Identity/testassets/Identity.DefaultUI.WebSite/NoIdentityStartup.cs b/src/Identity/testassets/Identity.DefaultUI.WebSite/NoIdentityStartup.cs index ea77545ca2..3122315479 100644 --- a/src/Identity/testassets/Identity.DefaultUI.WebSite/NoIdentityStartup.cs +++ b/src/Identity/testassets/Identity.DefaultUI.WebSite/NoIdentityStartup.cs @@ -34,7 +34,8 @@ namespace Identity.DefaultUI.WebSite { options.Conventions.AuthorizeFolder("/Areas/Identity/Pages/Account/Manage"); options.Conventions.AuthorizePage("/Areas/Identity/Pages/Account/Logout"); - }); + }) + .AddNewtonsoftJson(); } // This method gets called by the runtime. Use this method to configure the HTTP request pipeline. diff --git a/src/Identity/testassets/Identity.DefaultUI.WebSite/PocoUserStartup.cs b/src/Identity/testassets/Identity.DefaultUI.WebSite/PocoUserStartup.cs index 39d742c583..0277bd669a 100644 --- a/src/Identity/testassets/Identity.DefaultUI.WebSite/PocoUserStartup.cs +++ b/src/Identity/testassets/Identity.DefaultUI.WebSite/PocoUserStartup.cs @@ -31,7 +31,8 @@ namespace Identity.DefaultUI.WebSite .AddUserManager>(); services.AddSingleton, InMemoryUserStore>(); - services.AddMvc(); + services.AddMvc() + .AddNewtonsoftJson(); } } } diff --git a/src/Identity/testassets/Identity.DefaultUI.WebSite/StartupBase.cs b/src/Identity/testassets/Identity.DefaultUI.WebSite/StartupBase.cs index fb08f9741b..c73d12f7ad 100644 --- a/src/Identity/testassets/Identity.DefaultUI.WebSite/StartupBase.cs +++ b/src/Identity/testassets/Identity.DefaultUI.WebSite/StartupBase.cs @@ -12,7 +12,7 @@ using Microsoft.Extensions.FileProviders; namespace Identity.DefaultUI.WebSite { - public class StartupBase + public class StartupBase where TUser : class where TContext : DbContext { @@ -45,7 +45,8 @@ namespace Identity.DefaultUI.WebSite .AddRoles() .AddEntityFrameworkStores(); - services.AddMvc(); + services.AddMvc() + .AddNewtonsoftJson(); } // This method gets called by the runtime. Use this method to configure the HTTP request pipeline. diff --git a/src/Identity/testassets/Identity.DefaultUI.WebSite/appsettings.Development.json b/src/Identity/testassets/Identity.DefaultUI.WebSite/appsettings.Development.json index 0623a3f445..dfab32b8c6 100644 --- a/src/Identity/testassets/Identity.DefaultUI.WebSite/appsettings.Development.json +++ b/src/Identity/testassets/Identity.DefaultUI.WebSite/appsettings.Development.json @@ -2,8 +2,8 @@ "Logging": { "LogLevel": { "Default": "Debug", - "System": "Information", - "Microsoft": "Information" + "System": "Warning", + "Microsoft": "Warning" } } } diff --git a/src/Mvc/Mvc.sln b/src/Mvc/Mvc.sln index cfe5ef3a73..d0cb0d402c 100644 --- a/src/Mvc/Mvc.sln +++ b/src/Mvc/Mvc.sln @@ -83,11 +83,11 @@ Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.AspNetCore.Mvc.Ab EndProject Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.AspNetCore.Mvc.ViewFeatures", "src\Microsoft.AspNetCore.Mvc.ViewFeatures\Microsoft.AspNetCore.Mvc.ViewFeatures.csproj", "{3F8B8FC1-9FE4-4788-8991-367113E8D7AD}" EndProject -Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.AspNetCore.Mvc.Formatters.Json", "src\Microsoft.AspNetCore.Mvc.Formatters.Json\Microsoft.AspNetCore.Mvc.Formatters.Json.csproj", "{3FC8D9D6-9352-43A3-8E81-422F270085B7}" +Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.AspNetCore.Mvc.NewtonsoftJson", "src\Microsoft.AspNetCore.Mvc.NewtonsoftJson\Microsoft.AspNetCore.Mvc.NewtonsoftJson.csproj", "{3FC8D9D6-9352-43A3-8E81-422F270085B7}" EndProject Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.AspNetCore.Mvc.Formatters.Xml", "src\Microsoft.AspNetCore.Mvc.Formatters.Xml\Microsoft.AspNetCore.Mvc.Formatters.Xml.csproj", "{42C81540-CD47-4C68-A7A3-2A93B9C3B210}" EndProject -Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.AspNetCore.Mvc.Formatters.Json.Test", "test\Microsoft.AspNetCore.Mvc.Formatters.Json.Test\Microsoft.AspNetCore.Mvc.Formatters.Json.Test.csproj", "{493780DA-E696-40FF-BD12-4A5C5736F292}" +Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test", "test\Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test\Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test.csproj", "{493780DA-E696-40FF-BD12-4A5C5736F292}" EndProject Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.AspNetCore.Mvc.Formatters.Xml.Test", "test\Microsoft.AspNetCore.Mvc.Formatters.Xml.Test\Microsoft.AspNetCore.Mvc.Formatters.Xml.Test.csproj", "{22019146-BDFA-442E-8C8E-345FB9644578}" EndProject diff --git a/src/Mvc/benchmarkapps/BasicApi/BasicApi.csproj b/src/Mvc/benchmarkapps/BasicApi/BasicApi.csproj index fc84deb124..9e7f952efb 100644 --- a/src/Mvc/benchmarkapps/BasicApi/BasicApi.csproj +++ b/src/Mvc/benchmarkapps/BasicApi/BasicApi.csproj @@ -24,7 +24,7 @@ - + diff --git a/src/Mvc/benchmarkapps/BasicApi/Startup.cs b/src/Mvc/benchmarkapps/BasicApi/Startup.cs index 52fa10105a..e1d5428d93 100644 --- a/src/Mvc/benchmarkapps/BasicApi/Startup.cs +++ b/src/Mvc/benchmarkapps/BasicApi/Startup.cs @@ -125,7 +125,7 @@ namespace BasicApi services .AddMvcCore() .AddAuthorization() - .AddJsonFormatters(json => json.ContractResolver = new CamelCasePropertyNamesContractResolver()) + .AddNewtonsoftJson(options => options.SerializerSettings.ContractResolver = new CamelCasePropertyNamesContractResolver()) .AddDataAnnotations(); } diff --git a/src/Mvc/benchmarks/Microsoft.AspNetCore.Mvc.Performance.Views/Microsoft.AspNetCore.Mvc.Performance.Views.csproj b/src/Mvc/benchmarks/Microsoft.AspNetCore.Mvc.Performance.Views/Microsoft.AspNetCore.Mvc.Performance.Views.csproj index b29ceedc03..22a5b9d99b 100644 --- a/src/Mvc/benchmarks/Microsoft.AspNetCore.Mvc.Performance.Views/Microsoft.AspNetCore.Mvc.Performance.Views.csproj +++ b/src/Mvc/benchmarks/Microsoft.AspNetCore.Mvc.Performance.Views/Microsoft.AspNetCore.Mvc.Performance.Views.csproj @@ -4,8 +4,6 @@ netcoreapp3.0 false - - <_EnableAllInclusiveRazorSdk>true true diff --git a/src/Mvc/samples/MvcSandbox/MvcSandbox.csproj b/src/Mvc/samples/MvcSandbox/MvcSandbox.csproj index 9f144737c6..3e0d928151 100644 --- a/src/Mvc/samples/MvcSandbox/MvcSandbox.csproj +++ b/src/Mvc/samples/MvcSandbox/MvcSandbox.csproj @@ -1,15 +1,12 @@ - + netcoreapp3.0 - - true - - + diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Abstractions/Properties/AssemblyInfo.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.Abstractions/Properties/AssemblyInfo.cs index f28aa5fed6..ae3b2c662b 100644 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Abstractions/Properties/AssemblyInfo.cs +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.Abstractions/Properties/AssemblyInfo.cs @@ -8,7 +8,6 @@ using System.Runtime.CompilerServices; [assembly: InternalsVisibleTo("Microsoft.AspNetCore.Mvc.Core, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] [assembly: InternalsVisibleTo("Microsoft.AspNetCore.Mvc.Cors, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] [assembly: InternalsVisibleTo("Microsoft.AspNetCore.Mvc.DataAnnotations, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] -[assembly: InternalsVisibleTo("Microsoft.AspNetCore.Mvc.Formatters.Json, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] [assembly: InternalsVisibleTo("Microsoft.AspNetCore.Mvc.Formatters.Xml, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] [assembly: InternalsVisibleTo("Microsoft.AspNetCore.Mvc.Localization, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] [assembly: InternalsVisibleTo("Microsoft.AspNetCore.Mvc.Razor, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] @@ -23,7 +22,6 @@ using System.Runtime.CompilerServices; [assembly: InternalsVisibleTo("Microsoft.AspNetCore.Mvc.Core.TestCommon, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] [assembly: InternalsVisibleTo("Microsoft.AspNetCore.Mvc.Cors.Test, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] [assembly: InternalsVisibleTo("Microsoft.AspNetCore.Mvc.DataAnnotations.Test, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] -[assembly: InternalsVisibleTo("Microsoft.AspNetCore.Mvc.Formatters.Json.Test, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] [assembly: InternalsVisibleTo("Microsoft.AspNetCore.Mvc.Formatters.Xml.Test, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] [assembly: InternalsVisibleTo("Microsoft.AspNetCore.Mvc.IntegrationTests, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] [assembly: InternalsVisibleTo("Microsoft.AspNetCore.Mvc.Localization.Test, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Core/ApplicationParts/ApplicationAssembliesProvider.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.Core/ApplicationParts/ApplicationAssembliesProvider.cs index b1d414a8ca..b8e54d1d0d 100644 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Core/ApplicationParts/ApplicationAssembliesProvider.cs +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.Core/ApplicationParts/ApplicationAssembliesProvider.cs @@ -24,9 +24,9 @@ namespace Microsoft.AspNetCore.Mvc.ApplicationParts "Microsoft.AspNetCore.Mvc.Core", "Microsoft.AspNetCore.Mvc.Cors", "Microsoft.AspNetCore.Mvc.DataAnnotations", - "Microsoft.AspNetCore.Mvc.Formatters.Json", "Microsoft.AspNetCore.Mvc.Formatters.Xml", "Microsoft.AspNetCore.Mvc.Localization", + "Microsoft.AspNetCore.Mvc.NewtonsoftJson", "Microsoft.AspNetCore.Mvc.Razor", "Microsoft.AspNetCore.Mvc.RazorPages", "Microsoft.AspNetCore.Mvc.TagHelpers", diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/JsonResult.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.Core/JsonResult.cs similarity index 72% rename from src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/JsonResult.cs rename to src/Mvc/src/Microsoft.AspNetCore.Mvc.Core/JsonResult.cs index 5abad92bff..ac0107311b 100644 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/JsonResult.cs +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.Core/JsonResult.cs @@ -3,10 +3,9 @@ using System; using System.Threading.Tasks; -using Microsoft.AspNetCore.Mvc.Formatters; +using Microsoft.AspNetCore.Mvc.Core; using Microsoft.AspNetCore.Mvc.Infrastructure; using Microsoft.Extensions.DependencyInjection; -using Newtonsoft.Json; namespace Microsoft.AspNetCore.Mvc { @@ -28,9 +27,8 @@ namespace Microsoft.AspNetCore.Mvc /// Creates a new with the given . /// /// The value to format as JSON. - /// The to be used by - /// the formatter. - public JsonResult(object value, JsonSerializerSettings serializerSettings) + /// The serializer settings to be used by the formatter. + public JsonResult(object value, object serializerSettings) { if (serializerSettings == null) { @@ -47,9 +45,9 @@ namespace Microsoft.AspNetCore.Mvc public string ContentType { get; set; } /// - /// Gets or sets the . + /// Gets or sets the serializer settings. /// - public JsonSerializerSettings SerializerSettings { get; set; } + public object SerializerSettings { get; set; } /// /// Gets or sets the HTTP status code. @@ -70,7 +68,17 @@ namespace Microsoft.AspNetCore.Mvc } var services = context.HttpContext.RequestServices; - var executor = services.GetRequiredService(); + var executor = services.GetService>(); + if (executor == null) + { + throw new InvalidOperationException(Resources.FormatReferenceToNewtonsoftJsonRequired( + $"{nameof(JsonResult)}.{nameof(ExecuteResultAsync)}", + "Microsoft.AspNetCore.Mvc.NewtonsoftJson", + nameof(IMvcBuilder), + "AddNewtonsoftJson", + "ConfigureServices(...)")); + } + return executor.ExecuteAsync(context, this); } } diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Core/ProblemDetails.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.Core/ProblemDetails.cs index 9d07004103..19691cae5c 100644 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Core/ProblemDetails.cs +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.Core/ProblemDetails.cs @@ -3,7 +3,6 @@ using System; using System.Collections.Generic; -using Newtonsoft.Json; namespace Microsoft.AspNetCore.Mvc { @@ -18,7 +17,6 @@ namespace Microsoft.AspNetCore.Mvc /// (e.g., using HTML [W3C.REC-html5-20141028]). When this member is not present, its value is assumed to be /// "about:blank". /// - [JsonProperty(NullValueHandling = NullValueHandling.Ignore, PropertyName = "type")] public string Type { get; set; } /// @@ -26,25 +24,21 @@ namespace Microsoft.AspNetCore.Mvc /// of the problem, except for purposes of localization(e.g., using proactive content negotiation; /// see[RFC7231], Section 3.4). /// - [JsonProperty(NullValueHandling = NullValueHandling.Ignore, PropertyName = "title")] public string Title { get; set; } /// /// The HTTP status code([RFC7231], Section 6) generated by the origin server for this occurrence of the problem. /// - [JsonProperty(NullValueHandling = NullValueHandling.Ignore, PropertyName = "status")] public int? Status { get; set; } /// /// A human-readable explanation specific to this occurrence of the problem. /// - [JsonProperty(NullValueHandling = NullValueHandling.Ignore, PropertyName = "detail")] public string Detail { get; set; } /// /// A URI reference that identifies the specific occurrence of the problem.It may or may not yield further information if dereferenced. /// - [JsonProperty(NullValueHandling = NullValueHandling.Ignore, PropertyName = "instance")] public string Instance { get; set; } /// @@ -58,7 +52,6 @@ namespace Microsoft.AspNetCore.Mvc /// The round-tripping behavior for is determined by the implementation of the Input \ Output formatters. /// In particular, complex types or collection types may not round-trip to the original type when using the built-in JSON or XML formatters. /// - [JsonExtensionData] public IDictionary Extensions { get; } = new Dictionary(StringComparer.Ordinal); } } diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Core/Properties/AssemblyInfo.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.Core/Properties/AssemblyInfo.cs index 14bede0243..526d0b26aa 100644 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Core/Properties/AssemblyInfo.cs +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.Core/Properties/AssemblyInfo.cs @@ -10,7 +10,6 @@ using Microsoft.AspNetCore.Mvc.Formatters; [assembly: InternalsVisibleTo("Microsoft.AspNetCore.Mvc.ApiExplorer, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] [assembly: InternalsVisibleTo("Microsoft.AspNetCore.Mvc.Cors, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] [assembly: InternalsVisibleTo("Microsoft.AspNetCore.Mvc.DataAnnotations, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] -[assembly: InternalsVisibleTo("Microsoft.AspNetCore.Mvc.Formatters.Json, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] [assembly: InternalsVisibleTo("Microsoft.AspNetCore.Mvc.Formatters.Xml, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] [assembly: InternalsVisibleTo("Microsoft.AspNetCore.Mvc.Localization, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] [assembly: InternalsVisibleTo("Microsoft.AspNetCore.Mvc.Razor, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] @@ -25,7 +24,6 @@ using Microsoft.AspNetCore.Mvc.Formatters; [assembly: InternalsVisibleTo("Microsoft.AspNetCore.Mvc.Core.TestCommon, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] [assembly: InternalsVisibleTo("Microsoft.AspNetCore.Mvc.Cors.Test, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] [assembly: InternalsVisibleTo("Microsoft.AspNetCore.Mvc.DataAnnotations.Test, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] -[assembly: InternalsVisibleTo("Microsoft.AspNetCore.Mvc.Formatters.Json.Test, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] [assembly: InternalsVisibleTo("Microsoft.AspNetCore.Mvc.Formatters.Xml.Test, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] [assembly: InternalsVisibleTo("Microsoft.AspNetCore.Mvc.IntegrationTests, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] [assembly: InternalsVisibleTo("Microsoft.AspNetCore.Mvc.Localization.Test, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Core/Properties/Resources.Designer.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.Core/Properties/Resources.Designer.cs index 8acff61ab2..0aff98e8f3 100644 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Core/Properties/Resources.Designer.cs +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.Core/Properties/Resources.Designer.cs @@ -1690,6 +1690,20 @@ namespace Microsoft.AspNetCore.Mvc.Core internal static string FormatApiConventions_Title_422() => GetString("ApiConventions_Title_422"); + /// + /// '{0}' requires a reference to '{1}'. Configure your application by adding a reference to the '{1}' package and calling '{2}.{3}' inside the call to '{4}' in the application startup code. + /// + internal static string ReferenceToNewtonsoftJsonRequired + { + get => GetString("ReferenceToNewtonsoftJsonRequired"); + } + + /// + /// '{0}' requires a reference to '{1}'. Configure your application by adding a reference to the '{1}' package and calling '{2}.{3}' inside the call to '{4}' in the application startup code. + /// + internal static string FormatReferenceToNewtonsoftJsonRequired(object p0, object p1, object p2, object p3, object p4) + => string.Format(CultureInfo.CurrentCulture, GetString("ReferenceToNewtonsoftJsonRequired"), p0, p1, p2, p3, p4); + private static string GetString(string name, params string[] formatterNames) { var value = _resourceManager.GetString(name); diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Core/Resources.resx b/src/Mvc/src/Microsoft.AspNetCore.Mvc.Core/Resources.resx index f1d2e78ade..820d111536 100644 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Core/Resources.resx +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.Core/Resources.resx @@ -490,4 +490,7 @@ Unprocessable Entity + + '{0}' requires a reference to '{1}'. Configure your application by adding a reference to the '{1}' package and calling '{2}.{3}' inside the call to '{4}' in the application startup code. + \ No newline at end of file diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Core/ValidationProblemDetails.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.Core/ValidationProblemDetails.cs index 56fdd49e9d..64f922a16c 100644 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Core/ValidationProblemDetails.cs +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.Core/ValidationProblemDetails.cs @@ -5,7 +5,6 @@ using System; using System.Collections.Generic; using Microsoft.AspNetCore.Mvc.Core; using Microsoft.AspNetCore.Mvc.ModelBinding; -using Newtonsoft.Json; namespace Microsoft.AspNetCore.Mvc { @@ -84,7 +83,6 @@ namespace Microsoft.AspNetCore.Mvc /// /// Gets the validation errors associated with this instance of . /// - [JsonProperty(PropertyName = "errors")] public IDictionary Errors { get; } = new Dictionary(StringComparer.Ordinal); } } diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/DependencyInjection/MvcJsonMvcBuilderExtensions.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/DependencyInjection/MvcJsonMvcBuilderExtensions.cs deleted file mode 100644 index 93e7bc7e40..0000000000 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/DependencyInjection/MvcJsonMvcBuilderExtensions.cs +++ /dev/null @@ -1,37 +0,0 @@ -// Copyright (c) .NET Foundation. All rights reserved. -// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information. - -using System; -using Microsoft.AspNetCore.Mvc; - -namespace Microsoft.Extensions.DependencyInjection -{ - /// - /// Extensions methods for configuring MVC via an . - /// - public static class MvcJsonMvcBuilderExtensions - { - /// - /// Adds configuration of for the application. - /// - /// The . - /// The which need to be configured. - public static IMvcBuilder AddJsonOptions( - this IMvcBuilder builder, - Action setupAction) - { - if (builder == null) - { - throw new ArgumentNullException(nameof(builder)); - } - - if (setupAction == null) - { - throw new ArgumentNullException(nameof(setupAction)); - } - - builder.Services.Configure(setupAction); - return builder; - } - } -} diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/DependencyInjection/MvcJsonMvcCoreBuilderExtensions.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/DependencyInjection/MvcJsonMvcCoreBuilderExtensions.cs deleted file mode 100644 index 4585cbb218..0000000000 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/DependencyInjection/MvcJsonMvcCoreBuilderExtensions.cs +++ /dev/null @@ -1,85 +0,0 @@ -// Copyright (c) .NET Foundation. All rights reserved. -// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information. - -using System; -using Microsoft.AspNetCore.Mvc; -using Microsoft.AspNetCore.Mvc.ApiExplorer; -using Microsoft.AspNetCore.Mvc.Formatters; -using Microsoft.AspNetCore.Mvc.Formatters.Json; -using Microsoft.Extensions.DependencyInjection.Extensions; -using Microsoft.Extensions.ObjectPool; -using Microsoft.Extensions.Options; -using Newtonsoft.Json; - -namespace Microsoft.Extensions.DependencyInjection -{ - public static class MvcJsonMvcCoreBuilderExtensions - { - public static IMvcCoreBuilder AddJsonFormatters(this IMvcCoreBuilder builder) - { - if (builder == null) - { - throw new ArgumentNullException(nameof(builder)); - } - - AddJsonFormatterServices(builder.Services); - return builder; - } - - public static IMvcCoreBuilder AddJsonFormatters( - this IMvcCoreBuilder builder, - Action setupAction) - { - if (builder == null) - { - throw new ArgumentNullException(nameof(builder)); - } - - if (setupAction == null) - { - throw new ArgumentNullException(nameof(setupAction)); - } - - AddJsonFormatterServices(builder.Services); - - builder.Services.Configure((options) => setupAction(options.SerializerSettings)); - - return builder; - } - - /// - /// Adds configuration of for the application. - /// - /// The . - /// The which need to be configured. - /// The . - public static IMvcCoreBuilder AddJsonOptions( - this IMvcCoreBuilder builder, - Action setupAction) - { - if (builder == null) - { - throw new ArgumentNullException(nameof(builder)); - } - - if (setupAction == null) - { - throw new ArgumentNullException(nameof(setupAction)); - } - - builder.Services.Configure(setupAction); - return builder; - } - - // Internal for testing. - internal static void AddJsonFormatterServices(IServiceCollection services) - { - services.TryAddSingleton(); - services.TryAddEnumerable( - ServiceDescriptor.Transient, MvcJsonMvcOptionsSetup>()); - services.TryAddEnumerable( - ServiceDescriptor.Transient()); - services.TryAddSingleton(); - } - } -} diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/Properties/Resources.Designer.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/Properties/Resources.Designer.cs deleted file mode 100644 index b552db2345..0000000000 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/Properties/Resources.Designer.cs +++ /dev/null @@ -1,58 +0,0 @@ -// -namespace Microsoft.AspNetCore.Mvc.Formatters.Json -{ - using System.Globalization; - using System.Reflection; - using System.Resources; - - internal static class Resources - { - private static readonly ResourceManager _resourceManager - = new ResourceManager("Microsoft.AspNetCore.Mvc.Formatters.Json.Resources", typeof(Resources).GetTypeInfo().Assembly); - - /// - /// {0} cannot be null. - /// - internal static string ContractResolverCannotBeNull - { - get => GetString("ContractResolverCannotBeNull"); - } - - /// - /// {0} cannot be null. - /// - internal static string FormatContractResolverCannotBeNull(object p0) - => string.Format(CultureInfo.CurrentCulture, GetString("ContractResolverCannotBeNull"), p0); - - /// - /// Cannot configure JSON casing behavior on '{0}' contract resolver. The supported contract resolver is {1}. - /// - internal static string InvalidContractResolverForJsonCasingConfiguration - { - get => GetString("InvalidContractResolverForJsonCasingConfiguration"); - } - - /// - /// Cannot configure JSON casing behavior on '{0}' contract resolver. The supported contract resolver is {1}. - /// - internal static string FormatInvalidContractResolverForJsonCasingConfiguration(object p0, object p1) - => string.Format(CultureInfo.CurrentCulture, GetString("InvalidContractResolverForJsonCasingConfiguration"), p0, p1); - - private static string GetString(string name, params string[] formatterNames) - { - var value = _resourceManager.GetString(name); - - System.Diagnostics.Debug.Assert(value != null); - - if (formatterNames != null) - { - for (var i = 0; i < formatterNames.Length; i++) - { - value = value.Replace("{" + formatterNames[i] + "}", "{" + i + "}"); - } - } - - return value; - } - } -} diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/baseline.netcore.json b/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/baseline.netcore.json deleted file mode 100644 index 9a1c0bda85..0000000000 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/baseline.netcore.json +++ /dev/null @@ -1,910 +0,0 @@ -{ - "AssemblyIdentity": "Microsoft.AspNetCore.Mvc.Formatters.Json, Version=2.1.1.0, Culture=neutral, PublicKeyToken=adb9793829ddae60", - "Types": [ - { - "Name": "Microsoft.AspNetCore.Mvc.JsonPatchExtensions", - "Visibility": "Public", - "Kind": "Class", - "Abstract": true, - "Static": true, - "Sealed": true, - "ImplementedInterfaces": [], - "Members": [ - { - "Kind": "Method", - "Name": "ApplyTo", - "Parameters": [ - { - "Name": "patchDoc", - "Type": "Microsoft.AspNetCore.JsonPatch.JsonPatchDocument" - }, - { - "Name": "objectToApplyTo", - "Type": "T0" - }, - { - "Name": "modelState", - "Type": "Microsoft.AspNetCore.Mvc.ModelBinding.ModelStateDictionary" - } - ], - "ReturnType": "System.Void", - "Static": true, - "Extension": true, - "Visibility": "Public", - "GenericParameter": [ - { - "ParameterName": "T", - "ParameterPosition": 0, - "Class": true, - "BaseTypeOrInterfaces": [] - } - ] - }, - { - "Kind": "Method", - "Name": "ApplyTo", - "Parameters": [ - { - "Name": "patchDoc", - "Type": "Microsoft.AspNetCore.JsonPatch.JsonPatchDocument" - }, - { - "Name": "objectToApplyTo", - "Type": "T0" - }, - { - "Name": "modelState", - "Type": "Microsoft.AspNetCore.Mvc.ModelBinding.ModelStateDictionary" - }, - { - "Name": "prefix", - "Type": "System.String" - } - ], - "ReturnType": "System.Void", - "Static": true, - "Extension": true, - "Visibility": "Public", - "GenericParameter": [ - { - "ParameterName": "T", - "ParameterPosition": 0, - "Class": true, - "BaseTypeOrInterfaces": [] - } - ] - } - ], - "GenericParameters": [] - }, - { - "Name": "Microsoft.AspNetCore.Mvc.JsonResult", - "Visibility": "Public", - "Kind": "Class", - "BaseType": "Microsoft.AspNetCore.Mvc.ActionResult", - "ImplementedInterfaces": [], - "Members": [ - { - "Kind": "Method", - "Name": "ExecuteResultAsync", - "Parameters": [ - { - "Name": "context", - "Type": "Microsoft.AspNetCore.Mvc.ActionContext" - } - ], - "ReturnType": "System.Threading.Tasks.Task", - "Virtual": true, - "Override": true, - "ImplementedInterface": "Microsoft.AspNetCore.Mvc.IActionResult", - "Visibility": "Public", - "GenericParameter": [] - }, - { - "Kind": "Method", - "Name": "get_ContentType", - "Parameters": [], - "ReturnType": "System.String", - "Visibility": "Public", - "GenericParameter": [] - }, - { - "Kind": "Method", - "Name": "set_ContentType", - "Parameters": [ - { - "Name": "value", - "Type": "System.String" - } - ], - "ReturnType": "System.Void", - "Visibility": "Public", - "GenericParameter": [] - }, - { - "Kind": "Method", - "Name": "get_SerializerSettings", - "Parameters": [], - "ReturnType": "Newtonsoft.Json.JsonSerializerSettings", - "Visibility": "Public", - "GenericParameter": [] - }, - { - "Kind": "Method", - "Name": "set_SerializerSettings", - "Parameters": [ - { - "Name": "value", - "Type": "Newtonsoft.Json.JsonSerializerSettings" - } - ], - "ReturnType": "System.Void", - "Visibility": "Public", - "GenericParameter": [] - }, - { - "Kind": "Method", - "Name": "get_StatusCode", - "Parameters": [], - "ReturnType": "System.Nullable", - "Visibility": "Public", - "GenericParameter": [] - }, - { - "Kind": "Method", - "Name": "set_StatusCode", - "Parameters": [ - { - "Name": "value", - "Type": "System.Nullable" - } - ], - "ReturnType": "System.Void", - "Visibility": "Public", - "GenericParameter": [] - }, - { - "Kind": "Method", - "Name": "get_Value", - "Parameters": [], - "ReturnType": "System.Object", - "Visibility": "Public", - "GenericParameter": [] - }, - { - "Kind": "Method", - "Name": "set_Value", - "Parameters": [ - { - "Name": "value", - "Type": "System.Object" - } - ], - "ReturnType": "System.Void", - "Visibility": "Public", - "GenericParameter": [] - }, - { - "Kind": "Constructor", - "Name": ".ctor", - "Parameters": [ - { - "Name": "value", - "Type": "System.Object" - } - ], - "Visibility": "Public", - "GenericParameter": [] - }, - { - "Kind": "Constructor", - "Name": ".ctor", - "Parameters": [ - { - "Name": "value", - "Type": "System.Object" - }, - { - "Name": "serializerSettings", - "Type": "Newtonsoft.Json.JsonSerializerSettings" - } - ], - "Visibility": "Public", - "GenericParameter": [] - } - ], - "GenericParameters": [] - }, - { - "Name": "Microsoft.AspNetCore.Mvc.MvcJsonOptions", - "Visibility": "Public", - "Kind": "Class", - "ImplementedInterfaces": [ - "System.Collections.Generic.IEnumerable" - ], - "Members": [ - { - "Kind": "Method", - "Name": "get_AllowInputFormatterExceptionMessages", - "Parameters": [], - "ReturnType": "System.Boolean", - "Visibility": "Public", - "GenericParameter": [] - }, - { - "Kind": "Method", - "Name": "set_AllowInputFormatterExceptionMessages", - "Parameters": [ - { - "Name": "value", - "Type": "System.Boolean" - } - ], - "ReturnType": "System.Void", - "Visibility": "Public", - "GenericParameter": [] - }, - { - "Kind": "Method", - "Name": "get_SerializerSettings", - "Parameters": [], - "ReturnType": "Newtonsoft.Json.JsonSerializerSettings", - "Visibility": "Public", - "GenericParameter": [] - }, - { - "Kind": "Constructor", - "Name": ".ctor", - "Parameters": [], - "Visibility": "Public", - "GenericParameter": [] - } - ], - "GenericParameters": [] - }, - { - "Name": "Microsoft.AspNetCore.Mvc.Formatters.JsonInputFormatter", - "Visibility": "Public", - "Kind": "Class", - "BaseType": "Microsoft.AspNetCore.Mvc.Formatters.TextInputFormatter", - "ImplementedInterfaces": [ - "Microsoft.AspNetCore.Mvc.Formatters.IInputFormatterExceptionPolicy" - ], - "Members": [ - { - "Kind": "Method", - "Name": "get_ExceptionPolicy", - "Parameters": [], - "ReturnType": "Microsoft.AspNetCore.Mvc.Formatters.InputFormatterExceptionPolicy", - "Virtual": true, - "ImplementedInterface": "Microsoft.AspNetCore.Mvc.Formatters.IInputFormatterExceptionPolicy", - "Visibility": "Public", - "GenericParameter": [] - }, - { - "Kind": "Method", - "Name": "get_SerializerSettings", - "Parameters": [], - "ReturnType": "Newtonsoft.Json.JsonSerializerSettings", - "Visibility": "Protected", - "GenericParameter": [] - }, - { - "Kind": "Method", - "Name": "ReadRequestBodyAsync", - "Parameters": [ - { - "Name": "context", - "Type": "Microsoft.AspNetCore.Mvc.Formatters.InputFormatterContext" - }, - { - "Name": "encoding", - "Type": "System.Text.Encoding" - } - ], - "ReturnType": "System.Threading.Tasks.Task", - "Virtual": true, - "Override": true, - "Visibility": "Public", - "GenericParameter": [] - }, - { - "Kind": "Method", - "Name": "CreateJsonSerializer", - "Parameters": [], - "ReturnType": "Newtonsoft.Json.JsonSerializer", - "Virtual": true, - "Visibility": "Protected", - "GenericParameter": [] - }, - { - "Kind": "Method", - "Name": "ReleaseJsonSerializer", - "Parameters": [ - { - "Name": "serializer", - "Type": "Newtonsoft.Json.JsonSerializer" - } - ], - "ReturnType": "System.Void", - "Virtual": true, - "Visibility": "Protected", - "GenericParameter": [] - }, - { - "Kind": "Constructor", - "Name": ".ctor", - "Parameters": [ - { - "Name": "logger", - "Type": "Microsoft.Extensions.Logging.ILogger" - }, - { - "Name": "serializerSettings", - "Type": "Newtonsoft.Json.JsonSerializerSettings" - }, - { - "Name": "charPool", - "Type": "System.Buffers.ArrayPool" - }, - { - "Name": "objectPoolProvider", - "Type": "Microsoft.Extensions.ObjectPool.ObjectPoolProvider" - } - ], - "Visibility": "Public", - "GenericParameter": [] - }, - { - "Kind": "Constructor", - "Name": ".ctor", - "Parameters": [ - { - "Name": "logger", - "Type": "Microsoft.Extensions.Logging.ILogger" - }, - { - "Name": "serializerSettings", - "Type": "Newtonsoft.Json.JsonSerializerSettings" - }, - { - "Name": "charPool", - "Type": "System.Buffers.ArrayPool" - }, - { - "Name": "objectPoolProvider", - "Type": "Microsoft.Extensions.ObjectPool.ObjectPoolProvider" - }, - { - "Name": "suppressInputFormatterBuffering", - "Type": "System.Boolean" - } - ], - "Visibility": "Public", - "GenericParameter": [] - }, - { - "Kind": "Constructor", - "Name": ".ctor", - "Parameters": [ - { - "Name": "logger", - "Type": "Microsoft.Extensions.Logging.ILogger" - }, - { - "Name": "serializerSettings", - "Type": "Newtonsoft.Json.JsonSerializerSettings" - }, - { - "Name": "charPool", - "Type": "System.Buffers.ArrayPool" - }, - { - "Name": "objectPoolProvider", - "Type": "Microsoft.Extensions.ObjectPool.ObjectPoolProvider" - }, - { - "Name": "suppressInputFormatterBuffering", - "Type": "System.Boolean" - }, - { - "Name": "allowInputFormatterExceptionMessages", - "Type": "System.Boolean" - } - ], - "Visibility": "Public", - "GenericParameter": [] - }, - { - "Kind": "Constructor", - "Name": ".ctor", - "Parameters": [ - { - "Name": "logger", - "Type": "Microsoft.Extensions.Logging.ILogger" - }, - { - "Name": "serializerSettings", - "Type": "Newtonsoft.Json.JsonSerializerSettings" - }, - { - "Name": "charPool", - "Type": "System.Buffers.ArrayPool" - }, - { - "Name": "objectPoolProvider", - "Type": "Microsoft.Extensions.ObjectPool.ObjectPoolProvider" - }, - { - "Name": "options", - "Type": "Microsoft.AspNetCore.Mvc.MvcOptions" - }, - { - "Name": "jsonOptions", - "Type": "Microsoft.AspNetCore.Mvc.MvcJsonOptions" - } - ], - "Visibility": "Public", - "GenericParameter": [] - } - ], - "GenericParameters": [] - }, - { - "Name": "Microsoft.AspNetCore.Mvc.Formatters.JsonOutputFormatter", - "Visibility": "Public", - "Kind": "Class", - "BaseType": "Microsoft.AspNetCore.Mvc.Formatters.TextOutputFormatter", - "ImplementedInterfaces": [], - "Members": [ - { - "Kind": "Method", - "Name": "get_SerializerSettings", - "Parameters": [], - "ReturnType": "Newtonsoft.Json.JsonSerializerSettings", - "Visibility": "Protected", - "GenericParameter": [] - }, - { - "Kind": "Method", - "Name": "get_PublicSerializerSettings", - "Parameters": [], - "ReturnType": "Newtonsoft.Json.JsonSerializerSettings", - "Visibility": "Public", - "GenericParameter": [] - }, - { - "Kind": "Method", - "Name": "WriteObject", - "Parameters": [ - { - "Name": "writer", - "Type": "System.IO.TextWriter" - }, - { - "Name": "value", - "Type": "System.Object" - } - ], - "ReturnType": "System.Void", - "Visibility": "Public", - "GenericParameter": [] - }, - { - "Kind": "Method", - "Name": "CreateJsonWriter", - "Parameters": [ - { - "Name": "writer", - "Type": "System.IO.TextWriter" - } - ], - "ReturnType": "Newtonsoft.Json.JsonWriter", - "Virtual": true, - "Visibility": "Protected", - "GenericParameter": [] - }, - { - "Kind": "Method", - "Name": "CreateJsonSerializer", - "Parameters": [], - "ReturnType": "Newtonsoft.Json.JsonSerializer", - "Virtual": true, - "Visibility": "Protected", - "GenericParameter": [] - }, - { - "Kind": "Method", - "Name": "WriteResponseBodyAsync", - "Parameters": [ - { - "Name": "context", - "Type": "Microsoft.AspNetCore.Mvc.Formatters.OutputFormatterWriteContext" - }, - { - "Name": "selectedEncoding", - "Type": "System.Text.Encoding" - } - ], - "ReturnType": "System.Threading.Tasks.Task", - "Virtual": true, - "Override": true, - "Visibility": "Public", - "GenericParameter": [] - }, - { - "Kind": "Constructor", - "Name": ".ctor", - "Parameters": [ - { - "Name": "serializerSettings", - "Type": "Newtonsoft.Json.JsonSerializerSettings" - }, - { - "Name": "charPool", - "Type": "System.Buffers.ArrayPool" - } - ], - "Visibility": "Public", - "GenericParameter": [] - } - ], - "GenericParameters": [] - }, - { - "Name": "Microsoft.AspNetCore.Mvc.Formatters.JsonPatchInputFormatter", - "Visibility": "Public", - "Kind": "Class", - "BaseType": "Microsoft.AspNetCore.Mvc.Formatters.JsonInputFormatter", - "ImplementedInterfaces": [], - "Members": [ - { - "Kind": "Method", - "Name": "CanRead", - "Parameters": [ - { - "Name": "context", - "Type": "Microsoft.AspNetCore.Mvc.Formatters.InputFormatterContext" - } - ], - "ReturnType": "System.Boolean", - "Virtual": true, - "Override": true, - "ImplementedInterface": "Microsoft.AspNetCore.Mvc.Formatters.IInputFormatter", - "Visibility": "Public", - "GenericParameter": [] - }, - { - "Kind": "Method", - "Name": "get_ExceptionPolicy", - "Parameters": [], - "ReturnType": "Microsoft.AspNetCore.Mvc.Formatters.InputFormatterExceptionPolicy", - "Virtual": true, - "Override": true, - "ImplementedInterface": "Microsoft.AspNetCore.Mvc.Formatters.IInputFormatterExceptionPolicy", - "Visibility": "Public", - "GenericParameter": [] - }, - { - "Kind": "Method", - "Name": "ReadRequestBodyAsync", - "Parameters": [ - { - "Name": "context", - "Type": "Microsoft.AspNetCore.Mvc.Formatters.InputFormatterContext" - }, - { - "Name": "encoding", - "Type": "System.Text.Encoding" - } - ], - "ReturnType": "System.Threading.Tasks.Task", - "Virtual": true, - "Override": true, - "Visibility": "Public", - "GenericParameter": [] - }, - { - "Kind": "Constructor", - "Name": ".ctor", - "Parameters": [ - { - "Name": "logger", - "Type": "Microsoft.Extensions.Logging.ILogger" - }, - { - "Name": "serializerSettings", - "Type": "Newtonsoft.Json.JsonSerializerSettings" - }, - { - "Name": "charPool", - "Type": "System.Buffers.ArrayPool" - }, - { - "Name": "objectPoolProvider", - "Type": "Microsoft.Extensions.ObjectPool.ObjectPoolProvider" - } - ], - "Visibility": "Public", - "GenericParameter": [] - }, - { - "Kind": "Constructor", - "Name": ".ctor", - "Parameters": [ - { - "Name": "logger", - "Type": "Microsoft.Extensions.Logging.ILogger" - }, - { - "Name": "serializerSettings", - "Type": "Newtonsoft.Json.JsonSerializerSettings" - }, - { - "Name": "charPool", - "Type": "System.Buffers.ArrayPool" - }, - { - "Name": "objectPoolProvider", - "Type": "Microsoft.Extensions.ObjectPool.ObjectPoolProvider" - }, - { - "Name": "suppressInputFormatterBuffering", - "Type": "System.Boolean" - } - ], - "Visibility": "Public", - "GenericParameter": [] - }, - { - "Kind": "Constructor", - "Name": ".ctor", - "Parameters": [ - { - "Name": "logger", - "Type": "Microsoft.Extensions.Logging.ILogger" - }, - { - "Name": "serializerSettings", - "Type": "Newtonsoft.Json.JsonSerializerSettings" - }, - { - "Name": "charPool", - "Type": "System.Buffers.ArrayPool" - }, - { - "Name": "objectPoolProvider", - "Type": "Microsoft.Extensions.ObjectPool.ObjectPoolProvider" - }, - { - "Name": "suppressInputFormatterBuffering", - "Type": "System.Boolean" - }, - { - "Name": "allowInputFormatterExceptionMessages", - "Type": "System.Boolean" - } - ], - "Visibility": "Public", - "GenericParameter": [] - }, - { - "Kind": "Constructor", - "Name": ".ctor", - "Parameters": [ - { - "Name": "logger", - "Type": "Microsoft.Extensions.Logging.ILogger" - }, - { - "Name": "serializerSettings", - "Type": "Newtonsoft.Json.JsonSerializerSettings" - }, - { - "Name": "charPool", - "Type": "System.Buffers.ArrayPool" - }, - { - "Name": "objectPoolProvider", - "Type": "Microsoft.Extensions.ObjectPool.ObjectPoolProvider" - }, - { - "Name": "options", - "Type": "Microsoft.AspNetCore.Mvc.MvcOptions" - }, - { - "Name": "jsonOptions", - "Type": "Microsoft.AspNetCore.Mvc.MvcJsonOptions" - } - ], - "Visibility": "Public", - "GenericParameter": [] - } - ], - "GenericParameters": [] - }, - { - "Name": "Microsoft.AspNetCore.Mvc.Formatters.JsonSerializerSettingsProvider", - "Visibility": "Public", - "Kind": "Class", - "Abstract": true, - "Static": true, - "Sealed": true, - "ImplementedInterfaces": [], - "Members": [ - { - "Kind": "Method", - "Name": "CreateSerializerSettings", - "Parameters": [], - "ReturnType": "Newtonsoft.Json.JsonSerializerSettings", - "Static": true, - "Visibility": "Public", - "GenericParameter": [] - } - ], - "GenericParameters": [] - }, - { - "Name": "Microsoft.AspNetCore.Mvc.Formatters.Json.JsonPatchOperationsArrayProvider", - "Visibility": "Public", - "Kind": "Class", - "ImplementedInterfaces": [ - "Microsoft.AspNetCore.Mvc.ApiExplorer.IApiDescriptionProvider" - ], - "Members": [ - { - "Kind": "Method", - "Name": "get_Order", - "Parameters": [], - "ReturnType": "System.Int32", - "Sealed": true, - "Virtual": true, - "ImplementedInterface": "Microsoft.AspNetCore.Mvc.ApiExplorer.IApiDescriptionProvider", - "Visibility": "Public", - "GenericParameter": [] - }, - { - "Kind": "Method", - "Name": "OnProvidersExecuting", - "Parameters": [ - { - "Name": "context", - "Type": "Microsoft.AspNetCore.Mvc.ApiExplorer.ApiDescriptionProviderContext" - } - ], - "ReturnType": "System.Void", - "Sealed": true, - "Virtual": true, - "ImplementedInterface": "Microsoft.AspNetCore.Mvc.ApiExplorer.IApiDescriptionProvider", - "Visibility": "Public", - "GenericParameter": [] - }, - { - "Kind": "Method", - "Name": "OnProvidersExecuted", - "Parameters": [ - { - "Name": "context", - "Type": "Microsoft.AspNetCore.Mvc.ApiExplorer.ApiDescriptionProviderContext" - } - ], - "ReturnType": "System.Void", - "Sealed": true, - "Virtual": true, - "ImplementedInterface": "Microsoft.AspNetCore.Mvc.ApiExplorer.IApiDescriptionProvider", - "Visibility": "Public", - "GenericParameter": [] - }, - { - "Kind": "Constructor", - "Name": ".ctor", - "Parameters": [ - { - "Name": "modelMetadataProvider", - "Type": "Microsoft.AspNetCore.Mvc.ModelBinding.IModelMetadataProvider" - } - ], - "Visibility": "Public", - "GenericParameter": [] - } - ], - "GenericParameters": [] - }, - { - "Name": "Microsoft.Extensions.DependencyInjection.MvcJsonMvcBuilderExtensions", - "Visibility": "Public", - "Kind": "Class", - "Abstract": true, - "Static": true, - "Sealed": true, - "ImplementedInterfaces": [], - "Members": [ - { - "Kind": "Method", - "Name": "AddJsonOptions", - "Parameters": [ - { - "Name": "builder", - "Type": "Microsoft.Extensions.DependencyInjection.IMvcBuilder" - }, - { - "Name": "setupAction", - "Type": "System.Action" - } - ], - "ReturnType": "Microsoft.Extensions.DependencyInjection.IMvcBuilder", - "Static": true, - "Extension": true, - "Visibility": "Public", - "GenericParameter": [] - } - ], - "GenericParameters": [] - }, - { - "Name": "Microsoft.Extensions.DependencyInjection.MvcJsonMvcCoreBuilderExtensions", - "Visibility": "Public", - "Kind": "Class", - "Abstract": true, - "Static": true, - "Sealed": true, - "ImplementedInterfaces": [], - "Members": [ - { - "Kind": "Method", - "Name": "AddJsonFormatters", - "Parameters": [ - { - "Name": "builder", - "Type": "Microsoft.Extensions.DependencyInjection.IMvcCoreBuilder" - } - ], - "ReturnType": "Microsoft.Extensions.DependencyInjection.IMvcCoreBuilder", - "Static": true, - "Extension": true, - "Visibility": "Public", - "GenericParameter": [] - }, - { - "Kind": "Method", - "Name": "AddJsonFormatters", - "Parameters": [ - { - "Name": "builder", - "Type": "Microsoft.Extensions.DependencyInjection.IMvcCoreBuilder" - }, - { - "Name": "setupAction", - "Type": "System.Action" - } - ], - "ReturnType": "Microsoft.Extensions.DependencyInjection.IMvcCoreBuilder", - "Static": true, - "Extension": true, - "Visibility": "Public", - "GenericParameter": [] - }, - { - "Kind": "Method", - "Name": "AddJsonOptions", - "Parameters": [ - { - "Name": "builder", - "Type": "Microsoft.Extensions.DependencyInjection.IMvcCoreBuilder" - }, - { - "Name": "setupAction", - "Type": "System.Action" - } - ], - "ReturnType": "Microsoft.Extensions.DependencyInjection.IMvcCoreBuilder", - "Static": true, - "Extension": true, - "Visibility": "Public", - "GenericParameter": [] - } - ], - "GenericParameters": [] - } - ] -} \ No newline at end of file diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/AnnotatedProblemDetails.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/AnnotatedProblemDetails.cs new file mode 100644 index 0000000000..1faf982d9f --- /dev/null +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/AnnotatedProblemDetails.cs @@ -0,0 +1,63 @@ +// Copyright (c) .NET Foundation. All rights reserved. +// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information. + +using System; +using System.Collections.Generic; +using Newtonsoft.Json; + +namespace Microsoft.AspNetCore.Mvc.NewtonsoftJson +{ + internal class AnnotatedProblemDetails + { + /// + /// Required for JSON.NET deserialization. + /// + public AnnotatedProblemDetails() { } + + public AnnotatedProblemDetails(ProblemDetails problemDetails) + { + Detail = problemDetails.Detail; + Instance = problemDetails.Instance; + Status = problemDetails.Status; + Title = problemDetails.Title; + Type = problemDetails.Type; + + foreach (var kvp in problemDetails.Extensions) + { + Extensions[kvp.Key] = kvp.Value; + } + } + + [JsonProperty(PropertyName = "type", NullValueHandling = NullValueHandling.Ignore)] + public string Type { get; set; } + + [JsonProperty(PropertyName = "title", NullValueHandling = NullValueHandling.Ignore)] + public string Title { get; set; } + + [JsonProperty(PropertyName = "status", NullValueHandling = NullValueHandling.Ignore)] + public int? Status { get; set; } + + [JsonProperty(PropertyName = "detail", NullValueHandling = NullValueHandling.Ignore)] + public string Detail { get; set; } + + [JsonProperty(PropertyName = "instance", NullValueHandling = NullValueHandling.Ignore)] + public string Instance { get; set; } + + [JsonExtensionData] + public IDictionary Extensions { get; } = new Dictionary(StringComparer.Ordinal); + + public void CopyTo(ProblemDetails problemDetails) + { + problemDetails.Type = Type; + problemDetails.Title = Title; + problemDetails.Status = Status; + problemDetails.Instance = Instance; + problemDetails.Detail = Detail; + + foreach (var kvp in Extensions) + { + problemDetails.Extensions[kvp.Key] = kvp.Value; + } + } + } +} diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Filters/TempDataSerializer.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/BsonTempDataSerializer.cs similarity index 93% rename from src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Filters/TempDataSerializer.cs rename to src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/BsonTempDataSerializer.cs index 244ea1f94e..302c1b813b 100644 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Filters/TempDataSerializer.cs +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/BsonTempDataSerializer.cs @@ -8,22 +8,22 @@ using System.Diagnostics; using System.IO; using System.Linq; using System.Reflection; -using Microsoft.AspNetCore.Mvc.Formatters; +using Microsoft.AspNetCore.Mvc.ViewFeatures.Infrastructure; using Microsoft.Extensions.Internal; using Newtonsoft.Json; using Newtonsoft.Json.Bson; using Newtonsoft.Json.Linq; -namespace Microsoft.AspNetCore.Mvc.ViewFeatures.Filters +namespace Microsoft.AspNetCore.Mvc.NewtonsoftJson { - internal class TempDataSerializer + internal class BsonTempDataSerializer : TempDataSerializer { private readonly JsonSerializer _jsonSerializer = JsonSerializer.Create(JsonSerializerSettingsProvider.CreateSerializerSettings()); - private static readonly MethodInfo _convertArrayMethodInfo = typeof(TempDataSerializer).GetMethod( + private static readonly MethodInfo _convertArrayMethodInfo = typeof(BsonTempDataSerializer).GetMethod( nameof(ConvertArray), BindingFlags.Static | BindingFlags.NonPublic); - private static readonly MethodInfo _convertDictionaryMethodInfo = typeof(TempDataSerializer).GetMethod( + private static readonly MethodInfo _convertDictionaryMethodInfo = typeof(BsonTempDataSerializer).GetMethod( nameof(ConvertDictionary), BindingFlags.Static | BindingFlags.NonPublic); private static readonly ConcurrentDictionary> _arrayConverters = @@ -43,7 +43,7 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures.Filters { JTokenType.Uri, typeof(Uri) }, }; - public IDictionary Deserialize(byte[] value) + public override IDictionary Deserialize(byte[] value) { Dictionary tempDataDictionary; @@ -124,7 +124,7 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures.Filters return convertedDictionary; } - public byte[] Serialize(IDictionary values) + public override byte[] Serialize(IDictionary values) { var hasValues = (values != null && values.Count > 0); if (hasValues) @@ -165,7 +165,7 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures.Filters } } - public static bool CanSerializeType(Type typeToSerialize, out string errorMessage) + private static bool CanSerializeType(Type typeToSerialize, out string errorMessage) { typeToSerialize = typeToSerialize ?? throw new ArgumentNullException(nameof(typeToSerialize)); @@ -195,7 +195,7 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures.Filters if (genericTypeArguments[0] != typeof(string)) { errorMessage = Resources.FormatTempData_CannotSerializeDictionary( - typeof(TempDataSerializer).FullName, + typeof(BsonTempDataSerializer).FullName, genericTypeArguments[0], typeof(string).FullName); return false; @@ -211,7 +211,7 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures.Filters if (!IsSimpleType(actualType)) { errorMessage = Resources.FormatTempData_CannotSerializeType( - typeof(TempDataSerializer).FullName, + typeof(BsonTempDataSerializer).FullName, actualType); return false; } diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/DependencyInjection/MvcJsonOptionsExtensions.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/DependencyInjection/MvcNewtonsoftJsonOptionsExtensions.cs similarity index 82% rename from src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/DependencyInjection/MvcJsonOptionsExtensions.cs rename to src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/DependencyInjection/MvcNewtonsoftJsonOptionsExtensions.cs index 876325d281..97faa23558 100644 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/DependencyInjection/MvcJsonOptionsExtensions.cs +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/DependencyInjection/MvcNewtonsoftJsonOptionsExtensions.cs @@ -3,13 +3,13 @@ using System; using Microsoft.AspNetCore.Mvc; -using Microsoft.AspNetCore.Mvc.Formatters.Json; +using Microsoft.AspNetCore.Mvc.NewtonsoftJson; using Newtonsoft.Json; using Newtonsoft.Json.Serialization; namespace Microsoft.Extensions.DependencyInjection { - public static class MvcJsonOptionsExtensions + public static class MvcNewtonsoftJsonOptionsExtensions { /// /// Configures the casing behavior of JSON serialization to use camel case for property names, @@ -18,10 +18,10 @@ namespace Microsoft.Extensions.DependencyInjection /// /// This method modifies . /// - /// + /// /// If true will camel case dictionary keys and properties of dynamic objects. - /// with camel case settings. - public static MvcJsonOptions UseCamelCasing(this MvcJsonOptions options, bool processDictionaryKeys) + /// with camel case settings. + public static MvcNewtonsoftJsonOptions UseCamelCasing(this MvcNewtonsoftJsonOptions options, bool processDictionaryKeys) { if (options == null) { @@ -57,9 +57,9 @@ namespace Microsoft.Extensions.DependencyInjection /// /// This method modifies . /// - /// - /// with member casing settings. - public static MvcJsonOptions UseMemberCasing(this MvcJsonOptions options) + /// + /// with member casing settings. + public static MvcNewtonsoftJsonOptions UseMemberCasing(this MvcNewtonsoftJsonOptions options) { if (options == null) { diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/DependencyInjection/MvcJsonMvcOptionsSetup.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/DependencyInjection/NewtonosftJsonMvcOptionsSetup.cs similarity index 80% rename from src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/DependencyInjection/MvcJsonMvcOptionsSetup.cs rename to src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/DependencyInjection/NewtonosftJsonMvcOptionsSetup.cs index bc2f044e92..a86a9fb3ae 100644 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/DependencyInjection/MvcJsonMvcOptionsSetup.cs +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/DependencyInjection/NewtonosftJsonMvcOptionsSetup.cs @@ -5,28 +5,29 @@ using System; using System.Buffers; using Microsoft.AspNetCore.JsonPatch; using Microsoft.AspNetCore.Mvc; -using Microsoft.AspNetCore.Mvc.Formatters; +using Microsoft.AspNetCore.Mvc.NewtonsoftJson; using Microsoft.AspNetCore.Mvc.ModelBinding; using Microsoft.Extensions.Logging; using Microsoft.Extensions.ObjectPool; using Microsoft.Extensions.Options; using Newtonsoft.Json.Linq; +using Microsoft.AspNetCore.Mvc.Formatters; namespace Microsoft.Extensions.DependencyInjection { /// /// Sets up JSON formatter options for . /// - internal class MvcJsonMvcOptionsSetup : IConfigureOptions + internal class NewtonosftJsonMvcOptionsSetup : IConfigureOptions { private readonly ILoggerFactory _loggerFactory; - private readonly MvcJsonOptions _jsonOptions; + private readonly MvcNewtonsoftJsonOptions _jsonOptions; private readonly ArrayPool _charPool; private readonly ObjectPoolProvider _objectPoolProvider; - public MvcJsonMvcOptionsSetup( + public NewtonosftJsonMvcOptionsSetup( ILoggerFactory loggerFactory, - IOptions jsonOptions, + IOptions jsonOptions, ArrayPool charPool, ObjectPoolProvider objectPoolProvider) { @@ -58,13 +59,13 @@ namespace Microsoft.Extensions.DependencyInjection public void Configure(MvcOptions options) { - options.OutputFormatters.Add(new JsonOutputFormatter(_jsonOptions.SerializerSettings, _charPool)); + options.OutputFormatters.Add(new NewtonsoftJsonOutputFormatter(_jsonOptions.SerializerSettings, _charPool)); // Register JsonPatchInputFormatter before JsonInputFormatter, otherwise // JsonInputFormatter would consume "application/json-patch+json" requests // before JsonPatchInputFormatter gets to see them. - var jsonInputPatchLogger = _loggerFactory.CreateLogger(); - options.InputFormatters.Add(new JsonPatchInputFormatter( + var jsonInputPatchLogger = _loggerFactory.CreateLogger(); + options.InputFormatters.Add(new NewtonsoftJsonPatchInputFormatter( jsonInputPatchLogger, _jsonOptions.SerializerSettings, _charPool, @@ -72,8 +73,8 @@ namespace Microsoft.Extensions.DependencyInjection options, _jsonOptions)); - var jsonInputLogger = _loggerFactory.CreateLogger(); - options.InputFormatters.Add(new JsonInputFormatter( + var jsonInputLogger = _loggerFactory.CreateLogger(); + options.InputFormatters.Add(new NewtonsoftJsonInputFormatter( jsonInputLogger, _jsonOptions.SerializerSettings, _charPool, diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/DependencyInjection/NewtonsoftJsonMvcBuilderExtensions.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/DependencyInjection/NewtonsoftJsonMvcBuilderExtensions.cs new file mode 100644 index 0000000000..4716288342 --- /dev/null +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/DependencyInjection/NewtonsoftJsonMvcBuilderExtensions.cs @@ -0,0 +1,56 @@ +// Copyright (c) .NET Foundation. All rights reserved. +// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information. + +using System; +using Microsoft.AspNetCore.Mvc; + +namespace Microsoft.Extensions.DependencyInjection +{ + /// + /// Extensions methods for configuring MVC via an . + /// + public static class NewtonsoftJsonMvcBuilderExtensions + { + /// + /// Configures Newtonsoft.Json specific features such as input and output formatters. + /// + /// The . + /// The . + public static IMvcBuilder AddNewtonsoftJson(this IMvcBuilder builder) + { + if (builder == null) + { + throw new ArgumentNullException(nameof(builder)); + } + + NewtonsoftJsonMvcCoreBuilderExtensions.AddServicesCore(builder.Services); + return builder; + } + + /// + /// Configures Newtonsoft.Json specific features such as input and output formatters. + /// + /// The . + /// Callback to configure . + /// The . + public static IMvcBuilder AddNewtonsoftJson( + this IMvcBuilder builder, + Action setupAction) + { + if (builder == null) + { + throw new ArgumentNullException(nameof(builder)); + } + + if (setupAction == null) + { + throw new ArgumentNullException(nameof(setupAction)); + } + + NewtonsoftJsonMvcCoreBuilderExtensions.AddServicesCore(builder.Services); + builder.Services.Configure(setupAction); + + return builder; + } + } +} diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/DependencyInjection/NewtonsoftJsonMvcCoreBuilderExtensions.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/DependencyInjection/NewtonsoftJsonMvcCoreBuilderExtensions.cs new file mode 100644 index 0000000000..2c94637891 --- /dev/null +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/DependencyInjection/NewtonsoftJsonMvcCoreBuilderExtensions.cs @@ -0,0 +1,110 @@ +// Copyright (c) .NET Foundation. All rights reserved. +// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information. + +using System; +using System.Buffers; +using System.Linq; +using Microsoft.AspNetCore.Mvc; +using Microsoft.AspNetCore.Mvc.ApiExplorer; +using Microsoft.AspNetCore.Mvc.Formatters; +using Microsoft.AspNetCore.Mvc.Infrastructure; +using Microsoft.AspNetCore.Mvc.NewtonsoftJson; +using Microsoft.AspNetCore.Mvc.Rendering; +using Microsoft.AspNetCore.Mvc.ViewFeatures.Infrastructure; +using Microsoft.Extensions.DependencyInjection.Extensions; +using Microsoft.Extensions.ObjectPool; +using Microsoft.Extensions.Options; + +namespace Microsoft.Extensions.DependencyInjection +{ + public static class NewtonsoftJsonMvcCoreBuilderExtensions + { + /// + /// Configures Newtonsoft.Json specific features such as input and output formatters. + /// + /// The . + /// The . + public static IMvcCoreBuilder AddNewtonsoftJson(this IMvcCoreBuilder builder) + { + if (builder == null) + { + throw new ArgumentNullException(nameof(builder)); + } + + AddServicesCore(builder.Services); + return builder; + } + + /// + /// Configures Newtonsoft.Json specific features such as input and output formatters. + /// + /// The . + /// Callback to configure . + /// The . + public static IMvcCoreBuilder AddNewtonsoftJson( + this IMvcCoreBuilder builder, + Action setupAction) + { + if (builder == null) + { + throw new ArgumentNullException(nameof(builder)); + } + + if (setupAction == null) + { + throw new ArgumentNullException(nameof(setupAction)); + } + + AddServicesCore(builder.Services); + + builder.Services.Configure(setupAction); + + return builder; + } + + // Internal for testing. + internal static void AddServicesCore(IServiceCollection services) + { + services.TryAddSingleton(); + services.TryAddEnumerable( + ServiceDescriptor.Transient, NewtonosftJsonMvcOptionsSetup>()); + services.TryAddEnumerable( + ServiceDescriptor.Transient()); + services.TryAddSingleton, JsonResultExecutor>(); + + var viewFeaturesAssembly = typeof(IHtmlHelper).Assembly; + + var tempDataSerializer = services.FirstOrDefault(f => + f.ServiceType == typeof(TempDataSerializer) && + f.ImplementationType?.Assembly == viewFeaturesAssembly && + f.ImplementationType.FullName == "Microsoft.AspNetCore.Mvc.ViewFeatures.Infrastructure.DefaultTempDataSerializer"); + + if (tempDataSerializer != null) + { + // Replace the default implementation of TempDataSerializer + services.Remove(tempDataSerializer); + } + services.TryAddSingleton(); + + // + // JSON Helper + // + var jsonHelper = services.FirstOrDefault( + f => f.ServiceType == typeof(IJsonHelper) && + f.ImplementationType?.Assembly == viewFeaturesAssembly && + f.ImplementationType.FullName == "Microsoft.AspNetCore.Mvc.Rendering.DefaultJsonHelper"); + if (jsonHelper != null) + { + services.Remove(jsonHelper); + } + + services.TryAddSingleton(); + services.TryAdd(ServiceDescriptor.Singleton(serviceProvider => + { + var options = serviceProvider.GetRequiredService>().Value; + var charPool = serviceProvider.GetRequiredService>(); + return new NewtonsoftJsonOutputFormatter(options.SerializerSettings, charPool); + })); + } + } +} diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/JsonArrayPool.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/JsonArrayPool.cs similarity index 94% rename from src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/JsonArrayPool.cs rename to src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/JsonArrayPool.cs index 773dc82693..c358bc2ba7 100644 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/JsonArrayPool.cs +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/JsonArrayPool.cs @@ -5,7 +5,7 @@ using System; using System.Buffers; using Newtonsoft.Json; -namespace Microsoft.AspNetCore.Mvc.Formatters +namespace Microsoft.AspNetCore.Mvc.NewtonsoftJson { internal class JsonArrayPool : IArrayPool { diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/JsonHelperExtensions.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/JsonHelperExtensions.cs new file mode 100644 index 0000000000..4c83a279c7 --- /dev/null +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/JsonHelperExtensions.cs @@ -0,0 +1,60 @@ +// Copyright (c) .NET Foundation. All rights reserved. +// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information. + +using System; +using Microsoft.AspNetCore.Html; +using Microsoft.AspNetCore.Mvc.NewtonsoftJson; +using Microsoft.Extensions.DependencyInjection; +using Newtonsoft.Json; + +namespace Microsoft.AspNetCore.Mvc.Rendering +{ + /// + /// Newtonsoft.Json specific extensions to . + /// + public static class JsonHelperExtensions + { + /// + /// Returns serialized JSON for the . + /// + /// The . + /// The value to serialize as JSON. + /// + /// The to be used by the serializer. + /// + /// A new containing the serialized JSON. + public static IHtmlContent Serialize( + this IJsonHelper jsonHelper, + object value, + JsonSerializerSettings serializerSettings) + { + if (jsonHelper == null) + { + throw new ArgumentNullException(nameof(jsonHelper)); + } + + if (!(jsonHelper is NewtonsoftJsonHelper newtonsoftJsonHelper)) + { + var message = Resources.FormatJsonHelperMustBeAnInstanceOfNewtonsoftJson( + nameof(jsonHelper), + nameof(IJsonHelper), + typeof(JsonHelperExtensions).Assembly.GetName().Name, + nameof(NewtonsoftJsonMvcBuilderExtensions.AddNewtonsoftJson)); + + throw new ArgumentException(message, nameof(jsonHelper)); + } + + if (value == null) + { + throw new ArgumentNullException(nameof(value)); + } + + if (serializerSettings == null) + { + throw new ArgumentNullException(nameof(serializerSettings)); + } + + return newtonsoftJsonHelper.Serialize(value, serializerSettings); + } + } +} diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/JsonPatchExtensions.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/JsonPatchExtensions.cs similarity index 100% rename from src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/JsonPatchExtensions.cs rename to src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/JsonPatchExtensions.cs diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/JsonPatchOperationsArrayProvider.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/JsonPatchOperationsArrayProvider.cs similarity index 92% rename from src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/JsonPatchOperationsArrayProvider.cs rename to src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/JsonPatchOperationsArrayProvider.cs index 840df5fdf8..fda34decc4 100644 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/JsonPatchOperationsArrayProvider.cs +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/JsonPatchOperationsArrayProvider.cs @@ -8,19 +8,19 @@ using Microsoft.AspNetCore.JsonPatch.Operations; using Microsoft.AspNetCore.Mvc.ApiExplorer; using Microsoft.AspNetCore.Mvc.ModelBinding; -namespace Microsoft.AspNetCore.Mvc.Formatters.Json +namespace Microsoft.AspNetCore.Mvc.NewtonsoftJson { /// - /// Implements a provider of to change parameters of + /// Implements a provider of to change parameters of /// type to an array of . /// - public class JsonPatchOperationsArrayProvider : IApiDescriptionProvider + internal sealed class JsonPatchOperationsArrayProvider : IApiDescriptionProvider { private readonly IModelMetadataProvider _modelMetadataProvider; /// /// Creates a new instance of . - /// + /// /// The . public JsonPatchOperationsArrayProvider(IModelMetadataProvider modelMetadataProvider) { diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/JsonResultExecutor.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/JsonResultExecutor.cs similarity index 78% rename from src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/JsonResultExecutor.cs rename to src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/JsonResultExecutor.cs index 81f0f783d7..b4ccaa171f 100644 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/JsonResultExecutor.cs +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/JsonResultExecutor.cs @@ -5,18 +5,19 @@ using System; using System.Buffers; using System.Text; using System.Threading.Tasks; +using Microsoft.AspNetCore.Mvc.Formatters; using Microsoft.AspNetCore.Mvc.Infrastructure; using Microsoft.Extensions.Logging; using Microsoft.Extensions.Options; using Microsoft.Net.Http.Headers; using Newtonsoft.Json; -namespace Microsoft.AspNetCore.Mvc.Formatters +namespace Microsoft.AspNetCore.Mvc.NewtonsoftJson { /// /// Executes a to write to the response. /// - internal class JsonResultExecutor + internal class JsonResultExecutor : IActionResultExecutor { private static readonly string DefaultContentType = new MediaTypeHeaderValue("application/json") { @@ -25,7 +26,7 @@ namespace Microsoft.AspNetCore.Mvc.Formatters private readonly IHttpResponseStreamWriterFactory _writerFactory; private readonly ILogger _logger; - private readonly MvcJsonOptions _options; + private readonly MvcNewtonsoftJsonOptions _options; private readonly IArrayPool _charPool; /// @@ -38,7 +39,7 @@ namespace Microsoft.AspNetCore.Mvc.Formatters public JsonResultExecutor( IHttpResponseStreamWriterFactory writerFactory, ILogger logger, - IOptions options, + IOptions options, ArrayPool charPool) { if (writerFactory == null) @@ -85,6 +86,8 @@ namespace Microsoft.AspNetCore.Mvc.Formatters throw new ArgumentNullException(nameof(result)); } + var jsonSerializerSettings = GetSerializerSettings(result); + var response = context.HttpContext.Response; ResponseContentTypeHelper.ResolveContentTypeAndEncoding( @@ -101,8 +104,6 @@ namespace Microsoft.AspNetCore.Mvc.Formatters response.StatusCode = result.StatusCode.Value; } - var serializerSettings = result.SerializerSettings ?? _options.SerializerSettings; - _logger.JsonResultExecuting(result.Value); using (var writer = _writerFactory.CreateWriter(response.Body, resolvedContentTypeEncoding)) { @@ -112,7 +113,7 @@ namespace Microsoft.AspNetCore.Mvc.Formatters jsonWriter.CloseOutput = false; jsonWriter.AutoCompleteOnClose = false; - var jsonSerializer = JsonSerializer.Create(serializerSettings); + var jsonSerializer = JsonSerializer.Create(jsonSerializerSettings); jsonSerializer.Serialize(jsonWriter, result.Value); } @@ -121,5 +122,26 @@ namespace Microsoft.AspNetCore.Mvc.Formatters await writer.FlushAsync(); } } + + private JsonSerializerSettings GetSerializerSettings(JsonResult result) + { + var serializerSettings = result.SerializerSettings; + if (serializerSettings == null) + { + return _options.SerializerSettings; + } + else + { + if (!(serializerSettings is JsonSerializerSettings settingsFromResult)) + { + throw new InvalidOperationException(Resources.FormatProperty_MustBeInstanceOfType( + nameof(JsonResult), + nameof(JsonResult.SerializerSettings), + typeof(JsonSerializerSettings))); + } + + return settingsFromResult; + } + } } } diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/JsonSerializerObjectPolicy.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/JsonSerializerObjectPolicy.cs similarity index 95% rename from src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/JsonSerializerObjectPolicy.cs rename to src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/JsonSerializerObjectPolicy.cs index 4efc81abcc..38c07201ab 100644 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/JsonSerializerObjectPolicy.cs +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/JsonSerializerObjectPolicy.cs @@ -4,7 +4,7 @@ using Microsoft.Extensions.ObjectPool; using Newtonsoft.Json; -namespace Microsoft.AspNetCore.Mvc.Formatters +namespace Microsoft.AspNetCore.Mvc.NewtonsoftJson { /// /// for . diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/JsonSerializerSettingsProvider.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/JsonSerializerSettingsProvider.cs similarity index 81% rename from src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/JsonSerializerSettingsProvider.cs rename to src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/JsonSerializerSettingsProvider.cs index 00793a13e6..cc95210878 100644 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/JsonSerializerSettingsProvider.cs +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/JsonSerializerSettingsProvider.cs @@ -4,7 +4,7 @@ using Newtonsoft.Json; using Newtonsoft.Json.Serialization; -namespace Microsoft.AspNetCore.Mvc.Formatters +namespace Microsoft.AspNetCore.Mvc.NewtonsoftJson { /// /// Helper class which provides . @@ -12,6 +12,8 @@ namespace Microsoft.AspNetCore.Mvc.Formatters public static class JsonSerializerSettingsProvider { private const int DefaultMaxDepth = 32; + private static readonly ProblemDetailsConverter ProblemDetailsConverter = new ProblemDetailsConverter(); + private static readonly ValidationProblemDetailsConverter ValidationProblemDetailsConverter = new ValidationProblemDetailsConverter(); // return shared resolver by default for perf so slow reflection logic is cached once // developers can set their own resolver after the settings are returned if desired @@ -41,6 +43,12 @@ namespace Microsoft.AspNetCore.Mvc.Formatters // Do not change this setting // Setting this to None prevents Json.NET from loading malicious, unsafe, or security-sensitive types TypeNameHandling = TypeNameHandling.None, + + Converters = + { + ValidationProblemDetailsConverter, + ProblemDetailsConverter, + } }; } diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/MediaTypeHeaderValues.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/MediaTypeHeaderValues.cs similarity index 94% rename from src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/MediaTypeHeaderValues.cs rename to src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/MediaTypeHeaderValues.cs index ec791b15ef..5795d08d35 100644 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/MediaTypeHeaderValues.cs +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/MediaTypeHeaderValues.cs @@ -3,7 +3,7 @@ using Microsoft.Net.Http.Headers; -namespace Microsoft.AspNetCore.Mvc.Formatters +namespace Microsoft.AspNetCore.Mvc.NewtonsoftJson { internal static class MediaTypeHeaderValues { diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/Microsoft.AspNetCore.Mvc.Formatters.Json.csproj b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/Microsoft.AspNetCore.Mvc.NewtonsoftJson.csproj similarity index 53% rename from src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/Microsoft.AspNetCore.Mvc.Formatters.Json.csproj rename to src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/Microsoft.AspNetCore.Mvc.NewtonsoftJson.csproj index 6d5677ebcd..9bb08478c3 100644 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/Microsoft.AspNetCore.Mvc.Formatters.Json.csproj +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/Microsoft.AspNetCore.Mvc.NewtonsoftJson.csproj @@ -1,7 +1,7 @@  - ASP.NET Core MVC formatters for JSON input and output and for JSON PATCH input using Json.NET. + ASP.NET Core MVC features that use Newtonsoft.Json. Includes input and output formatters for JSON and JSON PATCH. netcoreapp3.0 $(NoWarn);CS1591 true @@ -13,8 +13,13 @@ - - + + + + + + + diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/MvcJsonOptions.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/MvcNewtonsoftJsonOptions.cs similarity index 88% rename from src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/MvcJsonOptions.cs rename to src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/MvcNewtonsoftJsonOptions.cs index 2fae0e8751..57c0d7684d 100644 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/MvcJsonOptions.cs +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/MvcNewtonsoftJsonOptions.cs @@ -7,6 +7,7 @@ using System.Collections.Generic; using Microsoft.AspNetCore.Mvc.Formatters; using Microsoft.AspNetCore.Mvc.Infrastructure; using Microsoft.AspNetCore.Mvc.ModelBinding; +using Microsoft.AspNetCore.Mvc.NewtonsoftJson; using Newtonsoft.Json; namespace Microsoft.AspNetCore.Mvc @@ -14,13 +15,13 @@ namespace Microsoft.AspNetCore.Mvc /// /// Provides programmatic configuration for JSON in the MVC framework. /// - public class MvcJsonOptions : IEnumerable + public class MvcNewtonsoftJsonOptions : IEnumerable { private readonly IReadOnlyList _switches = Array.Empty(); /// /// Gets or sets a flag to determine whether error messages from JSON deserialization by the - /// will be added to the . If + /// will be added to the . If /// , a generic error message will be used instead. /// /// diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/JsonHelper.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/NewtonsoftJsonHelper.cs similarity index 82% rename from src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/JsonHelper.cs rename to src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/NewtonsoftJsonHelper.cs index 21f40342ae..5179cdf7bc 100644 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/JsonHelper.cs +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/NewtonsoftJsonHelper.cs @@ -10,25 +10,25 @@ using Microsoft.AspNetCore.Mvc.Formatters; using Microsoft.AspNetCore.Mvc.Rendering; using Newtonsoft.Json; -namespace Microsoft.AspNetCore.Mvc.ViewFeatures +namespace Microsoft.AspNetCore.Mvc.NewtonsoftJson { /// - /// Default implementation of . + /// Newtonsoft.Json based implementation of . /// - public class JsonHelper : IJsonHelper + internal class NewtonsoftJsonHelper : IJsonHelper { - private readonly JsonOutputFormatter _jsonOutputFormatter; + private readonly NewtonsoftJsonOutputFormatter _jsonOutputFormatter; private readonly ArrayPool _charPool; /// - /// Initializes a new instance of that is backed by . + /// Initializes a new instance of that is backed by . /// - /// The used to serialize JSON. + /// The used to serialize JSON. /// /// The for use with custom (see /// ). /// - public JsonHelper(JsonOutputFormatter jsonOutputFormatter, ArrayPool charPool) + public NewtonsoftJsonHelper(NewtonsoftJsonOutputFormatter jsonOutputFormatter, ArrayPool charPool) { if (jsonOutputFormatter == null) { @@ -60,12 +60,12 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures throw new ArgumentNullException(nameof(serializerSettings)); } - var jsonOutputFormatter = new JsonOutputFormatter(serializerSettings, _charPool); + var jsonOutputFormatter = new NewtonsoftJsonOutputFormatter(serializerSettings, _charPool); return SerializeInternal(jsonOutputFormatter, value); } - private IHtmlContent SerializeInternal(JsonOutputFormatter jsonOutputFormatter, object value) + private IHtmlContent SerializeInternal(NewtonsoftJsonOutputFormatter jsonOutputFormatter, object value) { var stringWriter = new StringWriter(CultureInfo.InvariantCulture); jsonOutputFormatter.WriteObject(stringWriter, value); diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/JsonInputFormatter.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/NewtonsoftJsonInputFormatter.cs similarity index 93% rename from src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/JsonInputFormatter.cs rename to src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/NewtonsoftJsonInputFormatter.cs index 1d8cdaab45..b778ae0dda 100644 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/JsonInputFormatter.cs +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/NewtonsoftJsonInputFormatter.cs @@ -11,6 +11,7 @@ using System.Threading; using System.Threading.Tasks; using Microsoft.AspNetCore.Http; using Microsoft.AspNetCore.Mvc.ModelBinding; +using Microsoft.AspNetCore.Mvc.NewtonsoftJson; using Microsoft.AspNetCore.WebUtilities; using Microsoft.Extensions.Logging; using Microsoft.Extensions.ObjectPool; @@ -21,13 +22,13 @@ namespace Microsoft.AspNetCore.Mvc.Formatters /// /// A for JSON content. /// - public class JsonInputFormatter : TextInputFormatter, IInputFormatterExceptionPolicy + public class NewtonsoftJsonInputFormatter : TextInputFormatter, IInputFormatterExceptionPolicy { private readonly IArrayPool _charPool; private readonly ILogger _logger; private readonly ObjectPoolProvider _objectPoolProvider; private readonly MvcOptions _options; - private readonly MvcJsonOptions _jsonOptions; + private readonly MvcNewtonsoftJsonOptions _jsonOptions; // These fields are used when one of the legacy constructors is called that doesn't provide the MvcOptions or // MvcJsonOptions. @@ -37,18 +38,18 @@ namespace Microsoft.AspNetCore.Mvc.Formatters private ObjectPool _jsonSerializerPool; /// - /// Initializes a new instance of . + /// Initializes a new instance of . /// /// The . /// /// The . Should be either the application-wide settings - /// () or an instance + /// () or an instance /// initially returned. /// /// The . /// The . [Obsolete("This constructor is obsolete and will be removed in a future version.")] - public JsonInputFormatter( + public NewtonsoftJsonInputFormatter( ILogger logger, JsonSerializerSettings serializerSettings, ArrayPool charPool, @@ -59,19 +60,19 @@ namespace Microsoft.AspNetCore.Mvc.Formatters } /// - /// Initializes a new instance of . + /// Initializes a new instance of . /// /// The . /// /// The . Should be either the application-wide settings - /// () or an instance + /// () or an instance /// initially returned. /// /// The . /// The . /// Flag to buffer entire request body before deserializing it. [Obsolete("This constructor is obsolete and will be removed in a future version.")] - public JsonInputFormatter( + public NewtonsoftJsonInputFormatter( ILogger logger, JsonSerializerSettings serializerSettings, ArrayPool charPool, @@ -84,12 +85,12 @@ namespace Microsoft.AspNetCore.Mvc.Formatters } /// - /// Initializes a new instance of . + /// Initializes a new instance of . /// /// The . /// /// The . Should be either the application-wide settings - /// () or an instance + /// () or an instance /// initially returned. /// /// The . @@ -97,7 +98,7 @@ namespace Microsoft.AspNetCore.Mvc.Formatters /// Flag to buffer entire request body before deserializing it. /// If , JSON deserialization exception messages will replaced by a generic message in model state. [Obsolete("This constructor is obsolete and will be removed in a future version.")] - public JsonInputFormatter( + public NewtonsoftJsonInputFormatter( ILogger logger, JsonSerializerSettings serializerSettings, ArrayPool charPool, @@ -141,25 +142,25 @@ namespace Microsoft.AspNetCore.Mvc.Formatters } /// - /// Initializes a new instance of . + /// Initializes a new instance of . /// /// The . /// /// The . Should be either the application-wide settings - /// () or an instance + /// () or an instance /// initially returned. /// /// The . /// The . /// The . - /// The . - public JsonInputFormatter( + /// The . + public NewtonsoftJsonInputFormatter( ILogger logger, JsonSerializerSettings serializerSettings, ArrayPool charPool, ObjectPoolProvider objectPoolProvider, MvcOptions options, - MvcJsonOptions jsonOptions) + MvcNewtonsoftJsonOptions jsonOptions) { if (logger == null) { @@ -201,7 +202,7 @@ namespace Microsoft.AspNetCore.Mvc.Formatters { get { - if (GetType() == typeof(JsonInputFormatter)) + if (GetType() == typeof(NewtonsoftJsonInputFormatter)) { return InputFormatterExceptionPolicy.MalformedInputExceptions; } @@ -214,7 +215,7 @@ namespace Microsoft.AspNetCore.Mvc.Formatters /// /// /// Any modifications to the object after this - /// has been used will have no effect. + /// has been used will have no effect. /// protected JsonSerializerSettings SerializerSettings { get; } diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/MvcJsonLoggerExtensions.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/NewtonsoftJsonLoggerExtensions.cs similarity index 89% rename from src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/MvcJsonLoggerExtensions.cs rename to src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/NewtonsoftJsonLoggerExtensions.cs index 8ca8f2ed30..14dcd92174 100644 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/MvcJsonLoggerExtensions.cs +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/NewtonsoftJsonLoggerExtensions.cs @@ -4,15 +4,15 @@ using System; using Microsoft.Extensions.Logging; -namespace Microsoft.AspNetCore.Mvc.Formatters +namespace Microsoft.AspNetCore.Mvc.NewtonsoftJson { - internal static class MvcJsonLoggerExtensions + internal static class NewtonsoftJsonLoggerExtensions { private static readonly Action _jsonInputFormatterCrashed; private static readonly Action _jsonResultExecuting; - static MvcJsonLoggerExtensions() + static NewtonsoftJsonLoggerExtensions() { _jsonInputFormatterCrashed = LoggerMessage.Define( LogLevel.Debug, diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/JsonOutputFormatter.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/NewtonsoftJsonOutputFormatter.cs similarity index 90% rename from src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/JsonOutputFormatter.cs rename to src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/NewtonsoftJsonOutputFormatter.cs index 7dafe6fe94..57825099ad 100644 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/JsonOutputFormatter.cs +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/NewtonsoftJsonOutputFormatter.cs @@ -7,6 +7,7 @@ using System.ComponentModel; using System.IO; using System.Text; using System.Threading.Tasks; +using Microsoft.AspNetCore.Mvc.NewtonsoftJson; using Newtonsoft.Json; namespace Microsoft.AspNetCore.Mvc.Formatters @@ -14,7 +15,7 @@ namespace Microsoft.AspNetCore.Mvc.Formatters /// /// A for JSON content. /// - public class JsonOutputFormatter : TextOutputFormatter + public class NewtonsoftJsonOutputFormatter : TextOutputFormatter { private readonly IArrayPool _charPool; @@ -23,15 +24,15 @@ namespace Microsoft.AspNetCore.Mvc.Formatters private JsonSerializer _serializer; /// - /// Initializes a new instance. + /// Initializes a new instance. /// /// /// The . Should be either the application-wide settings - /// () or an instance + /// () or an instance /// initially returned. /// /// The . - public JsonOutputFormatter(JsonSerializerSettings serializerSettings, ArrayPool charPool) + public NewtonsoftJsonOutputFormatter(JsonSerializerSettings serializerSettings, ArrayPool charPool) { if (serializerSettings == null) { @@ -58,7 +59,7 @@ namespace Microsoft.AspNetCore.Mvc.Formatters /// /// /// Any modifications to the object after this - /// has been used will have no effect. + /// has been used will have no effect. /// protected JsonSerializerSettings SerializerSettings { get; } @@ -67,7 +68,7 @@ namespace Microsoft.AspNetCore.Mvc.Formatters /// /// /// Any modifications to the object after this - /// has been used will have no effect. + /// has been used will have no effect. /// [EditorBrowsable(EditorBrowsableState.Never)] public JsonSerializerSettings PublicSerializerSettings => SerializerSettings; diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/JsonPatchInputFormatter.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/NewtonsoftJsonPatchInputFormatter.cs similarity index 85% rename from src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/JsonPatchInputFormatter.cs rename to src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/NewtonsoftJsonPatchInputFormatter.cs index 44d8718eeb..74ba02a1ae 100644 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/JsonPatchInputFormatter.cs +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/NewtonsoftJsonPatchInputFormatter.cs @@ -7,6 +7,7 @@ using System.Reflection; using System.Text; using System.Threading.Tasks; using Microsoft.AspNetCore.JsonPatch; +using Microsoft.AspNetCore.Mvc.NewtonsoftJson; using Microsoft.Extensions.Logging; using Microsoft.Extensions.ObjectPool; using Newtonsoft.Json; @@ -16,21 +17,21 @@ namespace Microsoft.AspNetCore.Mvc.Formatters /// /// A for JSON Patch (application/json-patch+json) content. /// - public class JsonPatchInputFormatter : JsonInputFormatter + public class NewtonsoftJsonPatchInputFormatter : NewtonsoftJsonInputFormatter { /// - /// Initializes a new instance. + /// Initializes a new instance. /// /// The . /// /// The . Should be either the application-wide settings - /// () or an instance + /// () or an instance /// initially returned. /// /// The . /// The . [Obsolete("This constructor is obsolete and will be removed in a future version.")] - public JsonPatchInputFormatter( + public NewtonsoftJsonPatchInputFormatter( ILogger logger, JsonSerializerSettings serializerSettings, ArrayPool charPool, @@ -40,19 +41,19 @@ namespace Microsoft.AspNetCore.Mvc.Formatters } /// - /// Initializes a new instance. + /// Initializes a new instance. /// /// The . /// /// The . Should be either the application-wide settings - /// () or an instance + /// () or an instance /// initially returned. /// /// The . /// The . /// Flag to buffer entire request body before deserializing it. [Obsolete("This constructor is obsolete and will be removed in a future version.")] - public JsonPatchInputFormatter( + public NewtonsoftJsonPatchInputFormatter( ILogger logger, JsonSerializerSettings serializerSettings, ArrayPool charPool, @@ -63,12 +64,12 @@ namespace Microsoft.AspNetCore.Mvc.Formatters } /// - /// Initializes a new instance. + /// Initializes a new instance. /// /// The . /// /// The . Should be either the application-wide settings - /// () or an instance + /// () or an instance /// initially returned. /// /// The . @@ -78,7 +79,7 @@ namespace Microsoft.AspNetCore.Mvc.Formatters /// If , JSON deserialization exception messages will replaced by a generic message in model state. /// [Obsolete("This constructor is obsolete and will be removed in a future version.")] - public JsonPatchInputFormatter( + public NewtonsoftJsonPatchInputFormatter( ILogger logger, JsonSerializerSettings serializerSettings, ArrayPool charPool, @@ -94,25 +95,25 @@ namespace Microsoft.AspNetCore.Mvc.Formatters } /// - /// Initializes a new instance. + /// Initializes a new instance. /// /// The . /// /// The . Should be either the application-wide settings - /// () or an instance + /// () or an instance /// initially returned. /// /// The . /// The . /// The . - /// The . - public JsonPatchInputFormatter( + /// The . + public NewtonsoftJsonPatchInputFormatter( ILogger logger, JsonSerializerSettings serializerSettings, ArrayPool charPool, ObjectPoolProvider objectPoolProvider, MvcOptions options, - MvcJsonOptions jsonOptions) + MvcNewtonsoftJsonOptions jsonOptions) : base(logger, serializerSettings, charPool, objectPoolProvider, options, jsonOptions) { // Clear all values and only include json-patch+json value. @@ -126,7 +127,7 @@ namespace Microsoft.AspNetCore.Mvc.Formatters { get { - if (GetType() == typeof(JsonPatchInputFormatter)) + if (GetType() == typeof(NewtonsoftJsonPatchInputFormatter)) { return InputFormatterExceptionPolicy.MalformedInputExceptions; } diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/ProblemDetailsConverter.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/ProblemDetailsConverter.cs new file mode 100644 index 0000000000..2ef8f76824 --- /dev/null +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/ProblemDetailsConverter.cs @@ -0,0 +1,50 @@ +// Copyright (c) .NET Foundation. All rights reserved. +// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information. + +using System; +using Newtonsoft.Json; + +namespace Microsoft.AspNetCore.Mvc.NewtonsoftJson +{ + /// + /// A RFC 7807 compliant for . + /// + public sealed class ProblemDetailsConverter : JsonConverter + { + /// + public override bool CanConvert(Type objectType) + { + return objectType == typeof(ProblemDetails); + } + + /// + public override object ReadJson(JsonReader reader, Type objectType, object existingValue, JsonSerializer serializer) + { + var annotatedProblemDetails = serializer.Deserialize(reader); + if (annotatedProblemDetails == null) + { + return null; + } + + var problemDetails = (ProblemDetails)existingValue ?? new ProblemDetails(); + annotatedProblemDetails.CopyTo(problemDetails); + + return problemDetails; + } + + /// + public override void WriteJson(JsonWriter writer, object value, JsonSerializer serializer) + { + if (value == null) + { + writer.WriteNull(); + return; + } + + var problemDetails = (ProblemDetails)value; + var annotatedProblemDetails = new AnnotatedProblemDetails(problemDetails); + + serializer.Serialize(writer, annotatedProblemDetails); + } + } +} diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/Properties/AssemblyInfo.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/Properties/AssemblyInfo.cs similarity index 71% rename from src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/Properties/AssemblyInfo.cs rename to src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/Properties/AssemblyInfo.cs index a6552b389c..7c329fe5e0 100644 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/Properties/AssemblyInfo.cs +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/Properties/AssemblyInfo.cs @@ -4,5 +4,5 @@ using System.Runtime.CompilerServices; [assembly: InternalsVisibleTo("Microsoft.AspNetCore.Mvc.Test, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] -[assembly: InternalsVisibleTo("Microsoft.AspNetCore.Mvc.Formatters.Json.Test, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] +[assembly: InternalsVisibleTo("Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] [assembly: InternalsVisibleTo("Microsoft.AspNetCore.Mvc.IntegrationTests, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/Properties/Resources.Designer.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/Properties/Resources.Designer.cs new file mode 100644 index 0000000000..b089148e77 --- /dev/null +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/Properties/Resources.Designer.cs @@ -0,0 +1,128 @@ +// +namespace Microsoft.AspNetCore.Mvc.NewtonsoftJson +{ + using System.Globalization; + using System.Reflection; + using System.Resources; + + internal static class Resources + { + private static readonly ResourceManager _resourceManager + = new ResourceManager("Microsoft.AspNetCore.Mvc.NewtonsoftJson.Resources", typeof(Resources).GetTypeInfo().Assembly); + + /// + /// {0} cannot be null. + /// + internal static string ContractResolverCannotBeNull + { + get => GetString("ContractResolverCannotBeNull"); + } + + /// + /// {0} cannot be null. + /// + internal static string FormatContractResolverCannotBeNull(object p0) + => string.Format(CultureInfo.CurrentCulture, GetString("ContractResolverCannotBeNull"), p0); + + /// + /// Cannot configure JSON casing behavior on '{0}' contract resolver. The supported contract resolver is {1}. + /// + internal static string InvalidContractResolverForJsonCasingConfiguration + { + get => GetString("InvalidContractResolverForJsonCasingConfiguration"); + } + + /// + /// Cannot configure JSON casing behavior on '{0}' contract resolver. The supported contract resolver is {1}. + /// + internal static string FormatInvalidContractResolverForJsonCasingConfiguration(object p0, object p1) + => string.Format(CultureInfo.CurrentCulture, GetString("InvalidContractResolverForJsonCasingConfiguration"), p0, p1); + + /// + /// Parameter '{0}' must be an instance of {1} provided by the '{2}' package. Configure the correct instance using '{3}' in your startup. + /// + internal static string JsonHelperMustBeAnInstanceOfNewtonsoftJson + { + get => GetString("JsonHelperMustBeAnInstanceOfNewtonsoftJson"); + } + + /// + /// Parameter '{0}' must be an instance of {1} provided by the '{2}' package. Configure the correct instance using '{3}' in your startup. + /// + internal static string FormatJsonHelperMustBeAnInstanceOfNewtonsoftJson(object p0, object p1, object p2, object p3) + => string.Format(CultureInfo.CurrentCulture, GetString("JsonHelperMustBeAnInstanceOfNewtonsoftJson"), p0, p1, p2, p3); + + /// + /// Property '{0}.{1}' must be an instance of type '{2}'. + /// + internal static string Property_MustBeInstanceOfType + { + get => GetString("Property_MustBeInstanceOfType"); + } + + /// + /// Property '{0}.{1}' must be an instance of type '{2}'. + /// + internal static string FormatProperty_MustBeInstanceOfType(object p0, object p1, object p2) + => string.Format(CultureInfo.CurrentCulture, GetString("Property_MustBeInstanceOfType"), p0, p1, p2); + + /// + /// Cannot deserialize {0} of type '{1}'. + /// + internal static string TempData_CannotDeserializeToken + { + get => GetString("TempData_CannotDeserializeToken"); + } + + /// + /// Cannot deserialize {0} of type '{1}'. + /// + internal static string FormatTempData_CannotDeserializeToken(object p0, object p1) + => string.Format(CultureInfo.CurrentCulture, GetString("TempData_CannotDeserializeToken"), p0, p1); + + /// + /// The '{0}' cannot serialize a dictionary with a key of type '{1}'. The key must be of type '{2}'. + /// + internal static string TempData_CannotSerializeDictionary + { + get => GetString("TempData_CannotSerializeDictionary"); + } + + /// + /// The '{0}' cannot serialize a dictionary with a key of type '{1}'. The key must be of type '{2}'. + /// + internal static string FormatTempData_CannotSerializeDictionary(object p0, object p1, object p2) + => string.Format(CultureInfo.CurrentCulture, GetString("TempData_CannotSerializeDictionary"), p0, p1, p2); + + /// + /// The '{0}' cannot serialize an object of type '{1}'. + /// + internal static string TempData_CannotSerializeType + { + get => GetString("TempData_CannotSerializeType"); + } + + /// + /// The '{0}' cannot serialize an object of type '{1}'. + /// + internal static string FormatTempData_CannotSerializeType(object p0, object p1) + => string.Format(CultureInfo.CurrentCulture, GetString("TempData_CannotSerializeType"), p0, p1); + + private static string GetString(string name, params string[] formatterNames) + { + var value = _resourceManager.GetString(name); + + System.Diagnostics.Debug.Assert(value != null); + + if (formatterNames != null) + { + for (var i = 0; i < formatterNames.Length; i++) + { + value = value.Replace("{" + formatterNames[i] + "}", "{" + i + "}"); + } + } + + return value; + } + } +} diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/Resources.resx b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/Resources.resx similarity index 81% rename from src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/Resources.resx rename to src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/Resources.resx index 729545d687..cedf5cbcde 100644 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc.Formatters.Json/Resources.resx +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/Resources.resx @@ -1,17 +1,17 @@  - @@ -123,4 +123,19 @@ Cannot configure JSON casing behavior on '{0}' contract resolver. The supported contract resolver is {1}. + + Parameter '{0}' must be an instance of {1} provided by the '{2}' package. Configure the correct instance using '{3}' in your startup. + + + Property '{0}.{1}' must be an instance of type '{2}'. + + + Cannot deserialize {0} of type '{1}'. + + + The '{0}' cannot serialize a dictionary with a key of type '{1}'. The key must be of type '{2}'. + + + The '{0}' cannot serialize an object of type '{1}'. + \ No newline at end of file diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/ValidationProblemDetailsConverter.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/ValidationProblemDetailsConverter.cs new file mode 100644 index 0000000000..776eccc66a --- /dev/null +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.NewtonsoftJson/ValidationProblemDetailsConverter.cs @@ -0,0 +1,81 @@ +// Copyright (c) .NET Foundation. All rights reserved. +// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information. + +using System; +using System.Collections.Generic; +using Newtonsoft.Json; + +namespace Microsoft.AspNetCore.Mvc.NewtonsoftJson +{ + /// + /// A RFC 7807 compliant for . + /// + public sealed class ValidationProblemDetailsConverter : JsonConverter + { + /// + public override bool CanConvert(Type objectType) + { + return objectType == typeof(ValidationProblemDetails); + } + + /// + public override object ReadJson(JsonReader reader, Type objectType, object existingValue, JsonSerializer serializer) + { + var annotatedProblemDetails = serializer.Deserialize(reader); + if (annotatedProblemDetails == null) + { + return null; + } + + var problemDetails = (ValidationProblemDetails)existingValue ?? new ValidationProblemDetails(); + annotatedProblemDetails.CopyTo(problemDetails); + + return problemDetails; + } + + /// + public override void WriteJson(JsonWriter writer, object value, JsonSerializer serializer) + { + if (value == null) + { + writer.WriteNull(); + return; + } + + var problemDetails = (ValidationProblemDetails)value; + var annotatedProblemDetails = new AnnotatedValidationProblemDetails(problemDetails); + + serializer.Serialize(writer, annotatedProblemDetails); + } + + private class AnnotatedValidationProblemDetails : AnnotatedProblemDetails + { + /// + /// Required for JSON.NET deserialization. + /// + public AnnotatedValidationProblemDetails() { } + + public AnnotatedValidationProblemDetails(ValidationProblemDetails problemDetails) + : base(problemDetails) + { + foreach (var kvp in problemDetails.Errors) + { + Errors[kvp.Key] = kvp.Value; + } + } + + [JsonProperty(PropertyName = "errors")] + public IDictionary Errors { get; } = new Dictionary(StringComparer.Ordinal); + + public void CopyTo(ValidationProblemDetails problemDetails) + { + base.CopyTo(problemDetails); + + foreach (var kvp in Errors) + { + problemDetails.Errors[kvp.Key] = kvp.Value; + } + } + } + } +} diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.RazorPages/ApplicationModels/TempDataFilterPageApplicationModelProvider.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.RazorPages/ApplicationModels/TempDataFilterPageApplicationModelProvider.cs index 62f0878a21..65b251d495 100644 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc.RazorPages/ApplicationModels/TempDataFilterPageApplicationModelProvider.cs +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.RazorPages/ApplicationModels/TempDataFilterPageApplicationModelProvider.cs @@ -4,17 +4,17 @@ using System; using Microsoft.AspNetCore.Mvc.Filters; using Microsoft.AspNetCore.Mvc.ViewFeatures.Filters; -using Microsoft.Extensions.Options; +using Microsoft.AspNetCore.Mvc.ViewFeatures.Infrastructure; namespace Microsoft.AspNetCore.Mvc.ApplicationModels { internal class TempDataFilterPageApplicationModelProvider : IPageApplicationModelProvider { - private readonly MvcViewOptions _options; + private readonly TempDataSerializer _tempDataSerializer; - public TempDataFilterPageApplicationModelProvider(IOptions options) + public TempDataFilterPageApplicationModelProvider(TempDataSerializer tempDataSerializer) { - _options = options.Value; + _tempDataSerializer = tempDataSerializer; } // The order is set to execute after the DefaultPageApplicationModelProvider. @@ -34,7 +34,7 @@ namespace Microsoft.AspNetCore.Mvc.ApplicationModels var pageApplicationModel = context.PageApplicationModel; var handlerType = pageApplicationModel.HandlerType.AsType(); - var tempDataProperties = SaveTempDataPropertyFilterBase.GetTempDataProperties(handlerType, _options); + var tempDataProperties = SaveTempDataPropertyFilterBase.GetTempDataProperties(_tempDataSerializer, handlerType); if (tempDataProperties == null) { return; diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Controller.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Controller.cs index 7af52c185a..6d2a841d7c 100644 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Controller.cs +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Controller.cs @@ -7,7 +7,6 @@ using Microsoft.AspNetCore.Mvc.Filters; using Microsoft.AspNetCore.Mvc.ModelBinding; using Microsoft.AspNetCore.Mvc.ViewFeatures; using Microsoft.Extensions.DependencyInjection; -using Newtonsoft.Json; namespace Microsoft.AspNetCore.Mvc { @@ -299,14 +298,13 @@ namespace Microsoft.AspNetCore.Mvc /// to JSON. /// /// The object to serialize. - /// The to be used by - /// the formatter. + /// The serializer settings to be used by the formatter. /// The created that serializes the specified /// as JSON format for the response. - /// Callers should cache an instance of to avoid + /// Callers should cache an instance of serializer settings to avoid /// recreating cached data with each call. [NonAction] - public virtual JsonResult Json(object data, JsonSerializerSettings serializerSettings) + public virtual JsonResult Json(object data, object serializerSettings) { if (serializerSettings == null) { diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/CookieTempDataProvider.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/CookieTempDataProvider.cs index 6a52e7b636..3b4e40221c 100644 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/CookieTempDataProvider.cs +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/CookieTempDataProvider.cs @@ -6,7 +6,7 @@ using System.Collections.Generic; using Microsoft.AspNetCore.DataProtection; using Microsoft.AspNetCore.Http; using Microsoft.AspNetCore.Internal; -using Microsoft.AspNetCore.Mvc.ViewFeatures.Filters; +using Microsoft.AspNetCore.Mvc.ViewFeatures.Infrastructure; using Microsoft.AspNetCore.WebUtilities; using Microsoft.Extensions.Logging; using Microsoft.Extensions.Options; @@ -30,11 +30,12 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures public CookieTempDataProvider( IDataProtectionProvider dataProtectionProvider, ILoggerFactory loggerFactory, - IOptions options) + IOptions options, + TempDataSerializer tempDataSerializer) { _dataProtector = dataProtectionProvider.CreateProtector(Purpose); _logger = loggerFactory.CreateLogger(); - _tempDataSerializer = new TempDataSerializer(); + _tempDataSerializer = tempDataSerializer; _chunkingCookieManager = new ChunkingCookieManager(); _options = options.Value; } diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/DependencyInjection/MvcViewFeaturesMvcCoreBuilderExtensions.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/DependencyInjection/MvcViewFeaturesMvcCoreBuilderExtensions.cs index 1c171ad4a3..9ef038271d 100644 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/DependencyInjection/MvcViewFeaturesMvcCoreBuilderExtensions.cs +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/DependencyInjection/MvcViewFeaturesMvcCoreBuilderExtensions.cs @@ -16,6 +16,7 @@ using Microsoft.AspNetCore.Mvc.ViewEngines; using Microsoft.AspNetCore.Mvc.ViewFeatures; using Microsoft.AspNetCore.Mvc.ViewFeatures.Buffers; using Microsoft.AspNetCore.Mvc.ViewFeatures.Filters; +using Microsoft.AspNetCore.Mvc.ViewFeatures.Infrastructure; using Microsoft.Extensions.DependencyInjection.Extensions; using Microsoft.Extensions.Options; @@ -169,16 +170,7 @@ namespace Microsoft.Extensions.DependencyInjection services.TryAddSingleton(s => s.GetRequiredService()); services.TryAddSingleton(); - // - // JSON Helper - // - services.TryAddSingleton(); - services.TryAdd(ServiceDescriptor.Singleton(serviceProvider => - { - var options = serviceProvider.GetRequiredService>().Value; - var charPool = serviceProvider.GetRequiredService>(); - return new JsonOutputFormatter(options.SerializerSettings, charPool); - })); + services.TryAddSingleton(); // // View Components @@ -212,6 +204,7 @@ namespace Microsoft.Extensions.DependencyInjection // This does caching so it should stay singleton services.TryAddSingleton(); + services.TryAddSingleton(); // // Antiforgery diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Filters/SaveTempDataPropertyFilterBase.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Filters/SaveTempDataPropertyFilterBase.cs index 548772b6d4..53c5ca3751 100644 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Filters/SaveTempDataPropertyFilterBase.cs +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Filters/SaveTempDataPropertyFilterBase.cs @@ -5,6 +5,7 @@ using System; using System.Collections.Generic; using System.Diagnostics; using System.Reflection; +using Microsoft.AspNetCore.Mvc.ViewFeatures.Infrastructure; using Microsoft.Extensions.Internal; namespace Microsoft.AspNetCore.Mvc.ViewFeatures.Filters @@ -80,7 +81,9 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures.Filters } } - public static IReadOnlyList GetTempDataProperties(Type type, MvcViewOptions viewOptions) + public static IReadOnlyList GetTempDataProperties( + TempDataSerializer tempDataSerializer, + Type type) { List results = null; @@ -92,7 +95,7 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures.Filters var tempDataAttribute = property.GetCustomAttribute(); if (tempDataAttribute != null) { - ValidateProperty(propertyHelper.Property); + ValidateProperty(tempDataSerializer, propertyHelper.Property); if (results == null) { results = new List(); @@ -111,7 +114,7 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures.Filters return results; } - private static void ValidateProperty(PropertyInfo property) + private static void ValidateProperty(TempDataSerializer tempDataSerializer, PropertyInfo property) { if (!(property.SetMethod != null && property.SetMethod.IsPublic && @@ -122,16 +125,13 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures.Filters Resources.FormatTempDataProperties_PublicGetterSetter(property.DeclaringType.FullName, property.Name, nameof(TempDataAttribute))); } - var propertyType = Nullable.GetUnderlyingType(property.PropertyType) ?? property.PropertyType; - - if (!TempDataSerializer.CanSerializeType(propertyType, out var errorMessage)) + if (!tempDataSerializer.CanSerializeType(property.PropertyType)) { - var messageWithPropertyInfo = Resources.FormatTempDataProperties_InvalidType( - property.DeclaringType.FullName, + throw new InvalidOperationException(Resources.FormatTempDataProperties_InvalidType( + tempDataSerializer.GetType().FullName, + TypeNameHelper.GetTypeDisplayName(property.DeclaringType), property.Name, - nameof(TempDataAttribute)); - - throw new InvalidOperationException($"{messageWithPropertyInfo} {errorMessage}"); + TypeNameHelper.GetTypeDisplayName(property.PropertyType))); } } } diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Filters/TempDataApplicationModelProvider.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Filters/TempDataApplicationModelProvider.cs index dce36d87da..59ec9926ad 100644 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Filters/TempDataApplicationModelProvider.cs +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Filters/TempDataApplicationModelProvider.cs @@ -3,17 +3,17 @@ using System; using Microsoft.AspNetCore.Mvc.ApplicationModels; -using Microsoft.Extensions.Options; +using Microsoft.AspNetCore.Mvc.ViewFeatures.Infrastructure; namespace Microsoft.AspNetCore.Mvc.ViewFeatures.Filters { internal class TempDataApplicationModelProvider : IApplicationModelProvider { - private readonly MvcViewOptions _options; + private readonly TempDataSerializer _tempDataSerializer; - public TempDataApplicationModelProvider(IOptions options) + public TempDataApplicationModelProvider(TempDataSerializer tempDataSerializer) { - _options = options.Value; + _tempDataSerializer = tempDataSerializer; } /// @@ -37,7 +37,7 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures.Filters { var modelType = controllerModel.ControllerType.AsType(); - var tempDataProperties = SaveTempDataPropertyFilterBase.GetTempDataProperties(modelType, _options); + var tempDataProperties = SaveTempDataPropertyFilterBase.GetTempDataProperties(_tempDataSerializer, modelType); if (tempDataProperties == null) { continue; diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Infrastructure/DefaultTempDataSerializer.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Infrastructure/DefaultTempDataSerializer.cs new file mode 100644 index 0000000000..7c2ebfb86a --- /dev/null +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Infrastructure/DefaultTempDataSerializer.cs @@ -0,0 +1,32 @@ +// Copyright (c) .NET Foundation. All rights reserved. +// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information. + +using System; +using System.Collections.Generic; +using Microsoft.Extensions.DependencyInjection; + +namespace Microsoft.AspNetCore.Mvc.ViewFeatures.Infrastructure +{ + internal class DefaultTempDataSerializer : TempDataSerializer + { + public override IDictionary Deserialize(byte[] unprotectedData) + { + throw new InvalidOperationException(Core.Resources.FormatReferenceToNewtonsoftJsonRequired( + Resources.DeserializingTempData, + "Microsoft.AspNetCore.Mvc.NewtonsoftJson", + nameof(IMvcBuilder), + "AddNewtonsoftJson", + "ConfigureServices(...)")); + } + + public override byte[] Serialize(IDictionary values) + { + throw new InvalidOperationException(Core.Resources.FormatReferenceToNewtonsoftJsonRequired( + Resources.SerializingTempData, + "Microsoft.AspNetCore.Mvc.NewtonsoftJson", + nameof(IMvcBuilder), + "AddNewtonsoftJson", + "ConfigureServices(...)")); + } + } +} diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Infrastructure/TempDataSerializer.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Infrastructure/TempDataSerializer.cs new file mode 100644 index 0000000000..ce8c1606de --- /dev/null +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Infrastructure/TempDataSerializer.cs @@ -0,0 +1,39 @@ +// Copyright (c) .NET Foundation. All rights reserved. +// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information. + +using System; +using System.Collections.Generic; + +namespace Microsoft.AspNetCore.Mvc.ViewFeatures.Infrastructure +{ + /// + /// Serializes and deserializes the contents of . + /// + public abstract class TempDataSerializer + { + /// + /// Deserializes to a + /// used to initialize an instance of . + /// + /// Serialized representation of . + /// The deserialized . + public abstract IDictionary Deserialize(byte[] unprotectedData); + + /// + /// Serializes the contents of . + /// + /// The contents of . + /// The serialized bytes. + public abstract byte[] Serialize(IDictionary values); + + /// + /// Determines if the serializer supports the specified . + /// + /// Defaults to returning for all instances. + /// + /// + /// The . + /// if the serializer supports serializing , otherwise . + public virtual bool CanSerializeType(Type type) => true; + } +} diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Microsoft.AspNetCore.Mvc.ViewFeatures.csproj b/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Microsoft.AspNetCore.Mvc.ViewFeatures.csproj index 8fcab3e0cb..2bbb0d2944 100644 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Microsoft.AspNetCore.Mvc.ViewFeatures.csproj +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Microsoft.AspNetCore.Mvc.ViewFeatures.csproj @@ -16,13 +16,11 @@ Microsoft.AspNetCore.Mvc.ViewComponent - - diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Properties/AssemblyInfo.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Properties/AssemblyInfo.cs index 581085ab42..01241ba199 100644 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Properties/AssemblyInfo.cs +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Properties/AssemblyInfo.cs @@ -8,6 +8,7 @@ using System.Runtime.CompilerServices; [assembly: InternalsVisibleTo("Microsoft.AspNetCore.Mvc.TagHelpers, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] [assembly: InternalsVisibleTo("Microsoft.AspNetCore.Mvc.Test, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] +[assembly: InternalsVisibleTo("Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] [assembly: InternalsVisibleTo("Microsoft.AspNetCore.Mvc.Razor.Test, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] [assembly: InternalsVisibleTo("Microsoft.AspNetCore.Mvc.RazorPages.Test, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] [assembly: InternalsVisibleTo("Microsoft.AspNetCore.Mvc.TagHelpers.Test, PublicKey=0024000004800000940000000602000000240000525341310004000001000100f33a29044fa9d740c9b3213a93e57c84b472c84e0b8a0e1ae48e67a9f8f6de9d5f7f3d52ac23e48ac51801f1dc950abe901da34d2a9e3baadb141a17c77ef3c565dd5ee5054b91cf63bb3c6ab83f72ab3aafe93d0fc3c2348b764fafb0b1c0733de51459aeab46580384bf9d74c4e28164b7cde247f891ba07891c9d872ad2bb")] diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Properties/Resources.Designer.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Properties/Resources.Designer.cs index 78f9ebcfb6..c83ef0745a 100644 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Properties/Resources.Designer.cs +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Properties/Resources.Designer.cs @@ -668,48 +668,6 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures internal static string FormatViewComponentResult_NameOrTypeMustBeSet(object p0, object p1) => string.Format(CultureInfo.CurrentCulture, GetString("ViewComponentResult_NameOrTypeMustBeSet"), p0, p1); - /// - /// Cannot deserialize {0} of type '{1}'. - /// - internal static string TempData_CannotDeserializeToken - { - get => GetString("TempData_CannotDeserializeToken"); - } - - /// - /// Cannot deserialize {0} of type '{1}'. - /// - internal static string FormatTempData_CannotDeserializeToken(object p0, object p1) - => string.Format(CultureInfo.CurrentCulture, GetString("TempData_CannotDeserializeToken"), p0, p1); - - /// - /// The '{0}' cannot serialize a dictionary with a key of type '{1}'. The key must be of type '{2}'. - /// - internal static string TempData_CannotSerializeDictionary - { - get => GetString("TempData_CannotSerializeDictionary"); - } - - /// - /// The '{0}' cannot serialize a dictionary with a key of type '{1}'. The key must be of type '{2}'. - /// - internal static string FormatTempData_CannotSerializeDictionary(object p0, object p1, object p2) - => string.Format(CultureInfo.CurrentCulture, GetString("TempData_CannotSerializeDictionary"), p0, p1, p2); - - /// - /// The '{0}' cannot serialize an object of type '{1}'. - /// - internal static string TempData_CannotSerializeType - { - get => GetString("TempData_CannotSerializeType"); - } - - /// - /// The '{0}' cannot serialize an object of type '{1}'. - /// - internal static string FormatTempData_CannotSerializeType(object p0, object p1) - => string.Format(CultureInfo.CurrentCulture, GetString("TempData_CannotSerializeType"), p0, p1); - /// /// The collection already contains an entry with key '{0}'. /// @@ -794,20 +752,6 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures internal static string FormatViewEnginesAreRequired(object p0, object p1, object p2) => string.Format(CultureInfo.CurrentCulture, GetString("ViewEnginesAreRequired"), p0, p1, p2); - /// - /// The '{0}.{1}' property with {2} is invalid. - /// - internal static string TempDataProperties_InvalidType - { - get => GetString("TempDataProperties_InvalidType"); - } - - /// - /// The '{0}.{1}' property with {2} is invalid. - /// - internal static string FormatTempDataProperties_InvalidType(object p0, object p1, object p2) - => string.Format(CultureInfo.CurrentCulture, GetString("TempDataProperties_InvalidType"), p0, p1, p2); - /// /// The '{0}.{1}' property with {2} is invalid. A property using {2} must have a public getter and setter. /// @@ -822,6 +766,48 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures internal static string FormatTempDataProperties_PublicGetterSetter(object p0, object p1, object p2) => string.Format(CultureInfo.CurrentCulture, GetString("TempDataProperties_PublicGetterSetter"), p0, p1, p2); + /// + /// TempData serializer '{0}' cannot serialize property '{1}.{2}' of type '{3}'. + /// + internal static string TempDataProperties_InvalidType + { + get => GetString("TempDataProperties_InvalidType"); + } + + /// + /// TempData serializer '{0}' cannot serialize property '{1}.{2}' of type '{3}'. + /// + internal static string FormatTempDataProperties_InvalidType(object p0, object p1, object p2, object p3) + => string.Format(CultureInfo.CurrentCulture, GetString("TempDataProperties_InvalidType"), p0, p1, p2, p3); + + /// + /// Deserializing TempDataDictionary + /// + internal static string DeserializingTempData + { + get => GetString("DeserializingTempData"); + } + + /// + /// Deserializing TempDataDictionary + /// + internal static string FormatDeserializingTempData() + => GetString("DeserializingTempData"); + + /// + /// Serializing TempDataDictionary + /// + internal static string SerializingTempData + { + get => GetString("SerializingTempData"); + } + + /// + /// Serializing TempDataDictionary + /// + internal static string FormatSerializingTempData() + => GetString("SerializingTempData"); + private static string GetString(string name, params string[] formatterNames) { var value = _resourceManager.GetString(name); diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Rendering/DefaultJsonHelper.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Rendering/DefaultJsonHelper.cs new file mode 100644 index 0000000000..df0646a686 --- /dev/null +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Rendering/DefaultJsonHelper.cs @@ -0,0 +1,24 @@ + +// Copyright (c) .NET Foundation. All rights reserved. +// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information. + +using System; +using Microsoft.AspNetCore.Html; +using Microsoft.Extensions.DependencyInjection; + +namespace Microsoft.AspNetCore.Mvc.Rendering +{ + internal class DefaultJsonHelper : IJsonHelper + { + /// + public IHtmlContent Serialize(object value) + { + throw new InvalidOperationException(Core.Resources.FormatReferenceToNewtonsoftJsonRequired( + $"{nameof(IJsonHelper)}.{nameof(Serialize)}", + "Microsoft.AspNetCore.Mvc.NewtonsoftJson", + nameof(IMvcBuilder), + "AddNewtonsoftJson", + "ConfigureServices(...)")); + } + } +} diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Rendering/IJsonHelper.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Rendering/IJsonHelper.cs index c958590e0c..120a54583a 100644 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Rendering/IJsonHelper.cs +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Rendering/IJsonHelper.cs @@ -2,7 +2,6 @@ // Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information. using Microsoft.AspNetCore.Html; -using Newtonsoft.Json; namespace Microsoft.AspNetCore.Mvc.Rendering { @@ -17,15 +16,5 @@ namespace Microsoft.AspNetCore.Mvc.Rendering /// The value to serialize as JSON. /// A new containing the serialized JSON. IHtmlContent Serialize(object value); - - /// - /// Returns serialized JSON for the . - /// - /// The value to serialize as JSON. - /// - /// The to be used by the serializer. - /// - /// A new containing the serialized JSON. - IHtmlContent Serialize(object value, JsonSerializerSettings serializerSettings); } } diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Resources.resx b/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Resources.resx index 4bfed7a827..c1d17c6e7b 100644 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Resources.resx +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/Resources.resx @@ -259,15 +259,6 @@ Either the '{0}' or '{1}' property must be set in order to invoke a view component. - - Cannot deserialize {0} of type '{1}'. - - - The '{0}' cannot serialize a dictionary with a key of type '{1}'. The key must be of type '{2}'. - - - The '{0}' cannot serialize an object of type '{1}'. - The collection already contains an entry with key '{0}'. @@ -286,10 +277,16 @@ '{0}.{1}' must not be empty. At least one '{2}' is required to locate a view for rendering. - - The '{0}.{1}' property with {2} is invalid. - The '{0}.{1}' property with {2} is invalid. A property using {2} must have a public getter and setter. + + TempData serializer '{0}' cannot serialize property '{1}.{2}' of type '{3}'. + + + Deserializing TempDataDictionary + + + Serializing TempDataDictionary + \ No newline at end of file diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/SessionStateTempDataProvider.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/SessionStateTempDataProvider.cs index 50fd26799c..0aa5cf3e40 100644 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/SessionStateTempDataProvider.cs +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc.ViewFeatures/SessionStateTempDataProvider.cs @@ -4,7 +4,7 @@ using System; using System.Collections.Generic; using Microsoft.AspNetCore.Http; -using Microsoft.AspNetCore.Mvc.ViewFeatures.Filters; +using Microsoft.AspNetCore.Mvc.ViewFeatures.Infrastructure; namespace Microsoft.AspNetCore.Mvc.ViewFeatures { @@ -17,9 +17,9 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures internal const string TempDataSessionStateKey = "__ControllerTempData"; private readonly TempDataSerializer _tempDataSerializer; - public SessionStateTempDataProvider() + public SessionStateTempDataProvider(TempDataSerializer tempDataSerializer) { - _tempDataSerializer = new TempDataSerializer(); + _tempDataSerializer = tempDataSerializer; } /// diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc/Microsoft.AspNetCore.Mvc.csproj b/src/Mvc/src/Microsoft.AspNetCore.Mvc/Microsoft.AspNetCore.Mvc.csproj index 8dd6d2b434..525841955d 100644 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc/Microsoft.AspNetCore.Mvc.csproj +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc/Microsoft.AspNetCore.Mvc.csproj @@ -13,7 +13,6 @@ - diff --git a/src/Mvc/src/Microsoft.AspNetCore.Mvc/MvcServiceCollectionExtensions.cs b/src/Mvc/src/Microsoft.AspNetCore.Mvc/MvcServiceCollectionExtensions.cs index 03a73516d2..eb045d1900 100644 --- a/src/Mvc/src/Microsoft.AspNetCore.Mvc/MvcServiceCollectionExtensions.cs +++ b/src/Mvc/src/Microsoft.AspNetCore.Mvc/MvcServiceCollectionExtensions.cs @@ -49,9 +49,6 @@ namespace Microsoft.Extensions.DependencyInjection // +1 order builder.AddDataAnnotations(); // +1 order - // +10 order - builder.AddJsonFormatters(); - builder.AddCors(); return new MvcBuilder(builder.Services, builder.PartManager); diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.ApiExplorer.Test/Microsoft.AspNetCore.Mvc.ApiExplorer.Test.csproj b/src/Mvc/test/Microsoft.AspNetCore.Mvc.ApiExplorer.Test/Microsoft.AspNetCore.Mvc.ApiExplorer.Test.csproj index 7fe3a9c78f..7ee460ea11 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.ApiExplorer.Test/Microsoft.AspNetCore.Mvc.ApiExplorer.Test.csproj +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.ApiExplorer.Test/Microsoft.AspNetCore.Mvc.ApiExplorer.Test.csproj @@ -6,7 +6,7 @@ - + diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.Core.Test/CreatedAtActionResultTests.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.Core.Test/CreatedAtActionResultTests.cs index a461f42d85..01e7362bc2 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.Core.Test/CreatedAtActionResultTests.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.Core.Test/CreatedAtActionResultTests.cs @@ -91,7 +91,7 @@ namespace Microsoft.AspNetCore.Mvc { var options = Options.Create(new MvcOptions()); options.Value.OutputFormatters.Add(new StringOutputFormatter()); - options.Value.OutputFormatters.Add(new JsonOutputFormatter( + options.Value.OutputFormatters.Add(new NewtonsoftJsonOutputFormatter( new JsonSerializerSettings(), ArrayPool.Shared)); diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.Core.Test/CreatedAtRouteResultTests.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.Core.Test/CreatedAtRouteResultTests.cs index 9e7cf1df9f..7494544d31 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.Core.Test/CreatedAtRouteResultTests.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.Core.Test/CreatedAtRouteResultTests.cs @@ -10,6 +10,7 @@ using Microsoft.AspNetCore.Http; using Microsoft.AspNetCore.Mvc.Abstractions; using Microsoft.AspNetCore.Mvc.Formatters; using Microsoft.AspNetCore.Mvc.Infrastructure; +using Microsoft.AspNetCore.Mvc.NewtonsoftJson; using Microsoft.AspNetCore.Routing; using Microsoft.AspNetCore.Testing; using Microsoft.Extensions.DependencyInjection; @@ -106,7 +107,7 @@ namespace Microsoft.AspNetCore.Mvc { var options = Options.Create(new MvcOptions()); options.Value.OutputFormatters.Add(new StringOutputFormatter()); - options.Value.OutputFormatters.Add(new JsonOutputFormatter( + options.Value.OutputFormatters.Add(new NewtonsoftJsonOutputFormatter( new JsonSerializerSettings(), ArrayPool.Shared)); diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.Core.Test/CreatedResultTests.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.Core.Test/CreatedResultTests.cs index daa982e53f..f6bcf13473 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.Core.Test/CreatedResultTests.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.Core.Test/CreatedResultTests.cs @@ -9,6 +9,7 @@ using Microsoft.AspNetCore.Http; using Microsoft.AspNetCore.Mvc.Abstractions; using Microsoft.AspNetCore.Mvc.Formatters; using Microsoft.AspNetCore.Mvc.Infrastructure; +using Microsoft.AspNetCore.Mvc.NewtonsoftJson; using Microsoft.AspNetCore.Routing; using Microsoft.Extensions.DependencyInjection; using Microsoft.Extensions.Logging.Abstractions; @@ -92,7 +93,7 @@ namespace Microsoft.AspNetCore.Mvc { var options = Options.Create(new MvcOptions()); options.Value.OutputFormatters.Add(new StringOutputFormatter()); - options.Value.OutputFormatters.Add(new JsonOutputFormatter( + options.Value.OutputFormatters.Add(new NewtonsoftJsonOutputFormatter( new JsonSerializerSettings(), ArrayPool.Shared)); diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.Core.Test/Formatters/FormatFilterTest.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.Core.Test/Formatters/FormatFilterTest.cs index 7d5760fca9..0560d51d28 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.Core.Test/Formatters/FormatFilterTest.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.Core.Test/Formatters/FormatFilterTest.cs @@ -8,6 +8,7 @@ using Microsoft.AspNetCore.Http; using Microsoft.AspNetCore.Mvc.Abstractions; using Microsoft.AspNetCore.Mvc.Filters; using Microsoft.AspNetCore.Mvc.ModelBinding; +using Microsoft.AspNetCore.Mvc.NewtonsoftJson; using Microsoft.AspNetCore.Routing; using Microsoft.AspNetCore.Testing; using Microsoft.Extensions.Logging.Abstractions; @@ -467,7 +468,7 @@ namespace Microsoft.AspNetCore.Mvc.Formatters // Set up default output formatters. MvcOptions.OutputFormatters.Add(new HttpNoContentOutputFormatter()); MvcOptions.OutputFormatters.Add(new StringOutputFormatter()); - MvcOptions.OutputFormatters.Add(new JsonOutputFormatter( + MvcOptions.OutputFormatters.Add(new NewtonsoftJsonOutputFormatter( new JsonSerializerSettings(), ArrayPool.Shared)); diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.Core.Test/HttpNotFoundObjectResultTest.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.Core.Test/HttpNotFoundObjectResultTest.cs index 9bd11f8ab0..b6a64d8b53 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.Core.Test/HttpNotFoundObjectResultTest.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.Core.Test/HttpNotFoundObjectResultTest.cs @@ -8,6 +8,7 @@ using System.Threading.Tasks; using Microsoft.AspNetCore.Http; using Microsoft.AspNetCore.Mvc.Formatters; using Microsoft.AspNetCore.Mvc.Infrastructure; +using Microsoft.AspNetCore.Mvc.NewtonsoftJson; using Microsoft.Extensions.DependencyInjection; using Microsoft.Extensions.Logging.Abstractions; using Microsoft.Extensions.Options; @@ -71,7 +72,7 @@ namespace Microsoft.AspNetCore.Mvc { var options = Options.Create(new MvcOptions()); options.Value.OutputFormatters.Add(new StringOutputFormatter()); - options.Value.OutputFormatters.Add(new JsonOutputFormatter( + options.Value.OutputFormatters.Add(new NewtonsoftJsonOutputFormatter( new JsonSerializerSettings(), ArrayPool.Shared)); diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.Core.Test/HttpOkObjectResultTest.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.Core.Test/HttpOkObjectResultTest.cs index a6e6a4f99c..b8642a38f4 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.Core.Test/HttpOkObjectResultTest.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.Core.Test/HttpOkObjectResultTest.cs @@ -8,6 +8,7 @@ using Microsoft.AspNetCore.Http; using Microsoft.AspNetCore.Mvc.Abstractions; using Microsoft.AspNetCore.Mvc.Formatters; using Microsoft.AspNetCore.Mvc.Infrastructure; +using Microsoft.AspNetCore.Mvc.NewtonsoftJson; using Microsoft.AspNetCore.Routing; using Microsoft.Extensions.DependencyInjection; using Microsoft.Extensions.Logging.Abstractions; @@ -72,7 +73,7 @@ namespace Microsoft.AspNetCore.Mvc { var options = Options.Create(new MvcOptions()); options.Value.OutputFormatters.Add(new StringOutputFormatter()); - options.Value.OutputFormatters.Add(new JsonOutputFormatter( + options.Value.OutputFormatters.Add(new NewtonsoftJsonOutputFormatter( new JsonSerializerSettings(), ArrayPool.Shared)); diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.Core.Test/JsonResultTest.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.Core.Test/JsonResultTest.cs new file mode 100644 index 0000000000..a89c95e919 --- /dev/null +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.Core.Test/JsonResultTest.cs @@ -0,0 +1,32 @@ +// Copyright (c) .NET Foundation. All rights reserved. +// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information. + +using System; +using System.Threading.Tasks; +using Microsoft.AspNetCore.Http; +using Moq; +using Xunit; + +namespace Microsoft.AspNetCore.Mvc.Core +{ + public class JsonResultTest + { + [Fact] + public async Task ExecuteResultAsync_ThrowsIfExecutorIsNotAvailableInServices() + { + // Arrange + var jsonResult = new JsonResult("Hello"); + var message = "'JsonResult.ExecuteResultAsync' requires a reference to 'Microsoft.AspNetCore.Mvc.NewtonsoftJson'. " + + "Configure your application by adding a reference to the 'Microsoft.AspNetCore.Mvc.NewtonsoftJson' package and calling 'IMvcBuilder.AddNewtonsoftJson' " + + "inside the call to 'ConfigureServices(...)' in the application startup code."; + var actionContext = new ActionContext + { + HttpContext = new DefaultHttpContext { RequestServices = Mock.Of() } + }; + + // Act & Assert + var ex = await Assert.ThrowsAsync(() => jsonResult.ExecuteResultAsync(actionContext)); + Assert.Equal(message, ex.Message); + } + } +} diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.Core.Test/Microsoft.AspNetCore.Mvc.Core.Test.csproj b/src/Mvc/test/Microsoft.AspNetCore.Mvc.Core.Test/Microsoft.AspNetCore.Mvc.Core.Test.csproj index 320df56f66..70c1937a8f 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.Core.Test/Microsoft.AspNetCore.Mvc.Core.Test.csproj +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.Core.Test/Microsoft.AspNetCore.Mvc.Core.Test.csproj @@ -10,7 +10,7 @@ - + diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.Core.Test/ModelBinding/Binders/BodyModelBinderTests.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.Core.Test/ModelBinding/Binders/BodyModelBinderTests.cs index 6567e08b45..ffdf5733d8 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.Core.Test/ModelBinding/Binders/BodyModelBinderTests.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.Core.Test/ModelBinding/Binders/BodyModelBinderTests.cs @@ -10,6 +10,7 @@ using System.Text; using System.Threading.Tasks; using Microsoft.AspNetCore.Http; using Microsoft.AspNetCore.Mvc.Formatters; +using Microsoft.AspNetCore.Mvc.NewtonsoftJson; using Microsoft.Extensions.Logging; using Microsoft.Extensions.Logging.Abstractions; using Microsoft.Extensions.Logging.Testing; @@ -711,12 +712,12 @@ namespace Microsoft.AspNetCore.Mvc.ModelBinding.Binders } } - private class TestableJsonInputFormatter : JsonInputFormatter + private class TestableJsonInputFormatter : NewtonsoftJsonInputFormatter { private readonly bool _throwNonInputFormatterException; public TestableJsonInputFormatter(bool throwNonInputFormatterException) - : base(GetLogger(), new JsonSerializerSettings(), ArrayPool.Shared, new DefaultObjectPoolProvider(), new MvcOptions(), new MvcJsonOptions() + : base(GetLogger(), new JsonSerializerSettings(), ArrayPool.Shared, new DefaultObjectPoolProvider(), new MvcOptions(), new MvcNewtonsoftJsonOptions() { // The tests that use this class rely on the 2.1 behavior of this formatter. AllowInputFormatterExceptionMessages = true, @@ -781,12 +782,12 @@ namespace Microsoft.AspNetCore.Mvc.ModelBinding.Binders } } - private class DerivedJsonInputFormatter : JsonInputFormatter + private class DerivedJsonInputFormatter : NewtonsoftJsonInputFormatter { private readonly bool _throwNonInputFormatterException; public DerivedJsonInputFormatter(bool throwNonInputFormatterException) - : base(GetLogger(), new JsonSerializerSettings(), ArrayPool.Shared, new DefaultObjectPoolProvider(), new MvcOptions(), new MvcJsonOptions() + : base(GetLogger(), new JsonSerializerSettings(), ArrayPool.Shared, new DefaultObjectPoolProvider(), new MvcOptions(), new MvcNewtonsoftJsonOptions() { // The tests that use this class rely on the 2.1 behavior of this formatter. AllowInputFormatterExceptionMessages = true, diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.FunctionalTests/ApiBehaviorTest.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.FunctionalTests/ApiBehaviorTest.cs index 521db7b904..370db1ebcb 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.FunctionalTests/ApiBehaviorTest.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.FunctionalTests/ApiBehaviorTest.cs @@ -10,6 +10,7 @@ using System.Text; using System.Threading.Tasks; using BasicWebSite.Models; using Microsoft.AspNetCore.Hosting; +using Microsoft.AspNetCore.Mvc.NewtonsoftJson; using Newtonsoft.Json; using Newtonsoft.Json.Linq; using Xunit; @@ -53,7 +54,12 @@ namespace Microsoft.AspNetCore.Mvc.FunctionalTests // Assert await response.AssertStatusCodeAsync(HttpStatusCode.BadRequest); Assert.Equal("application/problem+json", response.Content.Headers.ContentType.MediaType); - var problemDetails = JsonConvert.DeserializeObject(await response.Content.ReadAsStringAsync()); + var problemDetails = JsonConvert.DeserializeObject( + await response.Content.ReadAsStringAsync(), + new JsonSerializerSettings + { + Converters = { new ValidationProblemDetailsConverter() } + }); Assert.Collection( problemDetails.Errors.OrderBy(kvp => kvp.Key), kvp => @@ -273,7 +279,12 @@ namespace Microsoft.AspNetCore.Mvc.FunctionalTests // Assert await response.AssertStatusCodeAsync(HttpStatusCode.NotFound); var content = await response.Content.ReadAsStringAsync(); - var problemDetails = JsonConvert.DeserializeObject(content); + var problemDetails = JsonConvert.DeserializeObject( + content, + new JsonSerializerSettings + { + Converters = { new ProblemDetailsConverter() } + }); Assert.Equal(404, problemDetails.Status); Assert.Collection( problemDetails.Extensions, @@ -328,7 +339,12 @@ namespace Microsoft.AspNetCore.Mvc.FunctionalTests // Assert await response.AssertStatusCodeAsync(HttpStatusCode.BadRequest); var content = await response.Content.ReadAsStringAsync(); - var validationProblemDetails = JsonConvert.DeserializeObject(content); + var validationProblemDetails = JsonConvert.DeserializeObject( + content, + new JsonSerializerSettings + { + Converters = { new ValidationProblemDetailsConverter() } + }); Assert.Equal("Error", validationProblemDetails.Title); Assert.Equal(400, validationProblemDetails.Status); diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.FunctionalTests/ApiExplorerTest.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.FunctionalTests/ApiExplorerTest.cs index e333821046..8df0fb27e2 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.FunctionalTests/ApiExplorerTest.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.FunctionalTests/ApiExplorerTest.cs @@ -575,7 +575,7 @@ namespace Microsoft.AspNetCore.Mvc.FunctionalTests // Arrange var type1 = typeof(ApiExplorerWebSite.Product).FullName; var type2 = typeof(SerializableError).FullName; - var expectedMediaTypes = new[] { "application/json", "text/json", "application/xml", "text/xml" }; + var expectedMediaTypes = new[] { "application/json", "application/xml", "text/json", "text/xml" }; // Act var response = await Client.GetAsync( @@ -592,13 +592,13 @@ namespace Microsoft.AspNetCore.Mvc.FunctionalTests Assert.Equal(201, responseType.StatusCode); Assert.Equal( expectedMediaTypes, - responseType.ResponseFormats.Select(responseFormat => responseFormat.MediaType).ToArray()); + responseType.ResponseFormats.Select(responseFormat => responseFormat.MediaType).OrderBy(o => o).ToArray()); responseType = description.SupportedResponseTypes[1]; Assert.Equal(type2, responseType.ResponseType); Assert.Equal(400, responseType.StatusCode); Assert.Equal( expectedMediaTypes, - responseType.ResponseFormats.Select(responseFormat => responseFormat.MediaType).ToArray()); + responseType.ResponseFormats.Select(responseFormat => responseFormat.MediaType).OrderBy(o => o).ToArray()); } [Fact] @@ -639,7 +639,7 @@ namespace Microsoft.AspNetCore.Mvc.FunctionalTests // Arrange var type1 = typeof(ApiExplorerWebSite.Product).FullName; var type2 = typeof(SerializableError).FullName; - var expectedMediaTypes = new[] { "application/json", "text/json", "application/xml", "text/xml" }; + var expectedMediaTypes = new[] { "application/json", "application/xml", "text/json", "text/xml" }; // Act var response = await Client.GetAsync( @@ -656,13 +656,13 @@ namespace Microsoft.AspNetCore.Mvc.FunctionalTests Assert.Equal(200, responseType.StatusCode); Assert.Equal( expectedMediaTypes, - responseType.ResponseFormats.Select(responseFormat => responseFormat.MediaType).ToArray()); + responseType.ResponseFormats.Select(responseFormat => responseFormat.MediaType).OrderBy(o => o).ToArray()); responseType = description.SupportedResponseTypes[1]; Assert.Equal(type2, responseType.ResponseType); Assert.Equal(400, responseType.StatusCode); Assert.Equal( expectedMediaTypes, - responseType.ResponseFormats.Select(responseFormat => responseFormat.MediaType).ToArray()); + responseType.ResponseFormats.Select(responseFormat => responseFormat.MediaType).OrderBy(o => o).ToArray()); } [Fact] @@ -789,9 +789,9 @@ namespace Microsoft.AspNetCore.Mvc.FunctionalTests Assert.Equal(typeof(XmlDataContractSerializerOutputFormatter).FullName, applicationXml.FormatterType); var textJson = Assert.Single(responseType.ResponseFormats, f => f.MediaType == "text/json"); - Assert.Equal(typeof(JsonOutputFormatter).FullName, textJson.FormatterType); + Assert.Equal(typeof(NewtonsoftJsonOutputFormatter).FullName, textJson.FormatterType); var applicationJson = Assert.Single(responseType.ResponseFormats, f => f.MediaType == "application/json"); - Assert.Equal(typeof(JsonOutputFormatter).FullName, applicationJson.FormatterType); + Assert.Equal(typeof(NewtonsoftJsonOutputFormatter).FullName, applicationJson.FormatterType); } [Fact] @@ -812,10 +812,10 @@ namespace Microsoft.AspNetCore.Mvc.FunctionalTests var applicationJson = Assert.Single( responseType.ResponseFormats, format => format.MediaType == "application/json"); - Assert.Equal(typeof(JsonOutputFormatter).FullName, applicationJson.FormatterType); + Assert.Equal(typeof(NewtonsoftJsonOutputFormatter).FullName, applicationJson.FormatterType); var textJson = Assert.Single(responseType.ResponseFormats, f => f.MediaType == "text/json"); - Assert.Equal(typeof(JsonOutputFormatter).FullName, textJson.FormatterType); + Assert.Equal(typeof(NewtonsoftJsonOutputFormatter).FullName, textJson.FormatterType); } [Fact] @@ -840,7 +840,7 @@ namespace Microsoft.AspNetCore.Mvc.FunctionalTests responseFormat => { Assert.Equal("application/hal+json", responseFormat.MediaType); - Assert.Equal(typeof(JsonOutputFormatter).FullName, responseFormat.FormatterType); + Assert.Equal(typeof(NewtonsoftJsonOutputFormatter).FullName, responseFormat.FormatterType); }); } @@ -869,12 +869,12 @@ namespace Microsoft.AspNetCore.Mvc.FunctionalTests [ConditionalTheory] // Mono issue - https://github.com/aspnet/External/issues/18 [FrameworkSkipCondition(RuntimeFrameworks.Mono)] - [InlineData("Controller", "text/xml", "Microsoft.AspNetCore.Mvc.Formatters.XmlDataContractSerializerOutputFormatter")] - [InlineData("Action", "application/json", "Microsoft.AspNetCore.Mvc.Formatters.JsonOutputFormatter")] + [InlineData("Controller", "text/xml", typeof(XmlDataContractSerializerOutputFormatter))] + [InlineData("Action", "application/json", typeof(NewtonsoftJsonOutputFormatter))] public async Task ApiExplorer_ResponseContentType_OverrideOnAction( string action, string contentType, - string formatterType) + Type formatterType) { // Arrange & Act var response = await Client.GetAsync( @@ -889,7 +889,7 @@ namespace Microsoft.AspNetCore.Mvc.FunctionalTests var responseType = Assert.Single(description.SupportedResponseTypes); var responseFormat = Assert.Single(responseType.ResponseFormats); Assert.Equal(contentType, responseFormat.MediaType); - Assert.Equal(formatterType, responseFormat.FormatterType); + Assert.Equal(formatterType.FullName, responseFormat.FormatterType); } [Fact] diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.FunctionalTests/BasicTests.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.FunctionalTests/BasicTests.cs index ffaebb4fe0..d17c06b9d9 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.FunctionalTests/BasicTests.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.FunctionalTests/BasicTests.cs @@ -280,7 +280,7 @@ namespace Microsoft.AspNetCore.Mvc.FunctionalTests Assert.Equal("text/html", response.Content.Headers.ContentType.MediaType); var actualBody = await response.Content.ReadAsStringAsync(); - Assert.Equal(expectedBody, actualBody, ignoreLineEndingDifferences: true); + Assert.Equal(expectedBody, actualBody.Trim(), ignoreLineEndingDifferences: true); } [Fact] @@ -302,7 +302,7 @@ namespace Microsoft.AspNetCore.Mvc.FunctionalTests Assert.Equal("text/html", response.Content.Headers.ContentType.MediaType); var actualBody = await response.Content.ReadAsStringAsync(); - Assert.Equal(expectedBody, actualBody, ignoreLineEndingDifferences: true); + Assert.Equal(expectedBody, actualBody.Trim(), ignoreLineEndingDifferences: true); } public static IEnumerable HtmlHelperLinkGenerationData diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.FunctionalTests/JsonOutputFormatterTests.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.FunctionalTests/JsonOutputFormatterTests.cs index 09ed5b4a07..692438f82b 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.FunctionalTests/JsonOutputFormatterTests.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.FunctionalTests/JsonOutputFormatterTests.cs @@ -8,6 +8,7 @@ using System.Net.Http.Headers; using System.Text; using System.Threading.Tasks; using Microsoft.AspNetCore.Mvc.Formatters; +using Microsoft.AspNetCore.Mvc.NewtonsoftJson; using Microsoft.AspNetCore.Testing.xunit; using Newtonsoft.Json; using Xunit; diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.FunctionalTests/TempDataPropertyTest.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.FunctionalTests/TempDataPropertyTest.cs index 18a1870efd..9899037d01 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.FunctionalTests/TempDataPropertyTest.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.FunctionalTests/TempDataPropertyTest.cs @@ -38,13 +38,13 @@ namespace Microsoft.AspNetCore.Mvc.FunctionalTests var redirectResponse = await Client.PostAsync("TempDataProperty/CreateForView", content); // Assert 1 - Assert.Equal(HttpStatusCode.Redirect, redirectResponse.StatusCode); + await redirectResponse.AssertStatusCodeAsync(HttpStatusCode.Redirect); // Act 2 var response = await Client.SendAsync(GetRequest(redirectResponse.Headers.Location.ToString(), redirectResponse)); // Assert 2 - Assert.Equal(HttpStatusCode.OK, response.StatusCode); + await response.AssertStatusCodeAsync(HttpStatusCode.OK); var body = await response.Content.ReadAsStringAsync(); Assert.Equal(expected, body.ToString().Trim()); } diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.IntegrationTests/BodyValidationIntegrationTests.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.IntegrationTests/BodyValidationIntegrationTests.cs index e4ee6a548c..8d437448d1 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.IntegrationTests/BodyValidationIntegrationTests.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.IntegrationTests/BodyValidationIntegrationTests.cs @@ -453,7 +453,7 @@ namespace Microsoft.AspNetCore.Mvc.IntegrationTests }); // Override the AllowInputFormatterExceptionMessages setting ModelBindingTestHelper chooses. - var options = testContext.GetService>().Value; + var options = testContext.GetService>().Value; options.AllowInputFormatterExceptionMessages = false; var parameterBinder = ModelBindingTestHelper.GetParameterBinder(testContext.HttpContext.RequestServices); @@ -553,7 +553,7 @@ namespace Microsoft.AspNetCore.Mvc.IntegrationTests }); // Override the AllowInputFormatterExceptionMessages setting ModelBindingTestHelper chooses. - var options = testContext.GetService>().Value; + var options = testContext.GetService>().Value; options.AllowInputFormatterExceptionMessages = false; var parameterBinder = ModelBindingTestHelper.GetParameterBinder(testContext.HttpContext.RequestServices); diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.IntegrationTests/Microsoft.AspNetCore.Mvc.IntegrationTests.csproj b/src/Mvc/test/Microsoft.AspNetCore.Mvc.IntegrationTests/Microsoft.AspNetCore.Mvc.IntegrationTests.csproj index 06f9586e15..8750db9a40 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.IntegrationTests/Microsoft.AspNetCore.Mvc.IntegrationTests.csproj +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.IntegrationTests/Microsoft.AspNetCore.Mvc.IntegrationTests.csproj @@ -6,6 +6,7 @@ + diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.IntegrationTests/ModelBindingTestHelper.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.IntegrationTests/ModelBindingTestHelper.cs index be137ba69d..ce4cc9155b 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.IntegrationTests/ModelBindingTestHelper.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.IntegrationTests/ModelBindingTestHelper.cs @@ -191,7 +191,8 @@ namespace Microsoft.AspNetCore.Mvc.IntegrationTests serviceCollection.AddSingleton(Options.Create(mvcOptions)); } - serviceCollection.AddMvc(); + serviceCollection.AddMvc() + .AddNewtonsoftJson(); serviceCollection .AddSingleton(NullLoggerFactory.Instance) .AddTransient, Logger>(); diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.IntegrationTests/ServicesModelBinderIntegrationTest.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.IntegrationTests/ServicesModelBinderIntegrationTest.cs index 1ea4cbf95b..291ed441b1 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.IntegrationTests/ServicesModelBinderIntegrationTest.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.IntegrationTests/ServicesModelBinderIntegrationTest.cs @@ -5,7 +5,7 @@ using System; using System.Collections.Generic; using System.Threading.Tasks; using Microsoft.AspNetCore.Mvc.Abstractions; -using Microsoft.AspNetCore.Mvc.Formatters; +using Microsoft.AspNetCore.Mvc.Infrastructure; using Microsoft.AspNetCore.Mvc.ModelBinding; using Xunit; @@ -28,7 +28,7 @@ namespace Microsoft.AspNetCore.Mvc.IntegrationTests }, // Using a service type already in defaults. - ParameterType = typeof(JsonOutputFormatter) + ParameterType = typeof(ITypeActivatorCache) }; var testContext = ModelBindingTestHelper.GetTestContext(); @@ -43,8 +43,8 @@ namespace Microsoft.AspNetCore.Mvc.IntegrationTests Assert.True(modelBindingResult.IsModelSet); // Model - var outputFormatter = Assert.IsType(modelBindingResult.Model); - Assert.NotNull(outputFormatter); + var provider = Assert.IsAssignableFrom(modelBindingResult.Model); + Assert.NotNull(provider); // ModelState Assert.True(modelState.IsValid); @@ -65,7 +65,7 @@ namespace Microsoft.AspNetCore.Mvc.IntegrationTests }, // Use a service type already in defaults. - ParameterType = typeof(JsonOutputFormatter), + ParameterType = typeof(ITypeActivatorCache), }; var testContext = ModelBindingTestHelper.GetTestContext(); @@ -79,8 +79,8 @@ namespace Microsoft.AspNetCore.Mvc.IntegrationTests Assert.True(modelBindingResult.IsModelSet); // Model - var outputFormatter = Assert.IsType(modelBindingResult.Model); - Assert.NotNull(outputFormatter); + var provider = Assert.IsAssignableFrom(modelBindingResult.Model); + Assert.NotNull(provider); // ModelState Assert.True(modelState.IsValid); @@ -101,7 +101,7 @@ namespace Microsoft.AspNetCore.Mvc.IntegrationTests }, // Use a service type already in defaults. - ParameterType = typeof(IEnumerable), + ParameterType = typeof(IEnumerable), }; var testContext = ModelBindingTestHelper.GetTestContext(); @@ -115,7 +115,7 @@ namespace Microsoft.AspNetCore.Mvc.IntegrationTests Assert.True(modelBindingResult.IsModelSet); // Model - var formatterArray = Assert.IsType(modelBindingResult.Model); + var formatterArray = Assert.IsType(modelBindingResult.Model); Assert.Single(formatterArray); // ModelState @@ -186,7 +186,7 @@ namespace Microsoft.AspNetCore.Mvc.IntegrationTests private class Person { - public JsonOutputFormatter Service { get; set; } + public ITypeActivatorCache Service { get; set; } } // [FromServices] cannot be associated with a type. But a [FromServices] or [ModelBinder] subclass or custom @@ -240,7 +240,7 @@ namespace Microsoft.AspNetCore.Mvc.IntegrationTests // Similar to a custom IBindingSourceMetadata implementation or [ModelBinder] subclass on a custom service. var metadataProvider = new TestModelMetadataProvider(); metadataProvider - .ForType() + .ForType() .BindingDetails(binding => binding.BindingSource = BindingSource.Services); var testContext = ModelBindingTestHelper.GetTestContext(metadataProvider: metadataProvider); @@ -250,7 +250,7 @@ namespace Microsoft.AspNetCore.Mvc.IntegrationTests { Name = "parameter-name", BindingInfo = bindingInfo, - ParameterType = typeof(JsonOutputFormatter), + ParameterType = typeof(ITypeActivatorCache), }; // Act @@ -258,7 +258,7 @@ namespace Microsoft.AspNetCore.Mvc.IntegrationTests // Assert Assert.True(modelBindingResult.IsModelSet); - Assert.IsType(modelBindingResult.Model); + Assert.IsAssignableFrom(modelBindingResult.Model); Assert.True(modelState.IsValid); Assert.Empty(modelState); diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.IntegrationTests/TestMvcOptions.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.IntegrationTests/TestMvcOptions.cs index 8c5904d884..1f4a8d7de2 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.IntegrationTests/TestMvcOptions.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.IntegrationTests/TestMvcOptions.cs @@ -36,11 +36,11 @@ namespace Microsoft.AspNetCore.Mvc.IntegrationTests dataAnnotationOptionsSetup.Configure(Value); var loggerFactory = new LoggerFactory(); - var jsonOptions = Options.Create(new MvcJsonOptions()); + var jsonOptions = Options.Create(new MvcNewtonsoftJsonOptions()); var charPool = ArrayPool.Shared; var objectPoolProvider = new DefaultObjectPoolProvider(); - var mvcJsonMvcOptionsSetup = new MvcJsonMvcOptionsSetup( + var mvcJsonMvcOptionsSetup = new NewtonosftJsonMvcOptionsSetup( loggerFactory, jsonOptions, charPool, diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/Filters/TempDataSerializerTest.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/BsonTempDataSerializerTest.cs similarity index 87% rename from src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/Filters/TempDataSerializerTest.cs rename to src/Mvc/test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/BsonTempDataSerializerTest.cs index 1e7320ef28..c2bc61d969 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/Filters/TempDataSerializerTest.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/BsonTempDataSerializerTest.cs @@ -5,9 +5,9 @@ using System; using System.Collections.Generic; using Xunit; -namespace Microsoft.AspNetCore.Mvc.ViewFeatures.Filters +namespace Microsoft.AspNetCore.Mvc.NewtonsoftJson { - public class TempDataSerializerTest + public class BsonTempDataSerializerTest { public static TheoryData InvalidTypes { @@ -29,14 +29,14 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures.Filters public void EnsureObjectCanBeSerialized_ThrowsException_OnInvalidType(object value, Type type) { // Arrange - var testProvider = new TempDataSerializer(); + var testProvider = new BsonTempDataSerializer(); // Act & Assert var exception = Assert.Throws(() => { testProvider.EnsureObjectCanBeSerialized(value); }); - Assert.Equal($"The '{typeof(TempDataSerializer).FullName}' cannot serialize " + + Assert.Equal($"The '{typeof(BsonTempDataSerializer).FullName}' cannot serialize " + $"an object of type '{type}'.", exception.Message); } @@ -60,14 +60,14 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures.Filters public void EnsureObjectCanBeSerialized_ThrowsException_OnInvalidDictionaryType(object value, Type type) { // Arrange - var testProvider = new TempDataSerializer(); + var testProvider = new BsonTempDataSerializer(); // Act & Assert var exception = Assert.Throws(() => { testProvider.EnsureObjectCanBeSerialized(value); }); - Assert.Equal($"The '{typeof(TempDataSerializer).FullName}' cannot serialize a dictionary " + + Assert.Equal($"The '{typeof(BsonTempDataSerializer).FullName}' cannot serialize a dictionary " + $"with a key of type '{type}'. The key must be of type 'System.String'.", exception.Message); } @@ -98,7 +98,7 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures.Filters public void EnsureObjectCanBeSerialized_DoesNotThrow_OnValidType(object value) { // Arrange - var testProvider = new TempDataSerializer(); + var testProvider = new BsonTempDataSerializer(); // Act & Assert (Does not throw) testProvider.EnsureObjectCanBeSerialized(value); @@ -108,7 +108,7 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures.Filters public void DeserializeTempData_ReturnsEmptyDictionary_DataIsEmpty() { // Arrange - var serializer = new TempDataSerializer(); + var serializer = new BsonTempDataSerializer(); // Act var tempDataDictionary = serializer.Deserialize(new byte[0]); @@ -123,7 +123,7 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures.Filters { // Arrange var key = "NullKey"; - var testProvider = new TempDataSerializer(); + var testProvider = new BsonTempDataSerializer(); var input = new Dictionary { { key, null } diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.Formatters.Json.Test/MvcJsonOptionsExtensionsTests.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/DependencyInjection/MvcNewtonsoftJsonOptionsExtensionsTest.cs similarity index 94% rename from src/Mvc/test/Microsoft.AspNetCore.Mvc.Formatters.Json.Test/MvcJsonOptionsExtensionsTests.cs rename to src/Mvc/test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/DependencyInjection/MvcNewtonsoftJsonOptionsExtensionsTest.cs index ab1c28fd3b..c7309084b9 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.Formatters.Json.Test/MvcJsonOptionsExtensionsTests.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/DependencyInjection/MvcNewtonsoftJsonOptionsExtensionsTest.cs @@ -4,21 +4,20 @@ using System; using System.Collections.Generic; using Microsoft.AspNetCore.Mvc; -using Microsoft.AspNetCore.Mvc.Formatters; -using Microsoft.AspNetCore.Mvc.Formatters.Json; +using Microsoft.AspNetCore.Mvc.NewtonsoftJson; using Newtonsoft.Json; using Newtonsoft.Json.Serialization; using Xunit; namespace Microsoft.Extensions.DependencyInjection { - public class MvcJsonOptionsExtensionsTests + public class MvcNewtonsoftJsonOptionsExtensionsTest { [Fact] public void UseCamelCasing_WillSet_CamelCasingStrategy_NameStrategy() { // Arrange - var options = new MvcJsonOptions(); + var options = new MvcNewtonsoftJsonOptions(); options.SerializerSettings.ContractResolver = new DefaultContractResolver() { NamingStrategy = new DefaultNamingStrategy() @@ -162,7 +161,7 @@ namespace Microsoft.Extensions.DependencyInjection public void UseMemberCasing_WillSet_DefaultNamingStrategy_AsNamingStrategy() { // Arrange - var options = new MvcJsonOptions(); + var options = new MvcNewtonsoftJsonOptions(); options.SerializerSettings.ContractResolver = new DefaultContractResolver { NamingStrategy = new CamelCaseNamingStrategy() @@ -217,7 +216,7 @@ namespace Microsoft.Extensions.DependencyInjection public void UseCamelCasing_WillThrow_IfContractResolver_IsNot_DefaultContractResolver() { // Arrange - var options = new MvcJsonOptions(); + var options = new MvcNewtonsoftJsonOptions(); options.SerializerSettings.ContractResolver = new FooContractResolver(); var expectedMessage = Resources.FormatInvalidContractResolverForJsonCasingConfiguration(nameof(FooContractResolver), nameof(DefaultContractResolver)); @@ -231,7 +230,7 @@ namespace Microsoft.Extensions.DependencyInjection public void UseMemberCasing_WillThrow_IfContractResolver_IsNot_DefaultContractResolver() { // Arrange - var options = new MvcJsonOptions(); + var options = new MvcNewtonsoftJsonOptions(); options.SerializerSettings.ContractResolver = new FooContractResolver(); var expectedMessage = Resources.FormatInvalidContractResolverForJsonCasingConfiguration(nameof(FooContractResolver), nameof(DefaultContractResolver)); @@ -243,14 +242,14 @@ namespace Microsoft.Extensions.DependencyInjection // NOTE: This method was created to make sure to create a different instance of contract resolver as by default // MvcJsonOptions uses a static shared instance of resolver which when changed causes other tests to fail. - private MvcJsonOptions CreateDefaultMvcJsonOptions() + private MvcNewtonsoftJsonOptions CreateDefaultMvcJsonOptions() { - var options = new MvcJsonOptions(); + var options = new MvcNewtonsoftJsonOptions(); options.SerializerSettings.ContractResolver = JsonSerializerSettingsProvider.CreateContractResolver(); return options; } - private static string SerializeToJson(MvcJsonOptions options, object value) + private static string SerializeToJson(MvcNewtonsoftJsonOptions options, object value) { return JsonConvert.SerializeObject( value: value, diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/DependencyInjection/NewtonsoftJsonMvcBuilderExtensionsTest.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/DependencyInjection/NewtonsoftJsonMvcBuilderExtensionsTest.cs new file mode 100644 index 0000000000..125520a009 --- /dev/null +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/DependencyInjection/NewtonsoftJsonMvcBuilderExtensionsTest.cs @@ -0,0 +1,30 @@ +// Copyright (c) .NET Foundation. All rights reserved. +// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information. + +using Microsoft.AspNetCore.Mvc; +using Microsoft.Extensions.Options; +using Newtonsoft.Json.Serialization; +using Xunit; + +namespace Microsoft.Extensions.DependencyInjection +{ + public class NewtonsoftJsonMvcBuilderExtensionsTest + { + [Fact] + public void AddNewtonsoftJson_ConfiguresOptions() + { + // Arrange + var services = new ServiceCollection(); + + // Act + services.AddMvc() + .AddNewtonsoftJson((options) => + { + options.SerializerSettings.ContractResolver = new CamelCasePropertyNamesContractResolver(); + }); + + // Assert + Assert.Single(services, d => d.ServiceType == typeof(IConfigureOptions)); + } + } +} diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/DependencyInjection/NewtonsoftJsonMvcCoreBuilderExtensionsTest.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/DependencyInjection/NewtonsoftJsonMvcCoreBuilderExtensionsTest.cs new file mode 100644 index 0000000000..84635d9ca6 --- /dev/null +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/DependencyInjection/NewtonsoftJsonMvcCoreBuilderExtensionsTest.cs @@ -0,0 +1,63 @@ +// Copyright (c) .NET Foundation. All rights reserved. +// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information. + +using Microsoft.AspNetCore.Mvc; +using Microsoft.AspNetCore.Mvc.NewtonsoftJson; +using Microsoft.AspNetCore.Mvc.Rendering; +using Microsoft.AspNetCore.Mvc.ViewFeatures.Infrastructure; +using Microsoft.Extensions.Options; +using Newtonsoft.Json.Serialization; +using Xunit; + +namespace Microsoft.Extensions.DependencyInjection +{ + public class NewtonsoftJsonMvcCoreBuilderExtensionsTest + { + [Fact] + public void AddNewtonsoftJson_ConfiguresOptions() + { + // Arrange + var services = new ServiceCollection(); + + // Act + services.AddMvcCore() + .AddNewtonsoftJson((options) => + { + options.SerializerSettings.ContractResolver = new CamelCasePropertyNamesContractResolver(); + }); + + // Assert + Assert.Single(services, d => d.ServiceType == typeof(IConfigureOptions)); + } + + [Fact] + public void AddServicesCore_ReplacesDefaultJsonHelper() + { + // Arrange + var services = new ServiceCollection() + .AddSingleton(); + + // Act + NewtonsoftJsonMvcCoreBuilderExtensions.AddServicesCore(services); + + // Assert + var jsonHelper = Assert.Single(services, d => d.ServiceType == typeof(IJsonHelper)); + Assert.Same(typeof(NewtonsoftJsonHelper), jsonHelper.ImplementationType); + } + + [Fact] + public void AddServicesCore_ReplacesDefaultTempDataSerializer() + { + // Arrange + var services = new ServiceCollection() + .AddSingleton(); + + // Act + NewtonsoftJsonMvcCoreBuilderExtensions.AddServicesCore(services); + + // Assert + var tempDataSerializer = Assert.Single(services, d => d.ServiceType == typeof(TempDataSerializer)); + Assert.Same(typeof(BsonTempDataSerializer), tempDataSerializer.ImplementationType); + } + } +} diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/JsonHelperTest.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/JsonHelperTest.cs similarity index 85% rename from src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/JsonHelperTest.cs rename to src/Mvc/test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/JsonHelperTest.cs index bcc3e4b538..44d45a62f9 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/JsonHelperTest.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/JsonHelperTest.cs @@ -8,7 +8,7 @@ using Newtonsoft.Json; using Newtonsoft.Json.Serialization; using Xunit; -namespace Microsoft.AspNetCore.Mvc.ViewFeatures +namespace Microsoft.AspNetCore.Mvc.NewtonsoftJson { public class JsonHelperTest { @@ -20,8 +20,8 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures { StringEscapeHandling = StringEscapeHandling.EscapeNonAscii, }; - var helper = new JsonHelper( - new JsonOutputFormatter(settings, ArrayPool.Shared), + var helper = new NewtonsoftJsonHelper( + new NewtonsoftJsonOutputFormatter(settings, ArrayPool.Shared), ArrayPool.Shared); var obj = new { @@ -48,8 +48,8 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures NamingStrategy = new CamelCaseNamingStrategy(), }, }; - var helper = new JsonHelper( - new JsonOutputFormatter(settings, ArrayPool.Shared), + var helper = new NewtonsoftJsonHelper( + new NewtonsoftJsonOutputFormatter(settings, ArrayPool.Shared), ArrayPool.Shared); var obj = new { diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.Test/JsonPatchExtensionsTest.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/JsonPatchExtensionsTest.cs similarity index 100% rename from src/Mvc/test/Microsoft.AspNetCore.Mvc.Test/JsonPatchExtensionsTest.cs rename to src/Mvc/test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/JsonPatchExtensionsTest.cs diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.Formatters.Json.Test/JsonPatchOperationsArrayProviderTests.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/JsonPatchOperationsArrayProviderTests.cs similarity index 97% rename from src/Mvc/test/Microsoft.AspNetCore.Mvc.Formatters.Json.Test/JsonPatchOperationsArrayProviderTests.cs rename to src/Mvc/test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/JsonPatchOperationsArrayProviderTests.cs index ed140a72e2..b829d0d3e8 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.Formatters.Json.Test/JsonPatchOperationsArrayProviderTests.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/JsonPatchOperationsArrayProviderTests.cs @@ -9,7 +9,7 @@ using Microsoft.AspNetCore.Mvc.ApiExplorer; using Microsoft.AspNetCore.Mvc.ModelBinding; using Xunit; -namespace Microsoft.AspNetCore.Mvc.Formatters.Json +namespace Microsoft.AspNetCore.Mvc.NewtonsoftJson { public class JsonPatchOperationsArrayProviderTests { diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.Formatters.Json.Test/JsonResultExecutorTest.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/JsonResultExecutorTest.cs similarity index 99% rename from src/Mvc/test/Microsoft.AspNetCore.Mvc.Formatters.Json.Test/JsonResultExecutorTest.cs rename to src/Mvc/test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/JsonResultExecutorTest.cs index 1db9b26cb6..628916dd25 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.Formatters.Json.Test/JsonResultExecutorTest.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/JsonResultExecutorTest.cs @@ -19,7 +19,7 @@ using Moq; using Newtonsoft.Json; using Xunit; -namespace Microsoft.AspNetCore.Mvc.Formatters +namespace Microsoft.AspNetCore.Mvc.NewtonsoftJson { public class JsonResultExecutorTest { @@ -284,7 +284,7 @@ namespace Microsoft.AspNetCore.Mvc.Formatters return new JsonResultExecutor( new TestHttpResponseStreamWriterFactory(), logger ?? NullLogger.Instance, - Options.Create(new MvcJsonOptions()), + Options.Create(new MvcNewtonsoftJsonOptions()), ArrayPool.Shared); } diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.Formatters.Json.Test/JsonResultTest.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/JsonResultTest.cs similarity index 90% rename from src/Mvc/test/Microsoft.AspNetCore.Mvc.Formatters.Json.Test/JsonResultTest.cs rename to src/Mvc/test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/JsonResultTest.cs index 866010f51e..dca9a52164 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.Formatters.Json.Test/JsonResultTest.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/JsonResultTest.cs @@ -7,7 +7,7 @@ using System.Text; using System.Threading.Tasks; using Microsoft.AspNetCore.Http; using Microsoft.AspNetCore.Mvc.Abstractions; -using Microsoft.AspNetCore.Mvc.Formatters; +using Microsoft.AspNetCore.Mvc.Infrastructure; using Microsoft.AspNetCore.Routing; using Microsoft.Extensions.DependencyInjection; using Microsoft.Extensions.Logging.Abstractions; @@ -15,7 +15,7 @@ using Microsoft.Extensions.Options; using Newtonsoft.Json; using Xunit; -namespace Microsoft.AspNetCore.Mvc +namespace Microsoft.AspNetCore.Mvc.NewtonsoftJson { public class JsonResultTest { @@ -47,11 +47,11 @@ namespace Microsoft.AspNetCore.Mvc var executor = new JsonResultExecutor( new TestHttpResponseStreamWriterFactory(), NullLogger.Instance, - Options.Create(new MvcJsonOptions()), + Options.Create(new MvcNewtonsoftJsonOptions()), ArrayPool.Shared); var services = new ServiceCollection(); - services.AddSingleton(executor); + services.AddSingleton>(executor); httpContext.RequestServices = services.BuildServiceProvider(); return httpContext; diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.Formatters.Json.Test/Microsoft.AspNetCore.Mvc.Formatters.Json.Test.csproj b/src/Mvc/test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test.csproj similarity index 71% rename from src/Mvc/test/Microsoft.AspNetCore.Mvc.Formatters.Json.Test/Microsoft.AspNetCore.Mvc.Formatters.Json.Test.csproj rename to src/Mvc/test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test.csproj index a3028a0d81..162629c31e 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.Formatters.Json.Test/Microsoft.AspNetCore.Mvc.Formatters.Json.Test.csproj +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test.csproj @@ -5,7 +5,8 @@ - + + diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.Formatters.Json.Test/JsonInputFormatterTest.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/NewtonsoftJsonInputFormatterTest.cs similarity index 96% rename from src/Mvc/test/Microsoft.AspNetCore.Mvc.Formatters.Json.Test/JsonInputFormatterTest.cs rename to src/Mvc/test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/NewtonsoftJsonInputFormatterTest.cs index 1829fd14f6..dce1e939ab 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.Formatters.Json.Test/JsonInputFormatterTest.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/NewtonsoftJsonInputFormatterTest.cs @@ -21,7 +21,7 @@ using Xunit; namespace Microsoft.AspNetCore.Mvc.Formatters { - public class JsonInputFormatterTest + public class NewtonsoftJsonInputFormatterTest { private static readonly ObjectPoolProvider _objectPoolProvider = new DefaultObjectPoolProvider(); private static readonly JsonSerializerSettings _serializerSettings = new JsonSerializerSettings(); @@ -31,7 +31,7 @@ namespace Microsoft.AspNetCore.Mvc.Formatters { // Arrange #pragma warning disable CS0618 - var formatter = new JsonInputFormatter( + var formatter = new NewtonsoftJsonInputFormatter( GetLogger(), _serializerSettings, ArrayPool.Shared, @@ -74,13 +74,13 @@ namespace Microsoft.AspNetCore.Mvc.Formatters public async Task Version_2_1_Constructor_BuffersRequestBody_UsingDefaultOptions() { // Arrange - var formatter = new JsonInputFormatter( + var formatter = new NewtonsoftJsonInputFormatter( GetLogger(), _serializerSettings, ArrayPool.Shared, _objectPoolProvider, new MvcOptions(), - new MvcJsonOptions()); + new MvcNewtonsoftJsonOptions()); var content = "{name: 'Person Name', Age: '30'}"; var contentBytes = Encoding.UTF8.GetBytes(content); @@ -119,7 +119,7 @@ namespace Microsoft.AspNetCore.Mvc.Formatters { // Arrange #pragma warning disable CS0618 - var formatter = new JsonInputFormatter( + var formatter = new NewtonsoftJsonInputFormatter( GetLogger(), _serializerSettings, ArrayPool.Shared, @@ -162,13 +162,13 @@ namespace Microsoft.AspNetCore.Mvc.Formatters { SuppressInputFormatterBuffering = true, }; - var formatter = new JsonInputFormatter( + var formatter = new NewtonsoftJsonInputFormatter( GetLogger(), _serializerSettings, ArrayPool.Shared, _objectPoolProvider, mvcOptions, - new MvcJsonOptions()); + new MvcNewtonsoftJsonOptions()); var content = "{name: 'Person Name', Age: '30'}"; var contentBytes = Encoding.UTF8.GetBytes(content); @@ -205,13 +205,13 @@ namespace Microsoft.AspNetCore.Mvc.Formatters { SuppressInputFormatterBuffering = false, }; - var formatter = new JsonInputFormatter( + var formatter = new NewtonsoftJsonInputFormatter( GetLogger(), _serializerSettings, ArrayPool.Shared, _objectPoolProvider, mvcOptions, - new MvcJsonOptions()); + new MvcNewtonsoftJsonOptions()); var content = "{name: 'Person Name', Age: '30'}"; var contentBytes = Encoding.UTF8.GetBytes(content); @@ -570,7 +570,7 @@ namespace Microsoft.AspNetCore.Mvc.Formatters [InlineData("{", "", "Unexpected end when reading JSON. Path '', line 1, position 1.")] [InlineData("{\"a\":{\"b\"}}", "a", "Invalid character after parsing property name. Expected ':' but got: }. Path 'a', line 1, position 9.")] [InlineData("{\"age\":\"x\"}", "age", "Could not convert string to decimal: x. Path 'age', line 1, position 10.")] - [InlineData("{\"login\":1}", "login", "Error converting value 1 to type 'Microsoft.AspNetCore.Mvc.Formatters.JsonInputFormatterTest+UserLogin'. Path 'login', line 1, position 10.")] + [InlineData("{\"login\":1}", "login", "Error converting value 1 to type 'Microsoft.AspNetCore.Mvc.Formatters.NewtonsoftJsonInputFormatterTest+UserLogin'. Path 'login', line 1, position 10.")] [InlineData("{\"login\":{\"username\":\"somevalue\"}}", "login.Password", "Required property 'Password' not found in JSON. Path 'login', line 1, position 33.")] public async Task ReadAsync_WithAllowInputFormatterExceptionMessages_RegistersJsonInputExceptionsAsInputFormatterException( string content, @@ -624,13 +624,13 @@ namespace Microsoft.AspNetCore.Mvc.Formatters public async Task ReadAsync_AllowInputFormatterExceptionMessages_DoesNotWrapJsonInputExceptions() { // Arrange - var formatter = new JsonInputFormatter( + var formatter = new NewtonsoftJsonInputFormatter( GetLogger(), _serializerSettings, ArrayPool.Shared, _objectPoolProvider, new MvcOptions(), - new MvcJsonOptions() + new MvcNewtonsoftJsonOptions() { AllowInputFormatterExceptionMessages = true, }); @@ -653,10 +653,10 @@ namespace Microsoft.AspNetCore.Mvc.Formatters Assert.NotEmpty(modelError.ErrorMessage); } - private class TestableJsonInputFormatter : JsonInputFormatter + private class TestableJsonInputFormatter : NewtonsoftJsonInputFormatter { public TestableJsonInputFormatter(JsonSerializerSettings settings) - : base(GetLogger(), settings, ArrayPool.Shared, _objectPoolProvider, new MvcOptions(), new MvcJsonOptions()) + : base(GetLogger(), settings, ArrayPool.Shared, _objectPoolProvider, new MvcOptions(), new MvcNewtonsoftJsonOptions()) { } @@ -670,15 +670,15 @@ namespace Microsoft.AspNetCore.Mvc.Formatters return NullLogger.Instance; } - private JsonInputFormatter CreateFormatter(JsonSerializerSettings serializerSettings = null, bool allowInputFormatterExceptionMessages = false) + private NewtonsoftJsonInputFormatter CreateFormatter(JsonSerializerSettings serializerSettings = null, bool allowInputFormatterExceptionMessages = false) { - return new JsonInputFormatter( + return new NewtonsoftJsonInputFormatter( GetLogger(), serializerSettings ?? _serializerSettings, ArrayPool.Shared, _objectPoolProvider, new MvcOptions(), - new MvcJsonOptions() + new MvcNewtonsoftJsonOptions() { AllowInputFormatterExceptionMessages = allowInputFormatterExceptionMessages, }); diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.Formatters.Json.Test/JsonOutputFormatterTests.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/NewtonsoftJsonOutputFormatterTest.cs similarity index 95% rename from src/Mvc/test/Microsoft.AspNetCore.Mvc.Formatters.Json.Test/JsonOutputFormatterTests.cs rename to src/Mvc/test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/NewtonsoftJsonOutputFormatterTest.cs index 15e735a328..26306876d4 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.Formatters.Json.Test/JsonOutputFormatterTests.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/NewtonsoftJsonOutputFormatterTest.cs @@ -10,8 +10,9 @@ using System.Text; using System.Threading.Tasks; using Microsoft.AspNetCore.Http; using Microsoft.AspNetCore.Mvc.Abstractions; +using Microsoft.AspNetCore.Mvc.Formatters; +using Microsoft.AspNetCore.Mvc.NewtonsoftJson; using Microsoft.AspNetCore.Routing; -using Microsoft.AspNetCore.Testing; using Microsoft.Extensions.Logging; using Microsoft.Extensions.Logging.Abstractions; using Microsoft.Extensions.Primitives; @@ -24,7 +25,7 @@ using Xunit; namespace Microsoft.AspNetCore.Mvc.Formatters { - public class JsonOutputFormatterTests + public class NewtonsoftJsonOutputFormatterTest { [Fact] public void Creates_SerializerSettings_ByDefault() @@ -61,7 +62,7 @@ namespace Microsoft.AspNetCore.Mvc.Formatters Formatting = Formatting.Indented, }; var expectedOutput = JsonConvert.SerializeObject(person, settings); - var jsonFormatter = new JsonOutputFormatter(settings, ArrayPool.Shared); + var jsonFormatter = new NewtonsoftJsonOutputFormatter(settings, ArrayPool.Shared); // Act await jsonFormatter.WriteResponseBodyAsync(outputFormatterContext, Encoding.UTF8); @@ -279,7 +280,7 @@ namespace Microsoft.AspNetCore.Mvc.Formatters { // Arrange var beforeMessage = "Hello World"; - var formatter = new JsonOutputFormatter(new JsonSerializerSettings(), ArrayPool.Shared); + var formatter = new NewtonsoftJsonOutputFormatter(new JsonSerializerSettings(), ArrayPool.Shared); var before = new JValue(beforeMessage); var memStream = new MemoryStream(); var outputFormatterContext = GetOutputFormatterContext( @@ -323,7 +324,7 @@ namespace Microsoft.AspNetCore.Mvc.Formatters bool isDefaultEncoding) { // Arrange - var formatter = new JsonOutputFormatter(new JsonSerializerSettings(), ArrayPool.Shared); + var formatter = new NewtonsoftJsonOutputFormatter(new JsonSerializerSettings(), ArrayPool.Shared); var formattedContent = "\"" + content + "\""; var mediaType = MediaTypeHeaderValue.Parse(string.Format("application/json; charset={0}", encodingAsString)); var encoding = CreateOrGetSupportedEncoding(formatter, encodingAsString, isDefaultEncoding); @@ -359,7 +360,7 @@ namespace Microsoft.AspNetCore.Mvc.Formatters new ModelWithSerializationError(), typeof(ModelWithSerializationError)); var serializerSettings = JsonSerializerSettingsProvider.CreateSerializerSettings(); - var jsonFormatter = new JsonOutputFormatter(serializerSettings, ArrayPool.Shared); + var jsonFormatter = new NewtonsoftJsonOutputFormatter(serializerSettings, ArrayPool.Shared); // Act try @@ -402,8 +403,8 @@ namespace Microsoft.AspNetCore.Mvc.Formatters string expectedResult) { // Arrange - var formatter = new JsonOutputFormatter(new JsonSerializerSettings(), ArrayPool.Shared); - + var formatter = new NewtonsoftJsonOutputFormatter(new JsonSerializerSettings(), ArrayPool.Shared); + var body = new MemoryStream(); var actionContext = GetActionContext(MediaTypeHeaderValue.Parse(mediaType), body); var outputFormatterContext = new OutputFormatterWriteContext( @@ -426,7 +427,7 @@ namespace Microsoft.AspNetCore.Mvc.Formatters } private static Encoding CreateOrGetSupportedEncoding( - JsonOutputFormatter formatter, + NewtonsoftJsonOutputFormatter formatter, string encodingAsString, bool isDefaultEncoding) { @@ -486,7 +487,7 @@ namespace Microsoft.AspNetCore.Mvc.Formatters return new ActionContext(httpContext.Object, new RouteData(), new ActionDescriptor()); } - private class TestableJsonOutputFormatter : JsonOutputFormatter + private class TestableJsonOutputFormatter : NewtonsoftJsonOutputFormatter { public TestableJsonOutputFormatter(JsonSerializerSettings serializerSettings) : base(serializerSettings, ArrayPool.Shared) diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.Formatters.Json.Test/JsonPatchInputFormatterTest.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/NewtonsoftJsonPatchInputFormatterTest.cs similarity index 94% rename from src/Mvc/test/Microsoft.AspNetCore.Mvc.Formatters.Json.Test/JsonPatchInputFormatterTest.cs rename to src/Mvc/test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/NewtonsoftJsonPatchInputFormatterTest.cs index 16961e2866..0503d093a8 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.Formatters.Json.Test/JsonPatchInputFormatterTest.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.NewtonsoftJson.Test/NewtonsoftJsonPatchInputFormatterTest.cs @@ -19,7 +19,7 @@ using Xunit; namespace Microsoft.AspNetCore.Mvc.Formatters { - public class JsonPatchInputFormatterTest + public class NewtonsoftJsonPatchInputFormatterTest { private static readonly ObjectPoolProvider _objectPoolProvider = new DefaultObjectPoolProvider(); private static readonly JsonSerializerSettings _serializerSettings = new JsonSerializerSettings(); @@ -29,8 +29,8 @@ namespace Microsoft.AspNetCore.Mvc.Formatters { // Arrange #pragma warning disable CS0618 - var formatter = new JsonPatchInputFormatter( - GetLogger(), + var formatter = new NewtonsoftJsonPatchInputFormatter( + GetLogger(), _serializerSettings, ArrayPool.Shared, _objectPoolProvider); @@ -73,13 +73,13 @@ namespace Microsoft.AspNetCore.Mvc.Formatters public async Task Version_2_1_Constructor_BuffersRequestBody_ByDefault() { // Arrange - var formatter = new JsonPatchInputFormatter( + var formatter = new NewtonsoftJsonPatchInputFormatter( GetLogger(), _serializerSettings, ArrayPool.Shared, _objectPoolProvider, new MvcOptions(), - new MvcJsonOptions()); + new MvcNewtonsoftJsonOptions()); var content = "[{\"op\":\"add\",\"path\":\"Customer/Name\",\"value\":\"John\"}]"; var contentBytes = Encoding.UTF8.GetBytes(content); @@ -119,11 +119,11 @@ namespace Microsoft.AspNetCore.Mvc.Formatters { // Arrange #pragma warning disable CS0618 - var formatter = new JsonPatchInputFormatter( - GetLogger(), - _serializerSettings, - ArrayPool.Shared, - _objectPoolProvider, + var formatter = new NewtonsoftJsonPatchInputFormatter( + GetLogger(), + _serializerSettings, + ArrayPool.Shared, + _objectPoolProvider, suppressInputFormatterBuffering: true); #pragma warning restore CS0618 @@ -164,17 +164,17 @@ namespace Microsoft.AspNetCore.Mvc.Formatters { SuppressInputFormatterBuffering = false, }; - var formatter = new JsonPatchInputFormatter( + var formatter = new NewtonsoftJsonPatchInputFormatter( GetLogger(), _serializerSettings, ArrayPool.Shared, _objectPoolProvider, mvcOptions, - new MvcJsonOptions()); + new MvcNewtonsoftJsonOptions()); var content = "[{\"op\":\"add\",\"path\":\"Customer/Name\",\"value\":\"John\"}]"; var contentBytes = Encoding.UTF8.GetBytes(content); - + var httpContext = new DefaultHttpContext(); httpContext.Features.Set(new TestResponseFeature()); httpContext.Request.Body = new NonSeekableReadStream(contentBytes); @@ -327,15 +327,15 @@ namespace Microsoft.AspNetCore.Mvc.Formatters return NullLogger.Instance; } - private JsonPatchInputFormatter CreateFormatter(bool allowInputFormatterExceptionMessages = false) + private NewtonsoftJsonPatchInputFormatter CreateFormatter(bool allowInputFormatterExceptionMessages = false) { - return new JsonPatchInputFormatter( + return new NewtonsoftJsonPatchInputFormatter( NullLogger.Instance, _serializerSettings, ArrayPool.Shared, _objectPoolProvider, new MvcOptions(), - new MvcJsonOptions() + new MvcNewtonsoftJsonOptions() { AllowInputFormatterExceptionMessages = allowInputFormatterExceptionMessages, }); diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.Razor.Test/RazorPageCreateTagHelperTest.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.Razor.Test/RazorPageCreateTagHelperTest.cs index aeeae9732e..9b0e4d7baa 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.Razor.Test/RazorPageCreateTagHelperTest.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.Razor.Test/RazorPageCreateTagHelperTest.cs @@ -76,9 +76,7 @@ namespace Microsoft.AspNetCore.Mvc.Razor var activator = new RazorPageActivator( modelMetadataProvider, new UrlHelperFactory(), - new JsonHelper( - new JsonOutputFormatter(new JsonSerializerSettings(), ArrayPool.Shared), - ArrayPool.Shared), + Mock.Of(), new DiagnosticListener("Microsoft.AspNetCore"), new HtmlTestEncoder(), modelExpressionProvider); diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.RazorPages.Test/ApplicationModels/TempDataFilterPageApplicationModelProviderTest.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.RazorPages.Test/ApplicationModels/TempDataFilterPageApplicationModelProviderTest.cs index 17b56a8cd6..42db7a3191 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.RazorPages.Test/ApplicationModels/TempDataFilterPageApplicationModelProviderTest.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.RazorPages.Test/ApplicationModels/TempDataFilterPageApplicationModelProviderTest.cs @@ -6,7 +6,8 @@ using System.Reflection; using System.Threading.Tasks; using Microsoft.AspNetCore.Mvc.Filters; using Microsoft.AspNetCore.Mvc.RazorPages; -using Microsoft.Extensions.Options; +using Microsoft.AspNetCore.Mvc.ViewFeatures.Infrastructure; +using Moq; using Xunit; namespace Microsoft.AspNetCore.Mvc.ApplicationModels @@ -18,8 +19,7 @@ namespace Microsoft.AspNetCore.Mvc.ApplicationModels { // Arrange var type = typeof(TestPageModel_NoTempDataProperties); - var options = Options.Create(new MvcViewOptions()); - var provider = new TempDataFilterPageApplicationModelProvider(options); + var provider = CreateProvider(); var context = CreateProviderContext(type); // Act @@ -36,8 +36,7 @@ namespace Microsoft.AspNetCore.Mvc.ApplicationModels var type = typeof(TestPageModel_PrivateSet); var expected = $"The '{type.FullName}.Test' property with TempDataAttribute is invalid. A property using TempDataAttribute must have a public getter and setter."; - var options = Options.Create(new MvcViewOptions()); - var provider = new TempDataFilterPageApplicationModelProvider(options); + var provider = CreateProvider(); var context = CreateProviderContext(type); // Act & Assert @@ -50,8 +49,7 @@ namespace Microsoft.AspNetCore.Mvc.ApplicationModels { // Arrange var type = typeof(TestPageModel_OneTempDataProperty); - var options = Options.Create(new MvcViewOptions()); - var provider = new TempDataFilterPageApplicationModelProvider(options); + var provider = CreateProvider(); var context = CreateProviderContext(type); // Act @@ -67,8 +65,7 @@ namespace Microsoft.AspNetCore.Mvc.ApplicationModels { // Arrange var type = typeof(TestPageModel_OneTempDataProperty); - var options = Options.Create(new MvcViewOptions()); - var provider = new TempDataFilterPageApplicationModelProvider(options); + var provider = CreateProvider(); var context = CreateProviderContext(type); // Act @@ -90,8 +87,7 @@ namespace Microsoft.AspNetCore.Mvc.ApplicationModels { // Arrange var type = typeof(TestPageModel_OneTempDataProperty); - var options = Options.Create(new MvcViewOptions()); - var provider = new TempDataFilterPageApplicationModelProvider(options); + var provider = CreateProvider(); var context = CreateProviderContext(type); // Act @@ -127,6 +123,12 @@ namespace Microsoft.AspNetCore.Mvc.ApplicationModels }; } + private static TempDataFilterPageApplicationModelProvider CreateProvider() + { + var tempDataSerializer = Mock.Of(s => s.CanSerializeType(It.IsAny()) == true); + return new TempDataFilterPageApplicationModelProvider(tempDataSerializer); + } + private class TestPage : Page { public object Model => null; diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.Test/ApplicationParts/ApplicationAssembliesProviderTest.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.Test/ApplicationParts/ApplicationAssembliesProviderTest.cs index 6bef5ad395..03d4ef3c73 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.Test/ApplicationParts/ApplicationAssembliesProviderTest.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.Test/ApplicationParts/ApplicationAssembliesProviderTest.cs @@ -31,6 +31,7 @@ namespace Microsoft.AspNetCore.Mvc.ApplicationParts { // The following assemblies are not reachable from Microsoft.AspNetCore.Mvc "Microsoft.AspNetCore.App", + "Microsoft.AspNetCore.Mvc.NewtonsoftJson", "Microsoft.AspNetCore.Mvc.Formatters.Xml", }; diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.Test/MvcOptionsSetupTest.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.Test/MvcOptionsSetupTest.cs index fa397bcd4b..c4a1876e44 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.Test/MvcOptionsSetupTest.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.Test/MvcOptionsSetupTest.cs @@ -11,7 +11,6 @@ using System.Xml; using System.Xml.Linq; using Microsoft.AspNetCore.Hosting; using Microsoft.AspNetCore.Http; -using Microsoft.AspNetCore.JsonPatch; using Microsoft.AspNetCore.Mvc.ApplicationParts; using Microsoft.AspNetCore.Mvc.DataAnnotations; using Microsoft.AspNetCore.Mvc.Formatters; @@ -96,8 +95,7 @@ namespace Microsoft.AspNetCore.Mvc Assert.Collection(options.OutputFormatters, formatter => Assert.IsType(formatter), formatter => Assert.IsType(formatter), - formatter => Assert.IsType(formatter), - formatter => Assert.IsType(formatter)); + formatter => Assert.IsType(formatter)); } [Fact] @@ -107,9 +105,7 @@ namespace Microsoft.AspNetCore.Mvc var options = GetOptions(); // Assert - Assert.Collection(options.InputFormatters, - formatter => Assert.IsType(formatter), - formatter => Assert.IsType(formatter)); + Assert.Empty(options.InputFormatters); } [Fact] @@ -229,16 +225,6 @@ namespace Microsoft.AspNetCore.Mvc Assert.Equal(typeof(Stream), excludeFilter.Type); }, provider => Assert.IsType(provider), - provider => - { - var excludeFilter = Assert.IsType(provider); - Assert.Equal(typeof(IJsonPatchDocument), excludeFilter.Type); - }, - provider => - { - var excludeFilter = Assert.IsType(provider); - Assert.Equal(typeof(JToken), excludeFilter.Type); - }, provider => Assert.IsType(provider), provider => { diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.Test/MvcServiceCollectionExtensionsTest.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.Test/MvcServiceCollectionExtensionsTest.cs index e9fbd9d7b9..259db589b9 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.Test/MvcServiceCollectionExtensionsTest.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.Test/MvcServiceCollectionExtensionsTest.cs @@ -15,7 +15,6 @@ using Microsoft.AspNetCore.Mvc.ApplicationParts; using Microsoft.AspNetCore.Mvc.Controllers; using Microsoft.AspNetCore.Mvc.Cors; using Microsoft.AspNetCore.Mvc.Filters; -using Microsoft.AspNetCore.Mvc.Formatters.Json; using Microsoft.AspNetCore.Mvc.Infrastructure; using Microsoft.AspNetCore.Mvc.Razor; using Microsoft.AspNetCore.Mvc.Razor.Compilation; @@ -232,23 +231,6 @@ namespace Microsoft.AspNetCore.Mvc Assert.Same(manager, descriptor.ImplementationInstance); } - [Fact] - public void AddMvcCore_AddsMvcJsonOption() - { - // Arrange - var services = new ServiceCollection(); - - // Act - services.AddMvcCore() - .AddJsonOptions((options) => - { - options.SerializerSettings.ContractResolver = new CamelCasePropertyNamesContractResolver(); - }); - - // Assert - Assert.Single(services, d => d.ServiceType == typeof(IConfigureOptions)); - } - [Fact] public void AddMvc_NoScopedServiceIsReferredToByASingleton() { @@ -337,7 +319,6 @@ namespace Microsoft.AspNetCore.Mvc { typeof(MvcCoreMvcOptionsSetup), typeof(MvcDataAnnotationsMvcOptionsSetup), - typeof(MvcJsonMvcOptionsSetup), typeof(TempDataMvcOptionsSetup), } }, @@ -435,7 +416,6 @@ namespace Microsoft.AspNetCore.Mvc new Type[] { typeof(DefaultApiDescriptionProvider), - typeof(JsonPatchOperationsArrayProvider), } }, { diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ControllerTest.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ControllerTest.cs index c7c347e867..3f4a10d0a6 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ControllerTest.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ControllerTest.cs @@ -16,7 +16,6 @@ using Microsoft.AspNetCore.Mvc.ViewFeatures; using Microsoft.AspNetCore.Routing; using Microsoft.Extensions.Options; using Moq; -using Newtonsoft.Json; using Xunit; namespace Microsoft.AspNetCore.Mvc.Test @@ -332,7 +331,7 @@ namespace Microsoft.AspNetCore.Mvc.Test // Arrange var controller = new TestableController(); var data = new object(); - var serializerSettings = new JsonSerializerSettings(); + var serializerSettings = new object(); // Act var actualJsonResult = controller.Json(data, serializerSettings); @@ -340,6 +339,7 @@ namespace Microsoft.AspNetCore.Mvc.Test // Assert Assert.IsType(actualJsonResult); Assert.Same(data, actualJsonResult.Value); + Assert.Same(serializerSettings, actualJsonResult.SerializerSettings); } // These tests share code with the ActionFilterAttribute tests because the various filter diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ControllerUnitTestabilityTests.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ControllerUnitTestabilityTests.cs index 34e560c7c2..63615039b1 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ControllerUnitTestabilityTests.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ControllerUnitTestabilityTests.cs @@ -10,7 +10,6 @@ using Microsoft.AspNetCore.Mvc.Controllers; using Microsoft.AspNetCore.Mvc.Formatters; using Microsoft.AspNetCore.Routing; using Moq; -using Newtonsoft.Json; using Xunit; namespace Microsoft.AspNetCore.Mvc @@ -225,7 +224,7 @@ namespace Microsoft.AspNetCore.Mvc // Arrange var controller = new TestabilityController(); var model = new MyModel() { Property1 = "Property_1" }; - var serializerSettings = new JsonSerializerSettings(); + var serializerSettings = new object(); // Act var result = controller.JsonWithSerializerSettings_Action(model, serializerSettings); @@ -745,7 +744,7 @@ namespace Microsoft.AspNetCore.Mvc return Json(data); } - public IActionResult JsonWithSerializerSettings_Action(object data, JsonSerializerSettings serializerSettings) + public IActionResult JsonWithSerializerSettings_Action(object data, object serializerSettings) { return Json(data, serializerSettings); } diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/CookieTempDataProviderTest.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/CookieTempDataProviderTest.cs index b42ad325db..302082bf5e 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/CookieTempDataProviderTest.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/CookieTempDataProviderTest.cs @@ -4,10 +4,11 @@ using System; using System.Collections; using System.Collections.Generic; +using System.Text; using Microsoft.AspNetCore.DataProtection; using Microsoft.AspNetCore.Http; using Microsoft.AspNetCore.Http.Internal; -using Microsoft.AspNetCore.Mvc.ViewFeatures.Filters; +using Microsoft.AspNetCore.Mvc.ViewFeatures.Infrastructure; using Microsoft.AspNetCore.WebUtilities; using Microsoft.Extensions.Logging.Abstractions; using Microsoft.Extensions.Options; @@ -19,17 +20,19 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures { public class CookieTempDataProviderTest { + private static readonly byte[] Bytes = Encoding.UTF8.GetBytes("test value"); + private static readonly IDictionary Dictionary = new Dictionary + { + { "key", "value" }, + }; + [Fact] public void SaveTempData_UsesCookieName_FromOptions() { // Arrange var expectedCookieName = "TestCookieName"; - var values = new Dictionary(); - values.Add("int", 10); - var tempDataProviderStore = new TempDataSerializer(); - var expectedDataToProtect = tempDataProviderStore.Serialize(values); - var expectedDataInCookie = WebEncoders.Base64UrlEncode(expectedDataToProtect); + var expectedDataInCookie = WebEncoders.Base64UrlEncode(Bytes); var tempDataProvider = GetProvider(dataProtector: null, options: new CookieTempDataProviderOptions() { Cookie = { Name = expectedCookieName } @@ -45,7 +48,7 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures .Returns(responseCookies); // Act - tempDataProvider.SaveTempData(httpContext.Object, values); + tempDataProvider.SaveTempData(httpContext.Object, Dictionary); // Assert Assert.Contains(responseCookies, (cookie) => cookie.Key == expectedCookieName); @@ -79,10 +82,7 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures var tempDataProvider = GetProvider(dataProtector.Object); - var inputData = new Dictionary(); - inputData.Add("int", 10); - var tempDataProviderSerializer = new TempDataSerializer(); - var expectedDataToUnprotect = tempDataProviderSerializer.Serialize(inputData); + var expectedDataToUnprotect = Bytes; var base64AndUrlEncodedDataInCookie = WebEncoders.Base64UrlEncode(expectedDataToUnprotect); var context = new DefaultHttpContext(); @@ -106,10 +106,7 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures public void LoadTempData_Base64UrlDecodesAnd_UnprotectsData_FromCookie() { // Arrange - var expectedValues = new Dictionary(); - expectedValues.Add("int", 10); - var tempDataProviderSerializer = new TempDataSerializer(); - var expectedDataToUnprotect = tempDataProviderSerializer.Serialize(expectedValues); + var expectedDataToUnprotect = Bytes; var base64AndUrlEncodedDataInCookie = WebEncoders.Base64UrlEncode(expectedDataToUnprotect); var dataProtector = new PassThroughDataProtector(); var tempDataProvider = GetProvider(dataProtector); @@ -127,7 +124,7 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures // Assert Assert.Equal(expectedDataToUnprotect, dataProtector.DataToUnprotect); - Assert.Equal(expectedValues, actualValues); + Assert.Same(Dictionary, actualValues); } [Fact] @@ -136,8 +133,7 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures // Arrange var values = new Dictionary(); values.Add("int", 10); - var tempDataProviderStore = new TempDataSerializer(); - var expectedDataToProtect = tempDataProviderStore.Serialize(values); + var expectedDataToProtect = Bytes; var expectedDataInCookie = WebEncoders.Base64UrlEncode(expectedDataToProtect); var dataProtector = new PassThroughDataProtector(); var tempDataProvider = GetProvider(dataProtector); @@ -151,7 +147,7 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures .Returns(responseCookies); // Act - tempDataProvider.SaveTempData(httpContext.Object, values); + tempDataProvider.SaveTempData(httpContext.Object, Dictionary); // Assert Assert.Equal(1, responseCookies.Count); @@ -174,10 +170,7 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures bool expectedSecureFlag) { // Arrange - var values = new Dictionary(); - values.Add("int", 10); - var tempDataProviderStore = new TempDataSerializer(); - var expectedDataToProtect = tempDataProviderStore.Serialize(values); + var expectedDataToProtect = Bytes; var expectedDataInCookie = WebEncoders.Base64UrlEncode(expectedDataToProtect); var dataProtector = new PassThroughDataProtector(); var options = new CookieTempDataProviderOptions(); @@ -196,7 +189,7 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures .Returns(responseCookies); // Act - tempDataProvider.SaveTempData(httpContext.Object, values); + tempDataProvider.SaveTempData(httpContext.Object, Dictionary); // Assert Assert.Equal(1, responseCookies.Count); @@ -221,10 +214,7 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures string expectedCookiePath) { // Arrange - var values = new Dictionary(); - values.Add("int", 10); - var tempDataProviderStore = new TempDataSerializer(); - var expectedDataToProtect = tempDataProviderStore.Serialize(values); + var expectedDataToProtect = Bytes; var expectedDataInCookie = WebEncoders.Base64UrlEncode(expectedDataToProtect); var dataProtector = new PassThroughDataProtector(); var tempDataProvider = GetProvider(dataProtector); @@ -241,7 +231,7 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures .Returns(responseCookies); // Act - tempDataProvider.SaveTempData(httpContext.Object, values); + tempDataProvider.SaveTempData(httpContext.Object, Dictionary); // Assert Assert.Equal(1, responseCookies.Count); @@ -271,10 +261,7 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures string expectedDomain) { // Arrange - var values = new Dictionary(); - values.Add("int", 10); - var tempDataProviderStore = new TempDataSerializer(); - var expectedDataToProtect = tempDataProviderStore.Serialize(values); + var expectedDataToProtect = Bytes; var expectedDataInCookie = WebEncoders.Base64UrlEncode(expectedDataToProtect); var dataProtector = new PassThroughDataProtector(); var tempDataProvider = GetProvider( @@ -300,7 +287,7 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures .Returns(responseCookies); // Act - tempDataProvider.SaveTempData(httpContext.Object, values); + tempDataProvider.SaveTempData(httpContext.Object, Dictionary); // Assert Assert.Equal(1, responseCookies.Count); @@ -320,9 +307,7 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures { // Arrange var values = new Dictionary(); - values.Add("int", 10); - var tempDataProviderStore = new TempDataSerializer(); - var serializedData = tempDataProviderStore.Serialize(values); + var serializedData = Bytes; var base64AndUrlEncodedData = WebEncoders.Base64UrlEncode(serializedData); var dataProtector = new PassThroughDataProtector(); var tempDataProvider = GetProvider(dataProtector); @@ -358,7 +343,7 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures } [Fact] - public void SaveAndLoad_StringCanBeStoredAndLoaded() + public void SaveAndLoad_Works() { // Arrange var testProvider = GetProvider(); @@ -371,220 +356,10 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures // Act testProvider.SaveTempData(context, input); UpdateRequestWithCookies(context); - var TempData = testProvider.LoadTempData(context); + var tempData = testProvider.LoadTempData(context); // Assert - var stringVal = Assert.IsType(TempData["string"]); - Assert.Equal("value", stringVal); - } - - [Theory] - [InlineData(10)] - [InlineData(int.MaxValue)] - [InlineData(int.MinValue)] - public void SaveAndLoad_IntCanBeStoredAndLoaded(int expected) - { - // Arrange - var testProvider = GetProvider(); - var input = new Dictionary - { - { "int", expected } - }; - var context = GetHttpContext(); - - // Act - testProvider.SaveTempData(context, input); - UpdateRequestWithCookies(context); - var TempData = testProvider.LoadTempData(context); - - // Assert - var intVal = Assert.IsType(TempData["int"]); - Assert.Equal(expected, intVal); - } - - [Theory] - [InlineData(false)] - [InlineData(true)] - public void SaveAndLoad_BoolCanBeStoredAndLoaded(bool value) - { - // Arrange - var testProvider = GetProvider(); - var input = new Dictionary - { - { "bool", value } - }; - var context = GetHttpContext(); - - // Act - testProvider.SaveTempData(context, input); - UpdateRequestWithCookies(context); - var TempData = testProvider.LoadTempData(context); - - // Assert - var boolVal = Assert.IsType(TempData["bool"]); - Assert.Equal(value, boolVal); - } - - [Fact] - public void SaveAndLoad_DateTimeCanBeStoredAndLoaded() - { - // Arrange - var testProvider = GetProvider(); - var inputDatetime = new DateTime(2010, 12, 12, 1, 2, 3, DateTimeKind.Local); - var input = new Dictionary - { - { "DateTime", inputDatetime } - }; - var context = GetHttpContext(); - - // Act - testProvider.SaveTempData(context, input); - UpdateRequestWithCookies(context); - var TempData = testProvider.LoadTempData(context); - - // Assert - var datetime = Assert.IsType(TempData["DateTime"]); - Assert.Equal(inputDatetime, datetime); - } - - [Fact] - public void SaveAndLoad_GuidCanBeStoredAndLoaded() - { - // Arrange - var testProvider = GetProvider(); - var inputGuid = Guid.NewGuid(); - var input = new Dictionary - { - { "Guid", inputGuid } - }; - var context = GetHttpContext(); - - // Act - testProvider.SaveTempData(context, input); - UpdateRequestWithCookies(context); - var TempData = testProvider.LoadTempData(context); - - // Assert - var guidVal = Assert.IsType(TempData["Guid"]); - Assert.Equal(inputGuid, guidVal); - } - - [Fact] - public void SaveAndLoad_EnumCanBeSavedAndLoaded() - { - // Arrange - var key = "EnumValue"; - var testProvider = GetProvider(); - var expected = DayOfWeek.Friday; - var input = new Dictionary - { - { key, expected } - }; - var context = GetHttpContext(); - - // Act - testProvider.SaveTempData(context, input); - UpdateRequestWithCookies(context); - var TempData = testProvider.LoadTempData(context); - var result = TempData[key]; - - // Assert - var actual = (DayOfWeek)result; - Assert.Equal(expected, actual); - } - - [Theory] - [InlineData(3100000000L)] - [InlineData(-3100000000L)] - public void SaveAndLoad_LongCanBeSavedAndLoaded(long expected) - { - // Arrange - var key = "LongValue"; - var testProvider = GetProvider(); - var input = new Dictionary - { - { key, expected } - }; - var context = GetHttpContext(); - - // Act - testProvider.SaveTempData(context, input); - UpdateRequestWithCookies(context); - var TempData = testProvider.LoadTempData(context); - var result = TempData[key]; - - // Assert - var actual = Assert.IsType(result); - Assert.Equal(expected, actual); - } - - [Fact] - public void SaveAndLoad_ListCanBeStoredAndLoaded() - { - // Arrange - var testProvider = GetProvider(); - var input = new Dictionary - { - { "List`string", new List { "one", "two" } } - }; - var context = GetHttpContext(); - - // Act - testProvider.SaveTempData(context, input); - UpdateRequestWithCookies(context); - var TempData = testProvider.LoadTempData(context); - - // Assert - var list = (IList)TempData["List`string"]; - Assert.Equal(2, list.Count); - Assert.Equal("one", list[0]); - Assert.Equal("two", list[1]); - } - - [Fact] - public void SaveAndLoad_DictionaryCanBeStoredAndLoaded() - { - // Arrange - var testProvider = GetProvider(); - var inputDictionary = new Dictionary - { - { "Hello", "World" }, - }; - var input = new Dictionary - { - { "Dictionary", inputDictionary } - }; - var context = GetHttpContext(); - - // Act - testProvider.SaveTempData(context, input); - UpdateRequestWithCookies(context); - var TempData = testProvider.LoadTempData(context); - - // Assert - var dictionary = Assert.IsType>(TempData["Dictionary"]); - Assert.Equal("World", dictionary["Hello"]); - } - - [Fact] - public void SaveAndLoad_EmptyDictionary_RoundTripsAsNull() - { - // Arrange - var testProvider = GetProvider(); - var input = new Dictionary - { - { "EmptyDictionary", new Dictionary() } - }; - var context = GetHttpContext(); - - // Act - testProvider.SaveTempData(context, input); - UpdateRequestWithCookies(context); - var TempData = testProvider.LoadTempData(context); - - // Assert - var emptyDictionary = (IDictionary)TempData["EmptyDictionary"]; - Assert.Null(emptyDictionary); + Assert.Same(Dictionary, tempData); } private static HttpContext GetHttpContext() @@ -680,7 +455,11 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures var testOptions = new Mock>(); testOptions.SetupGet(o => o.Value).Returns(options); - return new CookieTempDataProvider(new PassThroughDataProtectionProvider(dataProtector), NullLoggerFactory.Instance, testOptions.Object); + return new CookieTempDataProvider( + new PassThroughDataProtectionProvider(dataProtector), + NullLoggerFactory.Instance, + testOptions.Object, + new TestTempDataSerializer()); } private class PassThroughDataProtectionProvider : IDataProtectionProvider @@ -731,5 +510,18 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures public CookieOptions Options { get; set; } } + + private class TestTempDataSerializer : TempDataSerializer + { + public override IDictionary Deserialize(byte[] unprotectedData) + { + return Dictionary; + } + + public override byte[] Serialize(IDictionary values) + { + return Bytes; + } + } } } \ No newline at end of file diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/Filters/TempDataApplicationModelProviderTest.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/Filters/TempDataApplicationModelProviderTest.cs index b79150f56b..404bf2a4ab 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/Filters/TempDataApplicationModelProviderTest.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/Filters/TempDataApplicationModelProviderTest.cs @@ -6,7 +6,9 @@ using System.Linq; using System.Reflection; using Microsoft.AspNetCore.Mvc.ApplicationModels; using Microsoft.AspNetCore.Mvc.ModelBinding; +using Microsoft.AspNetCore.Mvc.ViewFeatures.Infrastructure; using Microsoft.Extensions.Options; +using Moq; using Xunit; namespace Microsoft.AspNetCore.Mvc.ViewFeatures.Filters @@ -18,8 +20,7 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures.Filters { // Arrange var type = typeof(TestController_NoTempDataProperties); - var options = Options.Create(new MvcViewOptions()); - var provider = new TempDataApplicationModelProvider(options); + var provider = CreateProvider(); var context = GetContext(type); @@ -36,8 +37,7 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures.Filters { // Arrange var type = typeof(TestController_PrivateSet); - var options = Options.Create(new MvcViewOptions()); - var provider = new TempDataApplicationModelProvider(options); + var provider = CreateProvider(); var expected = $"The '{type.FullName}.Test' property with TempDataAttribute is invalid. A property using TempDataAttribute must have a public getter and setter."; var context = GetContext(type); @@ -52,8 +52,7 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures.Filters { // Arrange var type = typeof(TestController_NullableNonPrimitiveTempDataProperty); - var options = Options.Create(new MvcViewOptions()); - var provider = new TempDataApplicationModelProvider(options); + var provider = CreateProvider(); var context = GetContext(type); @@ -71,8 +70,7 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures.Filters // Arrange var type = typeof(TestController_OneTempDataProperty); var expected = type.GetProperty(nameof(TestController_OneTempDataProperty.Test2)); - var options = Options.Create(new MvcViewOptions()); - var provider = new TempDataApplicationModelProvider(options); + var provider = CreateProvider(); var context = GetContext(type); @@ -93,9 +91,8 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures.Filters { // Arrange var expected = typeof(TestController_OneTempDataProperty).GetProperty(nameof(TestController_OneTempDataProperty.Test2)); - var options = Options.Create(new MvcViewOptions()); var type = typeof(TestController_OneTempDataProperty); - var provider = new TempDataApplicationModelProvider(options); + var provider = CreateProvider(); var context = GetContext(type); // Act @@ -110,6 +107,12 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures.Filters Assert.Equal("Test2", property.Key); } + private static TempDataApplicationModelProvider CreateProvider() + { + var tempDataSerializer = Mock.Of(s => s.CanSerializeType(It.IsAny()) == true); + return new TempDataApplicationModelProvider(tempDataSerializer); + } + private static ApplicationModelProviderContext GetContext(Type type) { var defaultProvider = new DefaultApplicationModelProvider( diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/PartialViewResultExecutorTest.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/PartialViewResultExecutorTest.cs index d3b74704df..5b161b6dab 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/PartialViewResultExecutorTest.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/PartialViewResultExecutorTest.cs @@ -366,7 +366,7 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures options, new TestHttpResponseStreamWriterFactory(), new CompositeViewEngine(options), - new TempDataDictionaryFactory(new SessionStateTempDataProvider()), + Mock.Of(), diagnosticListener, NullLoggerFactory.Instance, new EmptyModelMetadataProvider()); diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/PartialViewResultTest.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/PartialViewResultTest.cs index 91766e10cb..a78e3a103c 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/PartialViewResultTest.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/PartialViewResultTest.cs @@ -221,7 +221,7 @@ namespace Microsoft.AspNetCore.Mvc options, new TestHttpResponseStreamWriterFactory(), new CompositeViewEngine(options), - new TempDataDictionaryFactory(new SessionStateTempDataProvider()), + Mock.Of(), new DiagnosticListener("Microsoft.AspNetCore"), NullLoggerFactory.Instance, new EmptyModelMetadataProvider()); diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/SessionStateTempDataProviderTest.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/SessionStateTempDataProviderTest.cs index 2086bbccc1..47db8ef2bc 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/SessionStateTempDataProviderTest.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/SessionStateTempDataProviderTest.cs @@ -4,21 +4,29 @@ using System; using System.Collections.Generic; using System.Linq; +using System.Text; using System.Threading; using System.Threading.Tasks; using Microsoft.AspNetCore.Http; using Microsoft.AspNetCore.Http.Features; +using Microsoft.AspNetCore.Mvc.ViewFeatures.Infrastructure; using Xunit; namespace Microsoft.AspNetCore.Mvc.ViewFeatures { public class SessionStateTempDataProviderTest { + private static readonly byte[] Bytes = Encoding.UTF8.GetBytes("test value"); + private static readonly IDictionary Dictionary = new Dictionary + { + { "key", "value" }, + }; + [Fact] public void Load_ThrowsException_WhenSessionIsNotEnabled() { // Arrange - var testProvider = new SessionStateTempDataProvider(); + var testProvider = CreateTempDataProvider(); // Act & Assert Assert.Throws(() => @@ -31,14 +39,12 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures public void Save_ThrowsException_WhenSessionIsNotEnabled() { // Arrange - var testProvider = new SessionStateTempDataProvider(); - var values = new Dictionary(); - values.Add("key1", "value1"); + var testProvider = CreateTempDataProvider(); // Act & Assert Assert.Throws(() => { - testProvider.SaveTempData(GetHttpContext(sessionEnabled: false), values); + testProvider.SaveTempData(GetHttpContext(sessionEnabled: false), Dictionary); }); } @@ -46,7 +52,7 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures public void Load_ReturnsEmptyDictionary_WhenNoSessionDataIsAvailable() { // Arrange - var testProvider = new SessionStateTempDataProvider(); + var testProvider = CreateTempDataProvider(); // Act var tempDataDictionary = testProvider.LoadTempData(GetHttpContext()); @@ -56,223 +62,18 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures } [Fact] - public void SaveAndLoad_StringCanBeStoredAndLoaded() + public void SaveAndLoad_Works() { // Arrange - var testProvider = new SessionStateTempDataProvider(); - var input = new Dictionary - { - { "string", "value" } - }; + var testProvider = CreateTempDataProvider(); var context = GetHttpContext(); // Act - testProvider.SaveTempData(context, input); - var TempData = testProvider.LoadTempData(context); + testProvider.SaveTempData(context, Dictionary); + var result = testProvider.LoadTempData(context); // Assert - var stringVal = Assert.IsType(TempData["string"]); - Assert.Equal("value", stringVal); - } - - [Theory] - [InlineData(10)] - [InlineData(int.MaxValue)] - [InlineData(int.MinValue)] - public void SaveAndLoad_IntCanBeStoredAndLoaded(int expected) - { - // Arrange - var testProvider = new SessionStateTempDataProvider(); - var input = new Dictionary - { - { "int", expected } - }; - var context = GetHttpContext(); - - // Act - testProvider.SaveTempData(context, input); - var TempData = testProvider.LoadTempData(context); - - // Assert - var intVal = Assert.IsType(TempData["int"]); - Assert.Equal(expected, intVal); - } - - [Theory] - [InlineData(false)] - [InlineData(true)] - public void SaveAndLoad_BoolCanBeStoredAndLoaded(bool value) - { - // Arrange - var testProvider = new SessionStateTempDataProvider(); - var input = new Dictionary - { - { "bool", value } - }; - var context = GetHttpContext(); - - // Act - testProvider.SaveTempData(context, input); - var TempData = testProvider.LoadTempData(context); - - // Assert - var boolVal = Assert.IsType(TempData["bool"]); - Assert.Equal(value, boolVal); - } - - [Fact] - public void SaveAndLoad_DateTimeCanBeStoredAndLoaded() - { - // Arrange - var testProvider = new SessionStateTempDataProvider(); - var inputDatetime = new DateTime(2010, 12, 12, 1, 2, 3, DateTimeKind.Local); - var input = new Dictionary - { - { "DateTime", inputDatetime } - }; - var context = GetHttpContext(); - - // Act - testProvider.SaveTempData(context, input); - var TempData = testProvider.LoadTempData(context); - - // Assert - var datetime = Assert.IsType(TempData["DateTime"]); - Assert.Equal(inputDatetime, datetime); - } - - [Fact] - public void SaveAndLoad_GuidCanBeStoredAndLoaded() - { - // Arrange - var testProvider = new SessionStateTempDataProvider(); - var inputGuid = Guid.NewGuid(); - var input = new Dictionary - { - { "Guid", inputGuid } - }; - var context = GetHttpContext(); - - // Act - testProvider.SaveTempData(context, input); - var TempData = testProvider.LoadTempData(context); - - // Assert - var guidVal = Assert.IsType(TempData["Guid"]); - Assert.Equal(inputGuid, guidVal); - } - - [Fact] - public void SaveAndLoad_EnumCanBeSavedAndLoaded() - { - // Arrange - var key = "EnumValue"; - var testProvider = new SessionStateTempDataProvider(); - var expected = DayOfWeek.Friday; - var input = new Dictionary - { - { key, expected } - }; - var context = GetHttpContext(); - - // Act - testProvider.SaveTempData(context, input); - var TempData = testProvider.LoadTempData(context); - var result = TempData[key]; - - // Assert - var actual = (DayOfWeek)result; - Assert.Equal(expected, actual); - } - - [Theory] - [InlineData(3100000000L)] - [InlineData(-3100000000L)] - public void SaveAndLoad_LongCanBeSavedAndLoaded(long expected) - { - // Arrange - var key = "LongValue"; - var testProvider = new SessionStateTempDataProvider(); - var input = new Dictionary - { - { key, expected } - }; - var context = GetHttpContext(); - - // Act - testProvider.SaveTempData(context, input); - var TempData = testProvider.LoadTempData(context); - var result = TempData[key]; - - // Assert - var actual = Assert.IsType(result); - Assert.Equal(expected, actual); - } - - [Fact] - public void SaveAndLoad_ListCanBeStoredAndLoaded() - { - // Arrange - var testProvider = new SessionStateTempDataProvider(); - var input = new Dictionary - { - { "List`string", new List { "one", "two" } } - }; - var context = GetHttpContext(); - - // Act - testProvider.SaveTempData(context, input); - var TempData = testProvider.LoadTempData(context); - - // Assert - var list = (IList)TempData["List`string"]; - Assert.Equal(2, list.Count); - Assert.Equal("one", list[0]); - Assert.Equal("two", list[1]); - } - - [Fact] - public void SaveAndLoad_DictionaryCanBeStoredAndLoaded() - { - // Arrange - var testProvider = new SessionStateTempDataProvider(); - var inputDictionary = new Dictionary - { - { "Hello", "World" }, - }; - var input = new Dictionary - { - { "Dictionary", inputDictionary } - }; - var context = GetHttpContext(); - - // Act - testProvider.SaveTempData(context, input); - var TempData = testProvider.LoadTempData(context); - - // Assert - var dictionary = Assert.IsType>(TempData["Dictionary"]); - Assert.Equal("World", dictionary["Hello"]); - } - - [Fact] - public void SaveAndLoad_EmptyDictionary_RoundTripsAsNull() - { - // Arrange - var testProvider = new SessionStateTempDataProvider(); - var input = new Dictionary - { - { "EmptyDictionary", new Dictionary() } - }; - var context = GetHttpContext(); - - // Act - testProvider.SaveTempData(context, input); - var TempData = testProvider.LoadTempData(context); - - // Assert - var emptyDictionary = (IDictionary)TempData["EmptyDictionary"]; - Assert.Null(emptyDictionary); + Assert.Same(Dictionary, result); } private class TestItem @@ -290,6 +91,12 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures return httpContext; } + private static SessionStateTempDataProvider CreateTempDataProvider() + { + var tempDataSerializer = new TestTempDataSerializer(); + return new SessionStateTempDataProvider(tempDataSerializer); + } + private class SessionFeature : ISessionFeature { public ISession Session { get; set; } @@ -335,5 +142,18 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures return _innerDictionary.TryGetValue(key, out value); } } + + private class TestTempDataSerializer : TempDataSerializer + { + public override IDictionary Deserialize(byte[] unprotectedData) + { + return Dictionary; + } + + public override byte[] Serialize(IDictionary values) + { + return Bytes; + } + } } } \ No newline at end of file diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/TempDataDictionaryFactoryTest.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/TempDataDictionaryFactoryTest.cs index 1cd417ecf4..ae38b5350a 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/TempDataDictionaryFactoryTest.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/TempDataDictionaryFactoryTest.cs @@ -2,6 +2,7 @@ // Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information. using Microsoft.AspNetCore.Http; +using Moq; using Xunit; namespace Microsoft.AspNetCore.Mvc.ViewFeatures @@ -45,7 +46,7 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures private TempDataDictionaryFactory CreateFactory() { - var provider = new SessionStateTempDataProvider(); + var provider = Mock.Of(); return new TempDataDictionaryFactory(provider); } } diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/TempDataDictionaryTest.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/TempDataDictionaryTest.cs index 23ee996a27..b9c1b6c813 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/TempDataDictionaryTest.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/TempDataDictionaryTest.cs @@ -10,29 +10,6 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures { public class TempDataDictionaryTest { - [Fact] - public void ThrowscdException_OnSettingValue_AndWhenSessionIsNotEnabled() - { - // Arrange - var tempData = new TempDataDictionary(new DefaultHttpContext(), new SessionStateTempDataProvider()); - - // Act & Assert - Assert.Throws(() => - { - tempData["key1"] = "value1"; - }); - } - - [Fact] - public void Keep_DoesNotThrowException_WhenDataIsNotLoaded() - { - // Arrange - var tempData = new TempDataDictionary(new DefaultHttpContext(), new SessionStateTempDataProvider()); - - // Act & Assert - tempData.Keep(); - } - [Fact] public void TempData_Load_CreatesEmptyDictionaryIfProviderReturnsNull() { @@ -190,12 +167,11 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures public void TempData_RemovalOfKeysAreCaseInsensitive() { var tempData = new TempDataDictionary(new DefaultHttpContext(), new NullTempDataProvider()); - object fooValue; tempData["Foo"] = "Foo"; tempData["Bar"] = "Bar"; // Act - tempData.TryGetValue("foo", out fooValue); + tempData.TryGetValue("foo", out var fooValue); var barValue = tempData["bar"]; tempData.Save(); diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ViewComponentResultTest.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ViewComponentResultTest.cs index 03165321ab..ebc324dbea 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ViewComponentResultTest.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ViewComponentResultTest.cs @@ -17,6 +17,7 @@ using Microsoft.AspNetCore.Mvc.ModelBinding; using Microsoft.AspNetCore.Mvc.ViewComponents; using Microsoft.AspNetCore.Mvc.ViewFeatures; using Microsoft.AspNetCore.Mvc.ViewFeatures.Buffers; +using Microsoft.AspNetCore.Mvc.ViewFeatures.Infrastructure; using Microsoft.AspNetCore.Routing; using Microsoft.Extensions.DependencyInjection; using Microsoft.Extensions.Logging; @@ -24,6 +25,7 @@ using Microsoft.Extensions.Logging.Abstractions; using Microsoft.Extensions.Options; using Microsoft.Extensions.WebEncoders.Testing; using Microsoft.Net.Http.Headers; +using Moq; using Xunit; namespace Microsoft.AspNetCore.Mvc @@ -31,7 +33,7 @@ namespace Microsoft.AspNetCore.Mvc public class ViewComponentResultTest { private readonly ITempDataDictionary _tempDataDictionary = - new TempDataDictionary(new DefaultHttpContext(), new SessionStateTempDataProvider()); + new TempDataDictionary(new DefaultHttpContext(), Mock.Of()); [Fact] public void Model_ExposesViewDataModel() @@ -575,6 +577,7 @@ namespace Microsoft.AspNetCore.Mvc services.AddSingleton(NullLoggerFactory.Instance); services.AddSingleton(); services.AddSingleton(); + services.AddSingleton(); services.AddSingleton(); services.AddSingleton(); services.AddSingleton, ViewComponentResultExecutor>(); diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ViewComponentTests.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ViewComponentTests.cs index 772d5be1be..05a99dbb16 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ViewComponentTests.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ViewComponentTests.cs @@ -12,6 +12,7 @@ using Microsoft.AspNetCore.Http.Features; using Microsoft.AspNetCore.Mvc.Rendering; using Microsoft.AspNetCore.Mvc.ViewComponents; using Microsoft.AspNetCore.Mvc.ViewFeatures; +using Moq; using Xunit; namespace Microsoft.AspNetCore.Mvc @@ -244,7 +245,7 @@ namespace Microsoft.AspNetCore.Mvc var httpContext = new DefaultHttpContext(); httpContext.Features.Set(new SessionFeature() { Session = new TestSession() }); var viewContext = new ViewContext(); - viewContext.TempData = new TempDataDictionary(httpContext, new SessionStateTempDataProvider()); + viewContext.TempData = new TempDataDictionary(httpContext, Mock.Of()); var viewComponentContext = new ViewComponentContext(); viewComponentContext.ViewContext = viewContext; diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ViewComponents/ContentViewComponentResultTest.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ViewComponents/ContentViewComponentResultTest.cs index ab1dffe047..73c0d22ca0 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ViewComponents/ContentViewComponentResultTest.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ViewComponents/ContentViewComponentResultTest.cs @@ -46,7 +46,7 @@ namespace Microsoft.AspNetCore.Mvc actionContext, view, viewData, - new TempDataDictionary(httpContext, new SessionStateTempDataProvider()), + new TempDataDictionary(httpContext, Mock.Of()), TextWriter.Null, new HtmlHelperOptions()); diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ViewComponents/HtmlContentViewComponentResultTest.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ViewComponents/HtmlContentViewComponentResultTest.cs index 21f8f61c31..4a0694e52b 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ViewComponents/HtmlContentViewComponentResultTest.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ViewComponents/HtmlContentViewComponentResultTest.cs @@ -46,7 +46,7 @@ namespace Microsoft.AspNetCore.Mvc actionContext, view, viewData, - new TempDataDictionary(actionContext.HttpContext, new SessionStateTempDataProvider()), + new TempDataDictionary(actionContext.HttpContext, Mock.Of()), TextWriter.Null, new HtmlHelperOptions()); diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ViewComponents/ViewComponentContextTest.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ViewComponents/ViewComponentContextTest.cs index 8afdb8dc14..d1bc74fc33 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ViewComponents/ViewComponentContextTest.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ViewComponents/ViewComponentContextTest.cs @@ -11,6 +11,7 @@ using Microsoft.AspNetCore.Mvc.Rendering; using Microsoft.AspNetCore.Mvc.ViewFeatures; using Microsoft.AspNetCore.Routing; using Microsoft.Extensions.WebEncoders.Testing; +using Moq; using Xunit; namespace Microsoft.AspNetCore.Mvc.ViewComponents @@ -24,7 +25,7 @@ namespace Microsoft.AspNetCore.Mvc.ViewComponents var httpContext = new DefaultHttpContext(); var actionContext = new ActionContext(httpContext, new RouteData(), new ActionDescriptor()); var viewData = new ViewDataDictionary(new EmptyModelMetadataProvider()); - var tempData = new TempDataDictionary(httpContext, new SessionStateTempDataProvider()); + var tempData = new TempDataDictionary(httpContext, Mock.Of()); var viewContext = new ViewContext( actionContext, NullView.Instance, @@ -91,7 +92,7 @@ namespace Microsoft.AspNetCore.Mvc.ViewComponents actionContext, NullView.Instance, viewData, - new TempDataDictionary(httpContext, new SessionStateTempDataProvider()), + new TempDataDictionary(httpContext, Mock.Of()), TextWriter.Null, new HtmlHelperOptions()); diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ViewComponents/ViewViewComponentResultTest.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ViewComponents/ViewViewComponentResultTest.cs index 989afc52ab..1f0255c7e8 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ViewComponents/ViewViewComponentResultTest.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ViewComponents/ViewViewComponentResultTest.cs @@ -26,7 +26,7 @@ namespace Microsoft.AspNetCore.Mvc public class ViewViewComponentResultTest { private readonly ITempDataDictionary _tempDataDictionary = - new TempDataDictionary(new DefaultHttpContext(), new SessionStateTempDataProvider()); + new TempDataDictionary(new DefaultHttpContext(), Mock.Of()); [Fact] public void Execute_RendersPartialViews() @@ -529,7 +529,7 @@ namespace Microsoft.AspNetCore.Mvc actionContext, view, viewData, - new TempDataDictionary(httpContext, new SessionStateTempDataProvider()), + new TempDataDictionary(httpContext, Mock.Of()), TextWriter.Null, new HtmlHelperOptions()); diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ViewExecutorTest.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ViewExecutorTest.cs index 2729b86e99..e83dd07b71 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ViewExecutorTest.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ViewExecutorTest.cs @@ -128,7 +128,7 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures var httpContext = new DefaultHttpContext(); var serviceCollection = new ServiceCollection(); serviceCollection.AddSingleton(new EmptyModelMetadataProvider()); - var tempDataProvider = new SessionStateTempDataProvider(); + var tempDataProvider = Mock.Of(); serviceCollection.AddSingleton(new TempDataDictionary(httpContext, tempDataProvider)); return serviceCollection.BuildServiceProvider(); @@ -362,7 +362,7 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures Options.Create(new MvcViewOptions()), new TestHttpResponseStreamWriterFactory(), new Mock(MockBehavior.Strict).Object, - new TempDataDictionaryFactory(new SessionStateTempDataProvider()), + new TempDataDictionaryFactory(Mock.Of()), diagnosticListener, new EmptyModelMetadataProvider()); } diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ViewResultExecutorTest.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ViewResultExecutorTest.cs index 11d34a3d18..7fa09973a0 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ViewResultExecutorTest.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ViewResultExecutorTest.cs @@ -356,7 +356,7 @@ namespace Microsoft.AspNetCore.Mvc.ViewFeatures options, new TestHttpResponseStreamWriterFactory(), new CompositeViewEngine(options), - new TempDataDictionaryFactory(new SessionStateTempDataProvider()), + new TempDataDictionaryFactory(Mock.Of()), diagnosticListener, NullLoggerFactory.Instance, new EmptyModelMetadataProvider()); diff --git a/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ViewResultTest.cs b/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ViewResultTest.cs index 5275edc841..c05b10c071 100644 --- a/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ViewResultTest.cs +++ b/src/Mvc/test/Microsoft.AspNetCore.Mvc.ViewFeatures.Test/ViewResultTest.cs @@ -233,7 +233,7 @@ namespace Microsoft.AspNetCore.Mvc options, new TestHttpResponseStreamWriterFactory(), new CompositeViewEngine(options), - new TempDataDictionaryFactory(new SessionStateTempDataProvider()), + Mock.Of(), new DiagnosticListener("Microsoft.AspNetCore"), NullLoggerFactory.Instance, new EmptyModelMetadataProvider()); diff --git a/src/Mvc/test/WebSites/ApiExplorerWebSite/ApiExplorerWebSite.csproj b/src/Mvc/test/WebSites/ApiExplorerWebSite/ApiExplorerWebSite.csproj index d77acdb16a..c0486a4763 100644 --- a/src/Mvc/test/WebSites/ApiExplorerWebSite/ApiExplorerWebSite.csproj +++ b/src/Mvc/test/WebSites/ApiExplorerWebSite/ApiExplorerWebSite.csproj @@ -8,6 +8,7 @@ + diff --git a/src/Mvc/test/WebSites/ApiExplorerWebSite/Startup.cs b/src/Mvc/test/WebSites/ApiExplorerWebSite/Startup.cs index 08965fe0bf..28d1b4d6cf 100644 --- a/src/Mvc/test/WebSites/ApiExplorerWebSite/Startup.cs +++ b/src/Mvc/test/WebSites/ApiExplorerWebSite/Startup.cs @@ -33,12 +33,10 @@ namespace ApiExplorerWebSite typeof(ApiExplorerInboundOutBoundController))); options.Conventions.Add(new ApiExplorerRouteChangeConvention(wellKnownChangeToken)); - var jsonOutputFormatter = options.OutputFormatters.OfType().First(); - options.OutputFormatters.Clear(); - options.OutputFormatters.Add(jsonOutputFormatter); options.OutputFormatters.Add(new XmlDataContractSerializerOutputFormatter()); }) + .AddNewtonsoftJson() .SetCompatibilityVersion(CompatibilityVersion.Latest); services.AddSingleton(); diff --git a/src/Mvc/test/WebSites/BasicWebSite/Areas/Area1/Controllers/RemoteAttribute_VerifyController.cs b/src/Mvc/test/WebSites/BasicWebSite/Areas/Area1/Controllers/RemoteAttribute_VerifyController.cs index 04a33e129f..223f8e5aed 100644 --- a/src/Mvc/test/WebSites/BasicWebSite/Areas/Area1/Controllers/RemoteAttribute_VerifyController.cs +++ b/src/Mvc/test/WebSites/BasicWebSite/Areas/Area1/Controllers/RemoteAttribute_VerifyController.cs @@ -14,7 +14,7 @@ namespace BasicWebSite.Areas.Area1.Controllers [AcceptVerbs("Get", "Post")] public IActionResult IsIdAvailable(string userId1, string userId3) { - return Json(data: false); + return new JsonResult(value: false); } } } \ No newline at end of file diff --git a/src/Mvc/test/WebSites/BasicWebSite/Areas/Area2/Controllers/RemoteAttribute_VerifyController.cs b/src/Mvc/test/WebSites/BasicWebSite/Areas/Area2/Controllers/RemoteAttribute_VerifyController.cs index 41401e86ee..9762d64c33 100644 --- a/src/Mvc/test/WebSites/BasicWebSite/Areas/Area2/Controllers/RemoteAttribute_VerifyController.cs +++ b/src/Mvc/test/WebSites/BasicWebSite/Areas/Area2/Controllers/RemoteAttribute_VerifyController.cs @@ -14,7 +14,7 @@ namespace BasicWebSite.Ares.Area2.Controllers [HttpGet] public IActionResult IsIdAvailable(RemoteAttributeUser user) { - return Json(data: string.Format( + return new JsonResult(value: string.Format( "/Area2/RemoteAttribute_Verify/IsIdAvailable rejects '{0}' with '{1}', '{2}', and '{3}'.", user.UserId4, user.UserId1, diff --git a/src/Mvc/test/WebSites/BasicWebSite/BasicWebSite.csproj b/src/Mvc/test/WebSites/BasicWebSite/BasicWebSite.csproj index b7802698bb..a8e4544fb1 100644 --- a/src/Mvc/test/WebSites/BasicWebSite/BasicWebSite.csproj +++ b/src/Mvc/test/WebSites/BasicWebSite/BasicWebSite.csproj @@ -12,6 +12,7 @@ + diff --git a/src/Mvc/test/WebSites/BasicWebSite/Controllers/ContentNegotiation/FallbackOnTypeBasedMatchController.cs b/src/Mvc/test/WebSites/BasicWebSite/Controllers/ContentNegotiation/FallbackOnTypeBasedMatchController.cs index a232df7585..929c81e0f3 100644 --- a/src/Mvc/test/WebSites/BasicWebSite/Controllers/ContentNegotiation/FallbackOnTypeBasedMatchController.cs +++ b/src/Mvc/test/WebSites/BasicWebSite/Controllers/ContentNegotiation/FallbackOnTypeBasedMatchController.cs @@ -12,12 +12,12 @@ namespace BasicWebSite.Controllers.ContentNegotiation public class FallbackOnTypeBasedMatchController : Controller { private readonly IOptions _mvcOptions; - private readonly JsonOutputFormatter _jsonOutputFormatter; + private readonly NewtonsoftJsonOutputFormatter _jsonOutputFormatter; public FallbackOnTypeBasedMatchController(IOptions mvcOptions) { _mvcOptions = mvcOptions; - _jsonOutputFormatter = mvcOptions.Value.OutputFormatters.OfType().First(); + _jsonOutputFormatter = mvcOptions.Value.OutputFormatters.OfType().First(); } public int UseTheFallback_WithDefaultFormatters(int input) diff --git a/src/Mvc/test/WebSites/BasicWebSite/Controllers/ContentNegotiation/NormalController.cs b/src/Mvc/test/WebSites/BasicWebSite/Controllers/ContentNegotiation/NormalController.cs index bc3671b0bb..19150c264f 100644 --- a/src/Mvc/test/WebSites/BasicWebSite/Controllers/ContentNegotiation/NormalController.cs +++ b/src/Mvc/test/WebSites/BasicWebSite/Controllers/ContentNegotiation/NormalController.cs @@ -7,6 +7,7 @@ using BasicWebSite.Models; using Microsoft.AspNetCore.Mvc; using Microsoft.AspNetCore.Mvc.Filters; using Microsoft.AspNetCore.Mvc.Formatters; +using Microsoft.AspNetCore.Mvc.NewtonsoftJson; using Newtonsoft.Json; namespace BasicWebSite.Controllers.ContentNegotiation @@ -14,7 +15,7 @@ namespace BasicWebSite.Controllers.ContentNegotiation public class NormalController : Controller { private static readonly JsonSerializerSettings _indentedSettings; - private readonly JsonOutputFormatter _indentingFormatter; + private readonly NewtonsoftJsonOutputFormatter _indentingFormatter; static NormalController() { @@ -24,7 +25,7 @@ namespace BasicWebSite.Controllers.ContentNegotiation public NormalController(ArrayPool charPool) { - _indentingFormatter = new JsonOutputFormatter(_indentedSettings, charPool); + _indentingFormatter = new NewtonsoftJsonOutputFormatter(_indentedSettings, charPool); } public override void OnActionExecuted(ActionExecutedContext context) diff --git a/src/Mvc/test/WebSites/BasicWebSite/Controllers/HomeController.cs b/src/Mvc/test/WebSites/BasicWebSite/Controllers/HomeController.cs index 5d5fb11525..c2f1f402c2 100644 --- a/src/Mvc/test/WebSites/BasicWebSite/Controllers/HomeController.cs +++ b/src/Mvc/test/WebSites/BasicWebSite/Controllers/HomeController.cs @@ -91,7 +91,7 @@ namespace BasicWebSite.Controllers public IActionResult JsonHelperWithSettingsInView(bool snakeCase) { - Person person = new Person + var person = new Person { id = 9000, FullName = "John Smith" diff --git a/src/Mvc/test/WebSites/BasicWebSite/Controllers/JsonResultController.cs b/src/Mvc/test/WebSites/BasicWebSite/Controllers/JsonResultController.cs index 3964b292f3..0a07733629 100644 --- a/src/Mvc/test/WebSites/BasicWebSite/Controllers/JsonResultController.cs +++ b/src/Mvc/test/WebSites/BasicWebSite/Controllers/JsonResultController.cs @@ -2,7 +2,7 @@ // Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information. using Microsoft.AspNetCore.Mvc; -using Microsoft.AspNetCore.Mvc.Formatters; +using Microsoft.AspNetCore.Mvc.NewtonsoftJson; using Newtonsoft.Json; using Newtonsoft.Json.Serialization; @@ -20,7 +20,7 @@ namespace BasicWebSite.Controllers public JsonResult Plain() { - return Json(new { Message = "hello" }); + return new JsonResult(new { Message = "hello" }); } public JsonResult CustomContentType() @@ -32,17 +32,17 @@ namespace BasicWebSite.Controllers public JsonResult CustomSerializerSettings() { - return Json(new { Message = "hello" }, _customSerializerSettings); + return new JsonResult(new { Message = "hello" }, _customSerializerSettings); } public JsonResult Null() { - return Json(null); + return new JsonResult(null); } public JsonResult String() { - return Json("hello"); + return new JsonResult("hello"); } } } \ No newline at end of file diff --git a/src/Mvc/test/WebSites/BasicWebSite/Controllers/RemoteAttribute_VerifyController.cs b/src/Mvc/test/WebSites/BasicWebSite/Controllers/RemoteAttribute_VerifyController.cs index 1641d9870a..ab027927fd 100644 --- a/src/Mvc/test/WebSites/BasicWebSite/Controllers/RemoteAttribute_VerifyController.cs +++ b/src/Mvc/test/WebSites/BasicWebSite/Controllers/RemoteAttribute_VerifyController.cs @@ -38,7 +38,7 @@ namespace BasicWebSite.Controllers value = string.Empty; } - return Json(data: $"/RemoteAttribute_Verify/IsIdAvailable rejects {name}: '{value}'."); + return new JsonResult($"/RemoteAttribute_Verify/IsIdAvailable rejects {name}: '{value}'."); } } } \ No newline at end of file diff --git a/src/Mvc/test/WebSites/BasicWebSite/Controllers/RequestFormLimitsController.cs b/src/Mvc/test/WebSites/BasicWebSite/Controllers/RequestFormLimitsController.cs index 027ae44b0d..5bca108bbf 100644 --- a/src/Mvc/test/WebSites/BasicWebSite/Controllers/RequestFormLimitsController.cs +++ b/src/Mvc/test/WebSites/BasicWebSite/Controllers/RequestFormLimitsController.cs @@ -11,49 +11,49 @@ namespace BasicWebSite.Controllers { [HttpPost] [ValidateAntiForgeryToken] - public IActionResult RequestFormLimitsBeforeAntiforgeryValidation(Product product) + public ActionResult RequestFormLimitsBeforeAntiforgeryValidation(Product product) { if (!ModelState.IsValid) { return BadRequest(ModelState); } - return Json(product); + return product; } [HttpPost] [RequestFormLimits(ValueCountLimit = 5)] - public IActionResult OverrideControllerLevelLimits(Product product) + public ActionResult OverrideControllerLevelLimits(Product product) { if (!ModelState.IsValid) { return BadRequest(ModelState); } - return Json(product); + return product; } [HttpPost] [RequestFormLimits] - public IActionResult OverrideControllerLevelLimitsUsingDefaultLimits(Product product) + public ActionResult OverrideControllerLevelLimitsUsingDefaultLimits(Product product) { if (!ModelState.IsValid) { return BadRequest(ModelState); } - return Json(product); + return product; } [HttpPost] [RequestFormLimits(ValueCountLimit = 2)] [RequestSizeLimit(100)] [ValidateAntiForgeryToken] - public IActionResult RequestSizeLimitBeforeRequestFormLimits(Product product) + public ActionResult RequestSizeLimitBeforeRequestFormLimits(Product product) { if (!ModelState.IsValid) { return BadRequest(ModelState); } - return Json(product); + return product; } } } diff --git a/src/Mvc/test/WebSites/BasicWebSite/Controllers/RequestSizeLimitController.cs b/src/Mvc/test/WebSites/BasicWebSite/Controllers/RequestSizeLimitController.cs index f4e8f3c3b7..535ba80889 100644 --- a/src/Mvc/test/WebSites/BasicWebSite/Controllers/RequestSizeLimitController.cs +++ b/src/Mvc/test/WebSites/BasicWebSite/Controllers/RequestSizeLimitController.cs @@ -1,10 +1,8 @@ // Copyright (c) .NET Foundation. All rights reserved. // Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information. -using System; using BasicWebSite.Models; using Microsoft.AspNetCore.Mvc; -using Microsoft.AspNetCore.Mvc.Filters; namespace BasicWebSite.Controllers { @@ -13,25 +11,25 @@ namespace BasicWebSite.Controllers { [HttpPost] [ValidateAntiForgeryToken] - public IActionResult RequestSizeLimitCheckBeforeAntiforgeryValidation(Product product) + public ActionResult RequestSizeLimitCheckBeforeAntiforgeryValidation(Product product) { if (!ModelState.IsValid) { return BadRequest(ModelState); } - return Json(product); + return product; } [HttpPost] [DisableRequestSizeLimit] - public IActionResult DisableRequestSizeLimit([FromBody] Product product) + public ActionResult DisableRequestSizeLimit([FromBody] Product product) { if (!ModelState.IsValid) { return BadRequest(ModelState); } - return Json(product); + return product; } } } diff --git a/src/Mvc/test/WebSites/BasicWebSite/Controllers/RoutingController.cs b/src/Mvc/test/WebSites/BasicWebSite/Controllers/RoutingController.cs index e2c416505d..d20cbfd2a9 100644 --- a/src/Mvc/test/WebSites/BasicWebSite/Controllers/RoutingController.cs +++ b/src/Mvc/test/WebSites/BasicWebSite/Controllers/RoutingController.cs @@ -8,10 +8,10 @@ namespace BasicWebSite { public class RoutingController : Controller { - public ActionResult HasEndpointMatch() + public bool HasEndpointMatch() { var endpointFeature = HttpContext.Features.Get(); - return Json(endpointFeature?.Endpoint != null); + return endpointFeature?.Endpoint != null; } } } \ No newline at end of file diff --git a/src/Mvc/test/WebSites/BasicWebSite/Startup.cs b/src/Mvc/test/WebSites/BasicWebSite/Startup.cs index 4cd7646bfb..930837a49f 100644 --- a/src/Mvc/test/WebSites/BasicWebSite/Startup.cs +++ b/src/Mvc/test/WebSites/BasicWebSite/Startup.cs @@ -31,6 +31,7 @@ namespace BasicWebSite options.EnableEndpointRouting = false; }) .SetCompatibilityVersion(CompatibilityVersion.Latest) + .AddNewtonsoftJson() .AddXmlDataContractSerializerFormatters(); services.ConfigureBaseWebSiteAuthPolicies(); diff --git a/src/Mvc/test/WebSites/BasicWebSite/StartupRequestLimitSize.cs b/src/Mvc/test/WebSites/BasicWebSite/StartupRequestLimitSize.cs index 066fc406da..72aff81040 100644 --- a/src/Mvc/test/WebSites/BasicWebSite/StartupRequestLimitSize.cs +++ b/src/Mvc/test/WebSites/BasicWebSite/StartupRequestLimitSize.cs @@ -15,6 +15,7 @@ namespace BasicWebSite public void ConfigureServices(IServiceCollection services) { services.AddMvc() + .AddNewtonsoftJson() .SetCompatibilityVersion(CompatibilityVersion.Latest); services.ConfigureBaseWebSiteAuthPolicies(); } diff --git a/src/Mvc/test/WebSites/BasicWebSite/StartupWithCookieTempDataProviderAndCookieConsent.cs b/src/Mvc/test/WebSites/BasicWebSite/StartupWithCookieTempDataProviderAndCookieConsent.cs index db15febae3..923109fdda 100644 --- a/src/Mvc/test/WebSites/BasicWebSite/StartupWithCookieTempDataProviderAndCookieConsent.cs +++ b/src/Mvc/test/WebSites/BasicWebSite/StartupWithCookieTempDataProviderAndCookieConsent.cs @@ -12,6 +12,7 @@ namespace BasicWebSite public void ConfigureServices(IServiceCollection services) { services.AddMvc() + .AddNewtonsoftJson() .SetCompatibilityVersion(CompatibilityVersion.Latest); services.Configure(o => diff --git a/src/Mvc/test/WebSites/BasicWebSite/StartupWithCustomInvalidModelStateFactory.cs b/src/Mvc/test/WebSites/BasicWebSite/StartupWithCustomInvalidModelStateFactory.cs index 27c7b58761..f7d688a77a 100644 --- a/src/Mvc/test/WebSites/BasicWebSite/StartupWithCustomInvalidModelStateFactory.cs +++ b/src/Mvc/test/WebSites/BasicWebSite/StartupWithCustomInvalidModelStateFactory.cs @@ -19,6 +19,7 @@ namespace BasicWebSite services .AddMvc() + .AddNewtonsoftJson() .SetCompatibilityVersion(CompatibilityVersion.Latest); services.Configure(options => diff --git a/src/Mvc/test/WebSites/BasicWebSite/StartupWithEndpointRouting.cs b/src/Mvc/test/WebSites/BasicWebSite/StartupWithEndpointRouting.cs index 2bce493519..97c93de73a 100644 --- a/src/Mvc/test/WebSites/BasicWebSite/StartupWithEndpointRouting.cs +++ b/src/Mvc/test/WebSites/BasicWebSite/StartupWithEndpointRouting.cs @@ -17,6 +17,7 @@ namespace BasicWebSite services.AddMvc() .SetCompatibilityVersion(CompatibilityVersion.Latest) + .AddNewtonsoftJson() .AddXmlDataContractSerializerFormatters(); services.ConfigureBaseWebSiteAuthPolicies(); diff --git a/src/Mvc/test/WebSites/BasicWebSite/Views/Home/JsonHelperWithSettingsInView.cshtml b/src/Mvc/test/WebSites/BasicWebSite/Views/Home/JsonHelperWithSettingsInView.cshtml index 1f551bc9d3..f9537480c6 100644 --- a/src/Mvc/test/WebSites/BasicWebSite/Views/Home/JsonHelperWithSettingsInView.cshtml +++ b/src/Mvc/test/WebSites/BasicWebSite/Views/Home/JsonHelperWithSettingsInView.cshtml @@ -1,5 +1,6 @@ -@using Microsoft.AspNetCore.Mvc.Formatters -@using Newtonsoft.Json +@model BasicWebSite.Models.Person + +@using Microsoft.AspNetCore.Mvc.NewtonsoftJson @using Newtonsoft.Json.Serialization @{ var settings = JsonSerializerSettingsProvider.CreateSerializerSettings(); diff --git a/src/Mvc/test/WebSites/Common/TestResponseGenerator.cs b/src/Mvc/test/WebSites/Common/TestResponseGenerator.cs index 69427de69a..e2492fbfec 100644 --- a/src/Mvc/test/WebSites/Common/TestResponseGenerator.cs +++ b/src/Mvc/test/WebSites/Common/TestResponseGenerator.cs @@ -26,7 +26,7 @@ namespace Microsoft.AspNetCore.Mvc } } - public JsonResult Generate(params string[] expectedUrls) + public ActionResult Generate(params string[] expectedUrls) { var link = (string)null; var query = _actionContext.HttpContext.Request.Query; @@ -42,7 +42,7 @@ namespace Microsoft.AspNetCore.Mvc var attributeRoutingInfo = _actionContext.ActionDescriptor.AttributeRouteInfo; - return new JsonResult(new + return new OkObjectResult(new { expectedUrls = expectedUrls, actualUrl = _actionContext.HttpContext.Request.Path.Value, diff --git a/src/Mvc/test/WebSites/ControllersFromServicesClassLibrary/Inventory.cs b/src/Mvc/test/WebSites/ControllersFromServicesClassLibrary/Inventory.cs index 14cf643075..491994140c 100644 --- a/src/Mvc/test/WebSites/ControllersFromServicesClassLibrary/Inventory.cs +++ b/src/Mvc/test/WebSites/ControllersFromServicesClassLibrary/Inventory.cs @@ -8,9 +8,9 @@ namespace ControllersFromServicesClassLibrary public class Inventory : ResourcesController { [HttpGet] - public int Get() + public IActionResult Get() { - return 4; + return new ContentResult { Content = "4" }; } } } \ No newline at end of file diff --git a/src/Mvc/test/WebSites/ControllersFromServicesWebSite/AnotherController.cs b/src/Mvc/test/WebSites/ControllersFromServicesWebSite/AnotherController.cs index 2f2432b366..28343ab504 100644 --- a/src/Mvc/test/WebSites/ControllersFromServicesWebSite/AnotherController.cs +++ b/src/Mvc/test/WebSites/ControllersFromServicesWebSite/AnotherController.cs @@ -9,9 +9,9 @@ namespace ControllersFromServicesWebSite public class AnotherController : Controller { [HttpGet] - public int Get() + public IActionResult Get() { - return 1; + return new ContentResult { Content = "1" }; } [HttpGet("InServicesViewComponent")] diff --git a/src/Mvc/test/WebSites/CorsWebSite/CorsWebSite.csproj b/src/Mvc/test/WebSites/CorsWebSite/CorsWebSite.csproj index 87070b5059..5319d3cffa 100644 --- a/src/Mvc/test/WebSites/CorsWebSite/CorsWebSite.csproj +++ b/src/Mvc/test/WebSites/CorsWebSite/CorsWebSite.csproj @@ -8,6 +8,7 @@ + diff --git a/src/Mvc/test/WebSites/CorsWebSite/Startup.cs b/src/Mvc/test/WebSites/CorsWebSite/Startup.cs index 8759aa6922..37012118da 100644 --- a/src/Mvc/test/WebSites/CorsWebSite/Startup.cs +++ b/src/Mvc/test/WebSites/CorsWebSite/Startup.cs @@ -13,6 +13,7 @@ namespace CorsWebSite public void ConfigureServices(IServiceCollection services) { services.AddMvc(ConfigureMvcOptions) + .AddNewtonsoftJson() .SetCompatibilityVersion(CompatibilityVersion.Latest); services.Configure(options => { diff --git a/src/Mvc/test/WebSites/FilesWebSite/Controllers/UploadFilesController.cs b/src/Mvc/test/WebSites/FilesWebSite/Controllers/UploadFilesController.cs index 0839978cd0..3797be5269 100644 --- a/src/Mvc/test/WebSites/FilesWebSite/Controllers/UploadFilesController.cs +++ b/src/Mvc/test/WebSites/FilesWebSite/Controllers/UploadFilesController.cs @@ -12,7 +12,7 @@ namespace FilesWebSite.Controllers public class UploadFilesController : Controller { [HttpPost("UploadFiles")] - public async Task Post(User user) + public async Task Post(User user) { var resultUser = new { @@ -21,11 +21,11 @@ namespace FilesWebSite.Controllers Biography = await user.ReadBiography() }; - return Json(resultUser); + return resultUser; } [HttpPost("UploadProductSpecs")] - public IActionResult ProductSpecs(Product product) + public object ProductSpecs(Product product) { if (!ModelState.IsValid) { @@ -38,7 +38,7 @@ namespace FilesWebSite.Controllers files.Add(keyValuePair.Key, keyValuePair.Value?.Select(formFile => formFile?.FileName).ToList()); } - return Json(new { Name = product.Name, Specs = files }); + return new { Name = product.Name, Specs = files }; } } } diff --git a/src/Mvc/test/WebSites/FilesWebSite/FilesWebSite.csproj b/src/Mvc/test/WebSites/FilesWebSite/FilesWebSite.csproj index a56a9494f0..d17af6ea2f 100644 --- a/src/Mvc/test/WebSites/FilesWebSite/FilesWebSite.csproj +++ b/src/Mvc/test/WebSites/FilesWebSite/FilesWebSite.csproj @@ -12,6 +12,7 @@ + diff --git a/src/Mvc/test/WebSites/FilesWebSite/Startup.cs b/src/Mvc/test/WebSites/FilesWebSite/Startup.cs index 3e1404b3ff..8bb9762577 100644 --- a/src/Mvc/test/WebSites/FilesWebSite/Startup.cs +++ b/src/Mvc/test/WebSites/FilesWebSite/Startup.cs @@ -15,6 +15,7 @@ namespace FilesWebSite public void ConfigureServices(IServiceCollection services) { services.AddMvc() + .AddNewtonsoftJson() .SetCompatibilityVersion(CompatibilityVersion.Latest); } diff --git a/src/Mvc/test/WebSites/FormatterWebSite/Controllers/JsonFormatterController.cs b/src/Mvc/test/WebSites/FormatterWebSite/Controllers/JsonFormatterController.cs index e8e3f58d7f..569b86cc24 100644 --- a/src/Mvc/test/WebSites/FormatterWebSite/Controllers/JsonFormatterController.cs +++ b/src/Mvc/test/WebSites/FormatterWebSite/Controllers/JsonFormatterController.cs @@ -5,6 +5,7 @@ using System.Buffers; using Microsoft.AspNetCore.Http; using Microsoft.AspNetCore.Mvc; using Microsoft.AspNetCore.Mvc.Formatters; +using Microsoft.AspNetCore.Mvc.NewtonsoftJson; using Newtonsoft.Json; namespace FormatterWebSite.Controllers @@ -12,7 +13,7 @@ namespace FormatterWebSite.Controllers public class JsonFormatterController : Controller { private static readonly JsonSerializerSettings _indentedSettings; - private readonly JsonOutputFormatter _indentingFormatter; + private readonly NewtonsoftJsonOutputFormatter _indentingFormatter; static JsonFormatterController() { @@ -22,7 +23,7 @@ namespace FormatterWebSite.Controllers public JsonFormatterController(ArrayPool charPool) { - _indentingFormatter = new JsonOutputFormatter(_indentedSettings, charPool); + _indentingFormatter = new NewtonsoftJsonOutputFormatter(_indentedSettings, charPool); } public IActionResult ReturnsIndentedJson() diff --git a/src/Mvc/test/WebSites/FormatterWebSite/Controllers/ValidationController.cs b/src/Mvc/test/WebSites/FormatterWebSite/Controllers/ValidationController.cs index 5aee43c803..5b0f0ca4a0 100644 --- a/src/Mvc/test/WebSites/FormatterWebSite/Controllers/ValidationController.cs +++ b/src/Mvc/test/WebSites/FormatterWebSite/Controllers/ValidationController.cs @@ -57,15 +57,15 @@ namespace FormatterWebSite // 'Developer' type is excluded but the shallow validation on the // property Developers should happen [ModelStateValidationFilter] - public IActionResult CreateProject([FromBody] Project project) + public Project CreateProject([FromBody] Project project) { - return Json(project); + return project; } [ModelStateValidationFilter] - public IActionResult CreateSimpleTypePropertiesModel([FromBody] SimpleTypePropertiesModel simpleTypePropertiesModel) + public SimpleTypePropertiesModel CreateSimpleTypePropertiesModel([FromBody] SimpleTypePropertiesModel simpleTypePropertiesModel) { - return Json(simpleTypePropertiesModel); + return simpleTypePropertiesModel; } [HttpPost] diff --git a/src/Mvc/test/WebSites/FormatterWebSite/FormatterWebSite.csproj b/src/Mvc/test/WebSites/FormatterWebSite/FormatterWebSite.csproj index d77acdb16a..c0486a4763 100644 --- a/src/Mvc/test/WebSites/FormatterWebSite/FormatterWebSite.csproj +++ b/src/Mvc/test/WebSites/FormatterWebSite/FormatterWebSite.csproj @@ -8,6 +8,7 @@ + diff --git a/src/Mvc/test/WebSites/FormatterWebSite/Startup.cs b/src/Mvc/test/WebSites/FormatterWebSite/Startup.cs index c1b5895cea..82115f7844 100644 --- a/src/Mvc/test/WebSites/FormatterWebSite/Startup.cs +++ b/src/Mvc/test/WebSites/FormatterWebSite/Startup.cs @@ -19,10 +19,9 @@ namespace FormatterWebSite options.InputFormatters.Add(new StringInputFormatter()); }) + .AddNewtonsoftJson(options => options.SerializerSettings.Converters.Insert(0, new IModelConverter())) .AddXmlDataContractSerializerFormatters() .SetCompatibilityVersion(CompatibilityVersion.Latest); - - services.Configure(options => { options.SerializerSettings.Converters.Insert(0, new IModelConverter()); }); } public void Configure(IApplicationBuilder app) diff --git a/src/Mvc/test/WebSites/FormatterWebSite/StartupWithRespectBrowserAcceptHeader.cs b/src/Mvc/test/WebSites/FormatterWebSite/StartupWithRespectBrowserAcceptHeader.cs index 839e60b1c7..1a31461800 100644 --- a/src/Mvc/test/WebSites/FormatterWebSite/StartupWithRespectBrowserAcceptHeader.cs +++ b/src/Mvc/test/WebSites/FormatterWebSite/StartupWithRespectBrowserAcceptHeader.cs @@ -13,7 +13,8 @@ namespace FormatterWebSite services.AddMvc(options => { options.RespectBrowserAcceptHeader = true; - }); + }) + .AddNewtonsoftJson(); } public void Configure(IApplicationBuilder app) diff --git a/src/Mvc/test/WebSites/HtmlGenerationWebSite/HtmlGenerationWebSite.csproj b/src/Mvc/test/WebSites/HtmlGenerationWebSite/HtmlGenerationWebSite.csproj index 07d3d339b8..6bd3ddd1ae 100644 --- a/src/Mvc/test/WebSites/HtmlGenerationWebSite/HtmlGenerationWebSite.csproj +++ b/src/Mvc/test/WebSites/HtmlGenerationWebSite/HtmlGenerationWebSite.csproj @@ -7,6 +7,7 @@ + diff --git a/src/Mvc/test/WebSites/HtmlGenerationWebSite/Startup.cs b/src/Mvc/test/WebSites/HtmlGenerationWebSite/Startup.cs index 3cf249f37a..3e04fa49f7 100644 --- a/src/Mvc/test/WebSites/HtmlGenerationWebSite/Startup.cs +++ b/src/Mvc/test/WebSites/HtmlGenerationWebSite/Startup.cs @@ -19,6 +19,7 @@ namespace HtmlGenerationWebSite // null which is interpreted as true unless element includes an action attribute. services.AddMvc(ConfigureMvcOptions) .InitializeTagHelper((helper, _) => helper.Antiforgery = false) + .AddNewtonsoftJson() .SetCompatibilityVersion(CompatibilityVersion.Latest); services.AddSingleton(typeof(ISignalTokenProviderService<>), typeof(SignalTokenProviderService<>)); diff --git a/src/Mvc/test/WebSites/RazorPagesWebSite/RazorPagesWebSite.csproj b/src/Mvc/test/WebSites/RazorPagesWebSite/RazorPagesWebSite.csproj index 5b9dfef8cb..b06757396f 100644 --- a/src/Mvc/test/WebSites/RazorPagesWebSite/RazorPagesWebSite.csproj +++ b/src/Mvc/test/WebSites/RazorPagesWebSite/RazorPagesWebSite.csproj @@ -7,6 +7,7 @@ + diff --git a/src/Mvc/test/WebSites/RazorPagesWebSite/Startup.cs b/src/Mvc/test/WebSites/RazorPagesWebSite/Startup.cs index ea3a6bd601..5b6a6c7fec 100644 --- a/src/Mvc/test/WebSites/RazorPagesWebSite/Startup.cs +++ b/src/Mvc/test/WebSites/RazorPagesWebSite/Startup.cs @@ -17,6 +17,7 @@ namespace RazorPagesWebSite services.AddAuthentication(CookieAuthenticationDefaults.AuthenticationScheme).AddCookie(options => options.LoginPath = "/Login"); services.AddMvc() .AddMvcLocalization() + .AddNewtonsoftJson() .AddRazorPagesOptions(options => { options.Conventions.AuthorizePage("/HelloWorldWithAuth"); diff --git a/src/Mvc/test/WebSites/RoutingWebSite/Controllers/RoutingController.cs b/src/Mvc/test/WebSites/RoutingWebSite/Controllers/RoutingController.cs index ba7df5622b..388bba5713 100644 --- a/src/Mvc/test/WebSites/RoutingWebSite/Controllers/RoutingController.cs +++ b/src/Mvc/test/WebSites/RoutingWebSite/Controllers/RoutingController.cs @@ -8,10 +8,10 @@ namespace RoutingWebSite { public class RoutingController : Controller { - public ActionResult HasEndpointMatch() + public bool HasEndpointMatch() { var endpointFeature = HttpContext.Features.Get(); - return Json(endpointFeature?.Endpoint != null); + return endpointFeature?.Endpoint != null; } } } \ No newline at end of file diff --git a/src/Mvc/test/WebSites/RoutingWebSite/RoutingWebSite.csproj b/src/Mvc/test/WebSites/RoutingWebSite/RoutingWebSite.csproj index c75b215a2f..82ef998372 100644 --- a/src/Mvc/test/WebSites/RoutingWebSite/RoutingWebSite.csproj +++ b/src/Mvc/test/WebSites/RoutingWebSite/RoutingWebSite.csproj @@ -11,6 +11,7 @@ + diff --git a/src/Mvc/test/WebSites/RoutingWebSite/Startup.cs b/src/Mvc/test/WebSites/RoutingWebSite/Startup.cs index b113fda2c9..fe1765b123 100644 --- a/src/Mvc/test/WebSites/RoutingWebSite/Startup.cs +++ b/src/Mvc/test/WebSites/RoutingWebSite/Startup.cs @@ -1,14 +1,12 @@ // Copyright (c) .NET Foundation. All rights reserved. // Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information. -using System.Threading.Tasks; using Microsoft.AspNetCore.Builder; using Microsoft.AspNetCore.Http; using Microsoft.AspNetCore.Mvc; using Microsoft.AspNetCore.Mvc.ApplicationModels; using Microsoft.AspNetCore.Mvc.Infrastructure; using Microsoft.AspNetCore.Routing; -using Microsoft.AspNetCore.Routing.Matching; using Microsoft.Extensions.DependencyInjection; namespace RoutingWebSite @@ -22,6 +20,7 @@ namespace RoutingWebSite services .AddMvc(ConfigureMvcOptions) + .AddNewtonsoftJson() .AddRazorPagesOptions(options => { options.Conventions.AddPageRoute("/PageRouteTransformer/PageWithConfiguredRoute", "/PageRouteTransformer/NewConventionRoute/{id?}"); diff --git a/src/Mvc/test/WebSites/RoutingWebSite/StartupForLinkGenerator.cs b/src/Mvc/test/WebSites/RoutingWebSite/StartupForLinkGenerator.cs index 1d8ff727e7..557bc03053 100644 --- a/src/Mvc/test/WebSites/RoutingWebSite/StartupForLinkGenerator.cs +++ b/src/Mvc/test/WebSites/RoutingWebSite/StartupForLinkGenerator.cs @@ -18,6 +18,7 @@ namespace RoutingWebSite services .AddMvc() + .AddNewtonsoftJson() .AddRazorPagesOptions(options => { options.Conventions.AddFolderRouteModelConvention("/PageRouteTransformer", model => diff --git a/src/Mvc/test/WebSites/SimpleWebSite/SimpleWebSite.csproj b/src/Mvc/test/WebSites/SimpleWebSite/SimpleWebSite.csproj index eaa0efc833..8fadc0551a 100644 --- a/src/Mvc/test/WebSites/SimpleWebSite/SimpleWebSite.csproj +++ b/src/Mvc/test/WebSites/SimpleWebSite/SimpleWebSite.csproj @@ -7,6 +7,7 @@ + diff --git a/src/Mvc/test/WebSites/SimpleWebSite/Startup.cs b/src/Mvc/test/WebSites/SimpleWebSite/Startup.cs index a4264f8abb..1757a7adc3 100644 --- a/src/Mvc/test/WebSites/SimpleWebSite/Startup.cs +++ b/src/Mvc/test/WebSites/SimpleWebSite/Startup.cs @@ -20,7 +20,7 @@ namespace SimpleWebSite .AddMvcCore() .AddAuthorization() .AddFormatterMappings(m => m.SetMediaTypeMappingForFormat("js", new MediaTypeHeaderValue("application/json"))) - .AddJsonFormatters(j => j.Formatting = Formatting.Indented) + .AddNewtonsoftJson(options => options.SerializerSettings.Formatting = Formatting.Indented) .SetCompatibilityVersion(CompatibilityVersion.Latest); } diff --git a/src/Mvc/test/WebSites/VersioningWebSite/Controllers/RoutingController.cs b/src/Mvc/test/WebSites/VersioningWebSite/Controllers/RoutingController.cs index 709fb51494..62c6966095 100644 --- a/src/Mvc/test/WebSites/VersioningWebSite/Controllers/RoutingController.cs +++ b/src/Mvc/test/WebSites/VersioningWebSite/Controllers/RoutingController.cs @@ -8,10 +8,10 @@ namespace VersioningWebSite { public class RoutingController : Controller { - public ActionResult HasEndpointMatch() + public bool HasEndpointMatch() { var endpointFeature = HttpContext.Features.Get(); - return Json(endpointFeature?.Endpoint != null); + return endpointFeature?.Endpoint != null; } } } \ No newline at end of file diff --git a/src/Mvc/test/WebSites/VersioningWebSite/Startup.cs b/src/Mvc/test/WebSites/VersioningWebSite/Startup.cs index 4a2b23a9ee..c7031ec301 100644 --- a/src/Mvc/test/WebSites/VersioningWebSite/Startup.cs +++ b/src/Mvc/test/WebSites/VersioningWebSite/Startup.cs @@ -14,6 +14,7 @@ namespace VersioningWebSite { // Add MVC services to the services container services.AddMvc(ConfigureMvcOptions) + .AddNewtonsoftJson() .SetCompatibilityVersion(CompatibilityVersion.Latest); services.AddScoped(); diff --git a/src/Mvc/test/WebSites/VersioningWebSite/VersioningWebSite.csproj b/src/Mvc/test/WebSites/VersioningWebSite/VersioningWebSite.csproj index e2e026a1fb..1197242cd1 100644 --- a/src/Mvc/test/WebSites/VersioningWebSite/VersioningWebSite.csproj +++ b/src/Mvc/test/WebSites/VersioningWebSite/VersioningWebSite.csproj @@ -11,6 +11,7 @@ +