Giter Club home page Giter Club logo

Comments (9)

manuc66 avatar manuc66 commented on May 18, 2024

Hi, I agree that it might be better to do the mapping on the child instead of the parent.

In branch feature/base-without-useless-property I have support for the case you're exposing (having no possibility to add attributes on the parent)

JsonConvert.DefaultSettings = () => new JsonSerializerSettings();
var settings = JsonConvert.DefaultSettings();
settings.Converters.Add(JsonSubtypesConverterBuilder
  .Of(typeof(IAnimal), "Breed")
  .RegisterSubtype(typeof(Dog), "Dog")
  .RegisterSubtype(typeof(Cat), "Cat")
  .Build());

IAnimal animal = new Dog();

var json = JsonConvert.SerializeObject(animal, settings);
JsonConvert.DeserializeObject<IExpression2>(json, settings);

But it have situations where I did not managed yet to fix some edge cases, so it's not released yet.

from jsonsubtypes.

manuc66 avatar manuc66 commented on May 18, 2024

If JsonSubTypes uses TypeDescriptor.GetAttributes instead of Type.GetCustomAttributes something like this could have been implemented easily:

[JsonConverter(typeof(JsonSubtypes), "Breed")]
public interface IAnimal
{
    string Breed {get;set;}
}

The concrete type whitout attributes:

public class Dog : IAnimal
{
   public string Breed {get;set;} = "Dog";
   public bool HasChip {get;set;}
}

public class Cat : IAnimal
{
   public string Breed {get;set;} = "Cat";
   public bool HasClaws {get;set;}
}
// the mapping setup
TypeDescriptor.AddAttributes(typeof(IAnimal),
  new JsonSubtypes.KnownSubTypeAttribute(typeof(Cat), "cat"),
  new JsonSubtypes.KnownSubTypeAttribute(typeof(Dog), "dog"));

var json = "{\"catLives\":6,\"@type\":\"cat\",\"age\":11}";

var result = JsonConvert.DeserializeObject<Animal>(json);

Assert.AreEqual(typeof(Cat), result.GetType());
Assert.AreEqual(11, result.Age);
Assert.AreEqual(6, (result as Cat)?.Lives);

But TypeDescriptor.GetAttribute(...) is not available for at least netstandard1.3 and netstandard1.4

from jsonsubtypes.

ravensorb avatar ravensorb commented on May 18, 2024

They both are great ideas. How close is the 1st option? If is good enough to test for the standard use cases (maybe just part it as experimental and release it?)

from jsonsubtypes.

manuc66 avatar manuc66 commented on May 18, 2024

The 1st option is now released in v1.3.0 with #28

from jsonsubtypes.

ravensorb avatar ravensorb commented on May 18, 2024

I think I found an issue with #28 - if the interface and the concrete class is in different assemblies there is an issue in creating the concrete instance. I think the issue is when the interface and class are in different name space. It looks like their is an assumption in the code that the namespace for the interface is used to build the namespace for the class.

from jsonsubtypes.

manuc66 avatar manuc66 commented on May 18, 2024

@ravensorb I tried to reproduce the issue you described but did not managed (see: https://github.com/manuc66/JsonSubTypes/tree/bugfix/try-to-reproduce-bug). Can you provide some sample code and open an new issue with it?

Thanks

from jsonsubtypes.

ravensorb avatar ravensorb commented on May 18, 2024

So I tracked it down -- it looks like the code assumes that everything is in a single assembly (interface and classes). For my scenario I have the interface in one assembly and the concrete classes spread out over several other assemblies.

To repro create 3 assemblies

  • MainApp
  • Interface
  • Implementation

This will show the issue. Now the hard part is, I am not sure what the solution might be as you are supporting a lot of the legacy frameworks via PCL (I think) and up until the latest version AppDomain is not usable which makes getting a list of all loaded assemblies a bit tricky from what I can remember.

from jsonsubtypes.

manuc66 avatar manuc66 commented on May 18, 2024

When dynamic registration is used (which has been introduced with #28) the sub type should be is taken from the registration and not from the parent type assembly.

With #28 the method GetSubTypeMapping is overrided and then should provides some values so it did not fall in the GetTypeByName (which build the subtype from the assemble of the parent, but not in this case).

from jsonsubtypes.

ravensorb avatar ravensorb commented on May 18, 2024

issue with that is, it assumes that everything is loaded immediately and that is not always the case when you have things handled via DI

from jsonsubtypes.

Related Issues (20)

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.