Is there an equivalent to JsonSchemaResolver.GetSchema when using JSchemaResolver? - c#

I have some older code that use the JsonSchemaResolver class and the GetSchema method, but according to the documentation those are now obsolete. Therefore I want to update my code to use the new API, but I can't seem to find the corresponding way of getting a resolved schema with the JSchemaResolver class.

There isn't really an equivalent method with JSchemaResolver.
While JsonSchemaResolver was just an id/value dictionary of schemas, JSchemaResolver is designed to resolve schemas from external resources. Its main method GetSchemaResource returns a Stream which is then loaded internally.
Something like JsonSchemaResolver was removed because it couldn't handle complex situations like circular schema relationships.

Related

Using Omu.ValueInjecter to map peroperties of different types

We are currently in the process of upgrading one of the parts of our system. We are wanting to run both parts of the system at the same time so we can test that its working correctly.
To Achieve this we are using Omu.ValueInjecter.Map method to convert the old type to the new one. Many of the objects are the same they are just in a different namespace. and Mapper.Map is having difficulty dealing with this. I read on the git page that you can use Mapper.Default map to change the default behaviour of same name, same type using the following code.
Mapper.DefaultMap = (src, resType, tag) =>
{
var res = Activator.CreateInstance(resType);
res.InjectFrom(src);
return res;
};
But this isn't working and I can't find any more information on it to find out how to fix it.
As a temporary fix we have used a json converter to serialize and deserialize the object but it is messy and slow and we want to use Mapper.Map to tidy it up.
the docs in there may not be perfect;
Mapper.Defaultmap is used when you call Mapper.Map for types that don't have a mapping created using Mapper.AddMap
so for similar types (just different namespace) you don't need to do anything, and types that are different you need to call Mapper.AddMap

Define global BeforeMap and AfterMap callbacks for AutoMapper

I know about the feature of defining a Before/AfterMap callback on the map level for a given type pair. However, I'm searching for a solution to define a global Before/AfterMap function somehow, which would apply to every defined type map.
In most of my DTOs I have a mechanism which prevents changed notifications temporarly with the BeginUpdate/EndUpdate pattern. I would like AutoMapper to wrap the mapping between these calls whenever the target type supports it.
I've looked through questions here and the AutoMapper docs but haven't found a native solution.
I think I've found a porposed solution, but haven't tested it completely yet.
After all of my maps are registered, I would do something like this:
var typeMaps = Mapper.GetAllTypeMaps();
foreach (var typeMap in typeMaps)
{
typeMap.AddBeforeMapAction(...);
typeMap.AddAfterMapAction(...);
}

Deserializing JSON object to runtime type in WinRT (C#)

I have a small WinRT client app to my online service (Azure Web Service). The server sends a JSON encoded object with (with potential additional metadata) to the client and the client's responsibility would be to deserialize this data properly into classes and forward it to appropriate handlers.
Currently, the objects received can be deserialized with a simple
TodoItem todo = JsonConvert.DeserializeObject<TodoItem>(message.Content);
However, there can be multiple types of items received. So what I am currently thinking is this:
I include the type info in the header serverside, such as "Content-Object: TodoItem"
I define attributes to TodoItem on the client side (see below)
Upon receiving a message from the server, I find the class using the attribute I defined.
I call the deserialization method with the resolved type
(Example of the attribute mentioned in 2.)
[BackendObjectType="TodoItem"]
public class TodoItem
My problem with this approach however is the Type to Generics in the deserialization as I can't call:
Type t = ResolveType(message);
JsonConvert.DeserializeObject<t>(message.Content);
I tried finding some solutions to this and getting method info for the DeserializeObject and calling it using reflection seemed to be the way to go. However, GetMethod() does not exist in WinRT and I was not able to find an alternative I could use to retrieve the generic version of the DeserializeObject (as fetching by the name gives me the non-generic overload). I don't mind using reflection and GetMethod as I can cache (?) the methods and call them every time a message is received without having to resolve it every time.
So how do I achieve the latter part and/or is there another way to approach this?
Alright, I feel like this was not really a problem at all to begin with as I discovered the DeserializeObject(string, Type, JsonSerializerSettings) overload for the method. It works splendidly. However, I would still like to hear some feedback on the approach. Do you think using attributes as a way to resolve the type names is reasonable or are there better ways? I don't want to use the class names directly though, because I don't want to risk any sort of man-in-the-middle things be able to initialize whatever.
Just a few minutes ago we have posted the alternative way to do what you want. Please look here, if you will have any questions feel free to ask:
Prblem in Deserialization of JSON
Try this
http://json2csharp.com/
Put your Json string here it will generate a class
then
public static T DeserializeFromJson<T>(string json)
{
T deserializedProduct = JsonConvert.DeserializeObject<T>(json);
return deserializedProduct;
}
var container = DeserializeFromJson<ClassName>(JsonString);

Function import that returns object instead of complex type

I'm building dynamic table with stored procedure, so when adding function import, I want it to return object instead of specific type. Is it possible? Thanks
UDPATE
I've tested this and it doesn't work - the call to SqlQuery returns a System.Object. I'll not mark for deletion as it is useful to know that this technique doesn't work.
it should be possible but as #BorisB has said, I'm not sure why you would want to ...
List<dynamic> result = context
.Database
.SqlQuery<dynamic>("select * from ......")
.ToList();
If it were possible what would be the type of that returned object and how would you access its properties?
You'd somehow had to build an EF complex type and a function import at runtime or build a model using ModelBuilder (but you still don't have a data class), which may be possible in theory but it in practice it is way above the problem you are solving.
Maybe it would be better to use ADO.Net directly or modify those SPs to return results as XML which is then consumed by the client (but in XML case you still don't have compiled type of returned objects, so no deserialization, only XPath).

How to design to prompt users for new values for properties of deserialized objects?

Right now, I'm currently serializing a class like this:
class Session
{
String setting1;
String setting2;
...etc... (other member variables)
List<SessionAction> actionsPerformed;
}
Where SessionAction is an interface that just has one method. All implementations of the SessionAction interface have various properties describing what that specific SessionAction does.
Currently, I serialize this to a file which can be loaded again using the default .Net binary serializer. Now, I want to serialize this to a template. This template will just be the List of SessionActions serialized to a file, but upon loading it back into memory at another time, I want some properties of these SessionActions to require input from the user (which I plan to dynamically generate GUI controls on the fly depending on the property type). Right now, I'm stuck on determining the best way to do this.
Is there some way I could flag some properties so that upon using reflection, I could determine which properties need input from user? Or what are my other options? Feel free to leave comments if anything isn't clear.
For info, I don't recommend using BinaryFormatter for anything that you are storing long-term; it is very brittle between versions. It is fine for short-lived messages where you know the same version will be used for serialization and deserialization.
I would recommend any of: XmlSerializer, DataContractSerializer (3.0), or for fast binary, protobuf-net; all of these are contract-based, so much more version tolerant.
Re the question; you could use things like Nullable<T> for value-types, and null for strings etc - and ask for input for those that are null? There are other routes involving things like the ShouldSerialize* pattern, but this might upset the serialization APIs.
If you know from start what properties will have that SessionAction, you must implement IDeserializationCallback and put to those props the attribute [NonSerialized]. When you implement the OnDeserialization method you get the new values from the user.

Categories