cancel
Showing results for 
Search instead for 
Did you mean: 

Head's Up! Site migration is underway. Pause, resolving how to handle anonymous content

Importing nodes and create many-to-many relationships from CSV

alete89
Node Link

Hello everyone . This is my first time trying to deal with this kind of problem on Neo4j and I could use some help either with syntax, how to face the problem or both.

I have a CSV that looks like this:

user,workspace,invitedBy

Alice,Family,Bob
Alice,Business,
Bob,Family,
Charles,Family,Alice
Demian,Family,Alice

(note that invitedBy could be empty)

What I'm looking as result is something like this:
2X_b_b71563d26bae319ca6111a593c5b2320970b9df0.png

What I'v tried to start is importing nodes like this

LOAD CSV FROM 'file:///test.csv' AS line
CREATE (:Member { id: line[0], invitedBy: line[2]})

but as soon as I checked, noticed that nodes were duplicated. So I started investigating MERGE.
I thought I should have lists (arrays) because one Member could had been invited by many people as soon as it was into different workspaces. Then I tried to use some kind of map or dictionary but I'm not finding the way.

Any guidance or advice will be appreciated

1 ACCEPTED SOLUTION

yyyguy
Graph Buddy

Based on what you are trying to accomplish, you might want to think about it differently.

Here is another way to approach it.

Create a User node for all of the users in your data set. Don't separate your Users by InvitedBy node property.
Create a Workspace node for all of the workspaces in your data set.
Use two relationships in your graph. INVITED_BY and BELONGS_TO.

So your graph schema will look something like this.

If you are interested, here are the Cypher scripts that should provide you what you are looking for, or at least provide another perspective.

// Create the User nodes
LOAD CSV WITH HEADERS FROM 'file:///test.csv' AS line
MERGE (m:Member { id: line.user})
;
// Create the Workspace nodes
LOAD CSV WITH HEADERS FROM 'file:///test.csv' AS line
MERGE (w:Workspace { id: line.workspace})
;
// Create the relationships
LOAD CSV WITH HEADERS FROM 'file:///test.csv' AS line
MATCH (m1:Member { id: line.user})
MATCH (m2:Member { id: line.invitedBy})
MATCH (w:Workspace { id: line.workspace})
MERGE (m1)-[:BELONGS_TO]->(w)
MERGE (m1)-[:INVITED_BY]->(m2)
;

-yyyguy

View solution in original post

2 REPLIES 2

yyyguy
Graph Buddy

Based on what you are trying to accomplish, you might want to think about it differently.

Here is another way to approach it.

Create a User node for all of the users in your data set. Don't separate your Users by InvitedBy node property.
Create a Workspace node for all of the workspaces in your data set.
Use two relationships in your graph. INVITED_BY and BELONGS_TO.

So your graph schema will look something like this.

If you are interested, here are the Cypher scripts that should provide you what you are looking for, or at least provide another perspective.

// Create the User nodes
LOAD CSV WITH HEADERS FROM 'file:///test.csv' AS line
MERGE (m:Member { id: line.user})
;
// Create the Workspace nodes
LOAD CSV WITH HEADERS FROM 'file:///test.csv' AS line
MERGE (w:Workspace { id: line.workspace})
;
// Create the relationships
LOAD CSV WITH HEADERS FROM 'file:///test.csv' AS line
MATCH (m1:Member { id: line.user})
MATCH (m2:Member { id: line.invitedBy})
MATCH (w:Workspace { id: line.workspace})
MERGE (m1)-[:BELONGS_TO]->(w)
MERGE (m1)-[:INVITED_BY]->(m2)
;

-yyyguy

alete89
Node Link

MUCH clear that what I was thinking! Thanks for pointing it out.

Thank you for your quick, accurate and clear response. 10/10!