Search code examples
neo4jneo4j-apoc

neo4j apoc.path.expandConfig - How to use relationshipFilter with a list of relationships


According to the documentations, the pipe char (|) acts as a or in the relationshipFilter, while the comma char (,) acts as a concatenation of relationships, creating a list of them.

see for example (look at the explanation with the black background comparing to the query itself): enter image description here

and:

here, page 14: sequences: enter image description here

The question is, are commas stronger than pipes? i.e., If I want several options of steps sequences, can I specify several strict lists, or do I must specify one list, each step with several options?

I wanted to achieve 4 relationship sequence options:

1.CREATE> or

2.REACT,REPLY or

3.CREATE>,RELATED or

4.REPLY>,CREATE

So I wrote a simple query:

MATCH(u:User{key:1})
CALL apoc.path.expandConfig(u, {maxLevel: 3,
relationshipFilter: 'CREATE>|REACT,REPLY|CREATE>,RELATED|REPLY>,CREATE',
uniqueness:"RELATIONSHIP_GLOBAL"})
YIELD path
RETURN path

Given a sample data:

MERGE (a:User{key: 1})
MERGE (b:Tags{key: 2})
MERGE (c:Post{key: 3})
MERGE (d:Comment{key: 4})
MERGE (e:Comment{key: 5})
MERGE (f:Comment{key: 6})
MERGE (g:User{key: 7})
MERGE (h:User{key: 8})
MERGE (i:Post{key: 9})
MERGE (j:Tags{key: 10})
MERGE (k:Post{key: 11})
MERGE (l:Comment{key: 12})


MERGE (a)-[:CREATE]-(b)
MERGE (a)-[:CREATE]-(c)
MERGE (a)-[:REACT]-(c)
MERGE (a)-[:CREATE]-(d)
MERGE (a)-[:REACT]-(d)
MERGE (b)-[:RELATED]-(c)
MERGE (d)-[:REPLY]-(c)
MERGE (d)-[:REPLY]-(d)
MERGE (h)-[:REACT]-(c)
MERGE (g)-[:REACT]-(c)
MERGE (h)-[:CREATE]-(j)
MERGE (j)-[:RELATED]-(c)
MERGE (g)-[:CREATE]-(i)
MERGE (e)-[:REPLY]-(i)
MERGE (f)-[:REPLY]-(i)
MERGE (a)-[:REPLY]-(i)
MERGE (h)-[:CREATE]-(k)
MERGE (l)-[:REPLY]-(k)
MERGE (a)-[:REACT]-(l)

I was expecting to get an answer including (a:User{key: 1})-[:REPLY]->(i:Post{key: 9})<-[:CREATE]-(g:User{key: 7}), which corresponds with my last part of the relationshipFilter, but did not get it.

Thank you for your time


Solution

  • I believe your relationshipFilter needs to be changed.

    You have written: 'CREATE>|REACT,REPLY|CREATE>,RELATED|REPLY>,CREATE' Which matches:

    1. CREATE> OR REACT
    2. REPLY OR CREATE
    3. RELATED OR REPLY
    4. CREATE (this clause is never checked because of maxLevel:3.)

    It appears you intended to use the relationshipFilter: "CREATE>,REACT|REPLY,CREATE>|RELATED,REPLY>|CREATE"

    Which matches

    1. CREATE>
    2. REACT OR REPLY
    3. CREATE> OR RELATED
    4. REPLY> OR CREATE