Unable to create an index with parent child relationship using .net NEST


#1

I m trying to run the following code in .net

var descriptor = new CreateIndexDescriptor("raja")
.Mappings(ms => ms
.Map("employee", m => m.AutoMap())
.Map("employeeskillset", m => m.AutoMap().Parent()));

client.CreateIndex(descriptor);

I m not getting any errors but i m not getting my index created with Skill and Employee classes


(Russ Cam) #2

What version of NEST are you using, and what version of Elasticsearch are you targeting?


#3

@forloop I m using NEST 6.0.0-rc1, elastic search 6.0.0 version targeting .net framework 4..6.1

I also tried the same with NEST 5.5.0


(Russ Cam) #4

Parent/Child relationship mapping has changed quite a bit in Elasticsearch 6.0 with the removal of types.

Did you see the documentation for NEST 6.x on Parent/Child relationships?


#5

@forloop Sorry, I didn't notice this. I m going through that now.
Thanks for your quick reply


#6

@forloop
Hey..
Though I am following the documentation, i m getting errors still
I m trying to create index and insert data

But hanging with errors like
"Inferrer does not contain a definition for Routing and no extension method Routing....."
"String does not contain a definition for Should and no extension method Should..."

Is there any specific version of Nest Nuget package to be used with elastic 6.0.0??


(Russ Cam) #7

Take a look at my answer on Parent/Child relationship with NEST on 6.x.

The documentation contains test constructs to assert correct behaviour, because the documentation is generated from tests, to ensure it stays in sync with the source code.


#8

@forloop
Followed that link with your answer. Still not able to have my documents indexed. You can see empty index created without any parent child documents in the attached screenshot


(Russ Cam) #9

Can you provide a small, succinct, code example that reproduces your problem?


#10

@forloop
My POCO classes as follows(Similar to the the classes in documentation)
public abstract class Document
{
public int Id { get; set; }
public JoinField join { get; set; }
}
public class Employee:Document
{
public string firstName { get; set; }
public string lastName { get; set; }
[Completion]
public string designation { get; set; }

}

public class Skill:Document
{
[Completion]
public string skillName { get; set; }
}

Mapping and Indexing stuff here..............
var node = new Uri("http://localhost:9200");
var settings = new ConnectionSettings(node);
settings.DefaultIndex(IndexName);
settings.InferMappingFor(m => m.IndexName("myindex").TypeName("document"))
.InferMappingFor(m => m.IndexName("myindex").TypeName("document"))
.InferMappingFor(m => m.IndexName("myindex").TypeName("document").RelationName("parent"));

var createIndexResponse = client.CreateIndex("myindex", c => c
.Index()
.Mappings(ms => ms
.Map("document",m => m
.RoutingField(r => r.Required())
.AutoMap()
.AutoMap()
.Properties(props => props
.Join(j => j.Name(p => p.join).Relations(r => r.Join<Employee, Skill>()))))));
var parent = new Employee { Id = 1337, firstName = "ABCD", lastName = "XYZ", designation = "Developer", join = JoinField.Root() };
var indexParentResponse = client.IndexDocument(parent);
var child = new Skill { Name="C#", join = JoinField.Link(1337) };
var indexChildResponse = client.IndexDocument(child);


(Russ Cam) #11

Can you please format your code using </> or enclosing in ``` blocks


#12

@forloop
My POCO classes as follows(Similar to the the classes in documentation)

    public abstract class Document
    {
    public int Id { get; set; }
    public JoinField join { get; set; }
    }
    public class Employee:Document
    {
    public string firstName { get; set; }
    public string lastName { get; set; }
    [Completion]
    public string designation { get; set; }

    }
    public class Skill:Document
    {
    [Completion]
    public string skillName { get; set; }
    }

Mapping and Indexing stuff here..............

    var node = new Uri("http://localhost:9200");
    var settings = new ConnectionSettings(node);
    settings.DefaultIndex(IndexName);
    settings.InferMappingFor(m => m.IndexName("myindex").TypeName("document"))
    .InferMappingFor(m => m.IndexName("myindex").TypeName("document"))
    .InferMappingFor(m => m.IndexName("myindex").TypeName("document").RelationName("parent"));

    var createIndexResponse = client.CreateIndex("myindex", c => c
    .Index()
    .Mappings(ms => ms
    .Map("document",m => m
    .RoutingField(r => r.Required())
    .AutoMap()
    .AutoMap()
    .Properties(props => props
    .Join(j => j.Name(p => p.join).Relations(r => r.Join<Employee, Skill>()))))));
    var parent = new Employee { Id = 1337, firstName = "ABCD", lastName = "XYZ", designation = "Developer", join = JoinField.Root() };
    var indexParentResponse = client.IndexDocument(parent);
    var child = new Skill { skillName="C#", join = JoinField.Link(1337) };
    var indexChildResponse = client.IndexDocument(child);

#13

@forloop

Did you got time to look into this?


#14

This is the error i m getting while indexing documents(either child or parent documents)
# Response:
{"error":{"root_cause":[{"type":"routing_missing_exception","reason":"routing is required for
[myindex]/[document]/[1337]","index_uuid":"na","index":"myindex"}],"type":"routing_missing_exception","reason":"routing is required for [myindex]/[document]/[1337]","index_uuid":"na","index":"myindex"},"status":400}


(Russ Cam) #15

The error message indicates that the _routing parameter is missing when indexing the parent document. The formatting of your code is missing the generic type parameters, which would be useful to also see.

Can you show what the index mapping looks like in Elasticsearch for "myindex", and what the requests to Elasticsearch look like?


#16

@forloop
Hey, i have fixed this by adding "i => i.Routing("parent")" while indexing the documents (as shown in below code) I was able to create parent and child documents
var createIndexResponse = client.CreateIndex("myindex", c => c
.Index()
.Mappings(ms => ms
.Map("document", m => m
.RoutingField(r => r.Required())
.AutoMap()
.AutoMap()
.Properties(props => props
.Join(j => j
.Name(p => p.join)
.Relations(r => r
.Join<Employee, Skill>()
)
)
)
)
)
);
var infer = client.Infer;

	//creating developer parent document
        var devparent = new Employee { Id = "1337", firstName = "ABCD", lastName = "XYZ", designation = "Developer", join = JoinField.Root<Employee>() };
        infer.RelationName<Employee>();
        infer.RelationName("parent");
        //creating child documents (skillsets of developer) of devparent 
        var devchild1 = new Skill { Id = "1", Name ="Javascript", join = JoinField.Link<Skill>(1337) };
        var devchild2 = new Skill { Id = "2", Name = "Java", join = JoinField.Link<Skill>(1337) };
	//creating tester parent document
        var testparent = new Employee { Id = "1338", firstName = "FGHI", lastName = "PRS", designation = "Tester", join = JoinField.Root<Employee>() };
	//creating child documents (skillsets of tester) of testparent
        
        var testchild1 = new Skill { Id = "11", Name = "Jmeter", join = JoinField.Link<Skill>(1338) };
        var testchild2 = new Skill { Id = "12", Name = "Jira", join = JoinField.Link<Skill>(1338) };
	//indexing parent documents
        var indexdevParent = client.Index<Document>(devparent, i => i.Routing("parent"));
    var indextestParent = client.Index<Document>(testparent,i => i.Routing("parent")); 	
	//indexing child documents of developer parent
        var devindexChild1= client.Index<Document>(devchild1,  i => i.Routing("child"));
        var devindexChild2 = client.Index<Document>(devchild2, i => i.Routing("child"));
	//indexing child documents of tester parent
        var testindexChild1 = client.Index<Document>(testchild1 , i => i.Routing("child"));
        var testindexChild2 = client.Index<Document>(testchild2 , i => i.Routing("child"));

but strucked at some other point.. Here i need to search skillsets specific to either developer or tester by using autocomplete when i type a letter in textbox. Say for example of typing J for developer i should only get Java and Javascipt but not JIRA or Jmeter. For this i m trying on seein g this link https://www.elastic.co/guide/en/elasticsearch/client/net-api/current/has-parent-query-usage.html .. But no luck. Any help would be appreciated


(system) #17

This topic was automatically closed 28 days after the last reply. New replies are no longer allowed.