Try our conversational search powered by Generative AI!

Episerver messing up Json serializer settings(?)

Vote:
 

So, we're doing this when the site starts up:

var settings = GlobalConfiguration.Configuration.Formatters.JsonFormatter.SerializerSettings;
settings.ContractResolver = new CamelCasePropertyNamesContractResolver();

Json that we return from different Web APIs is camel cased, as expected.

Then, if an editor enters  "Find" -> "Configure" the Json formatting is set to Pascal Casing for the entire server!
That's not very nice :-) 

(Episerver 11.5.1.0)

#190797
Edited, Apr 17, 2018 9:58
Vote:
 

Someone should do their own formatter picking in their code and not touch the global stuff but I guess it's complex. There are similar issues with routing, authorization and ApiExplorer things.

For now I try to do as many things as possible closer to the code and relying as little as possible on on GlobalConfiguration.

Hopefully Core gives some better support for isolating these things. I'm not so sure though.

#191019
Apr 18, 2018 22:19
Vote:
 

statics/globals are bad :)

#191040
Apr 19, 2018 12:50
Vote:
 

The same thing happend to us after upgrading EPiServer 10.10.0.0 to 11.5.1.0. But it's only present in our test environment, can't reproduce it while in debug. Did you manage to find a solution?

#192122
Edited, May 08, 2018 8:35
Vote:
 

We added a custom attribute to the API controllers we created. The attribute enforces our serializer settings.

public class JsonConfigurationAttribute : Attribute, IControllerConfiguration
    {
        public void Initialize(HttpControllerSettings controllerSettings, HttpControllerDescriptor controllerDescriptor)
        {
            var formatter = controllerSettings.Formatters.OfType<JsonMediaTypeFormatter>().Single();
            controllerSettings.Formatters.Remove(formatter);

            formatter = new JsonMediaTypeFormatter
            {
                SerializerSettings = { ContractResolver = new CamelCasePropertyNamesContractResolver() }
            };

            controllerSettings.Formatters.Add(formatter);            
        }
    }


 

#192131
May 08, 2018 11:34
Vote:
 

Found a similar attribute, which I guess is more specific where as yours is more general;

[AttributeUsage(AttributeTargets.Class)]
    public class UseCamelCasePropertyNamesContractResolverAttribute : Attribute, IControllerConfiguration
    {
        public void Initialize(HttpControllerSettings controllerSettings, HttpControllerDescriptor controllerDescriptor)
        {
            var formatters = controllerSettings.Formatters;
            foreach (var jsonFormatter in formatters.OfType<JsonMediaTypeFormatter>().ToArray())
            {
                var newFormatter = (JsonMediaTypeFormatter)Activator.CreateInstance(jsonFormatter.GetType());
                newFormatter.SerializerSettings.ContractResolver = new CamelCasePropertyNamesContractResolver();

                var jsonFormatterIndex = formatters.IndexOf(jsonFormatter);
                formatters[jsonFormatterIndex] = newFormatter;
            }
        }
    }
#192134
May 08, 2018 11:54
Vote:
 

Erik, I think you can get this stuff done via global action filters - meaning that you don't fall off the track if someone forgot to decorate controller.

#192218
May 10, 2018 22:08
Vote:
 

Michael, I would use the version from Erik in case you don't absolutely definetily need the same Type for the formatter that was originally used as the version you pasted here uses reflection to create the new instance (which performance wise is not as good as using new for the known Type). Just mentioning the performance aspect as usually APIs are performance orientated so depending on how "stessed" your API is it can make a difference to use new vs Activator.CreateInstance.

What about the edge cases, the "unknown" formatter requires properties that you are now not passing in the createinstance call? So should you actually clone the existing formatter (you could serialize the instance with Newtonsoft JSON and then deresialize it back and set the wanted ContractResolver ;D).

#192264
May 13, 2018 11:07
Vote:
 

Yeah I went with Erik's version :) 

#192265
May 13, 2018 11:19
This topic was created over six months ago and has been resolved. If you have a similar question, please create a new topic and refer to this one.
* You are NOT allowed to include any hyperlinks in the post because your account hasn't associated to your company. User profile should be updated.