Question

I'm new to ElasticSearch and trying to use it on my C# application with Nest. I have a class which holds a list of a base type with classes which inherit from it:

public class Automobile
{
    public string ModelName { get; set; }
    public double EngineSize { get; set; }
}

public class Truck : Automobile
{
    public double CarryWeight { get; set; }
}

public class Car : Automobile
{
    public short SaftyStars { get; set; }
}

public class MotorCycle : Automobile
{
    public double DecibleNoise { get; set; }
}

public class AutoDealerShip
{
    public string Name { get; set; }
    [ElasticProperty(Type = FieldType.nested)]
    public IList<Automobile> Models { get; set; }

    public AutoDealerShip()
    {
        Models = new List<Automobile>();
    }
}

I'm trying to map the class so that the actual objects would be saved:

ElasticClient.MapFluent<AutoDealerShip>(m => m.MapFromAttributes().
                                             Properties(prop => prop.
                                             NestedObject<Automobile>(n => n.
                                                 Name(p => p.
                                                 Models.First()).
                                                      MapFromAttributes().
                                                      Dynamic())));

When trying to index data and retrieve it:

private static void IndexPolymorphicObject()
{
    ElasticClient.DeleteIndex(PersonIndex);

    var dealerShip = new AutoDealerShip();
    dealerShip.Name = "Mikes dealership";
    dealerShip.Models.Add(new Truck());
    dealerShip.Models.Add(new Car());
    dealerShip.Models.Add(new MotorCycle());
    ElasticClient.Index(dealerShip);
    ElasticClient.Flush();
}

private static void GetPolyMorphicData()
{
    var result = ElasticClient.Search<AutoDealerShip>(srch => srch.
                                               Query(q => q.MatchAll()));
    var dealerShip = result.Documents.First();
    foreach (var automobile in dealerShip.Models)
    {
        Console.WriteLine("Automobile of type {0}",automobile.GetType());
    }
}

I keep getting back objects of type AutoMobile. Is there a way to store polymorphic data using nest?

Thanks,

Izhar

Was it helpful?

Solution

NEST by default has great support for contravariant results of the documents you store

So if you do

Index<B>()

Index<C>()

Index<D>()

And then do a search for Search<A>(s=>s.Types(B,C,D)) given that all of them derive from A you will get an IEnumerable result with actual instances of B, C and D inside of it.

To get contra/covariance going inside your own document you'll have to do the wiring yourself.

You will have to register a custom jsonconverter on the property to make sure JSON.net deserializes the json back to the actual subtype instead of the supper.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top