How can I check if a path exist or not. I have this query but not success
MATCH path = ((u:User)-[:HAS]->(s:Service)-[:PAID]->(c:Charged))
CALL apoc.case([length(path) = 0, "RETURN 'pending payment'"], "RETURN 'Already paid'") YIELD value
RETURN value
But if I do the same with collect, it works, how is that possible?
MATCH path = ((u:User)-[:HAS]->(s:Service)-[:PAID]->(c:Charged))
with collect(path) as hops
CALL apoc.case([hops = [], "RETURN 'pending payment'"], "RETURN 'Already paid'") YIELD value
RETURN value
MATCH (u:User)-[:HAS]->(s:Service)
WITH u, s
OPTIONAL MATCH p = (s)-[:PAID]->(c:Charged)
RETURN u, s, CASE WHEN length(p) = 0 THEN 'pending payment' ELSE 'Already paid' END
OR
MATCH (u:User)-[:HAS]->(s:Service)
RETURN u, s, CASE WHEN NOT exists((s)-[:PAID]->(:Charged)) THEN 'pending payment' ELSE 'Already paid' END
I am struggling to understand why using WHEN CASE syntax the following expression works
RETURN CASE WHEN length(p) = 0 THEN ...
but when we use the apoc function does not
CALL apoc.case([length(p) = 0, ...
I guess in both cases the output is a boolean but in the second case it throws NULL pointer exception. This is because we cannot use that kind of expression there or it is a wrong usage.
The query would check if the service was paid or not, and the cypher would be the next one:
OPTIONAL MATCH p = (s)-[:PAID]->(c:Charged)
RETURN CASE WHEN length(p) = 0 THEN 'pending payment' ELSE 'Already paid' END
With that condition (length(p)=0), if there is not Charged node, it would jump to the else case because the length(p) is null and the condition wouldn't be true never if we equal 0. In that case, the possible options would be null OR 1. But what we want is that if we do not find the path, return pending payment. So using OPTIONAL MATCH, we should use IS NULL equality to check if path exist or not:
OPTIONAL MATCH p = (s)-[:PAID]->(c:Charged)
RETURN CASE WHEN length(p) IS NULL THEN 'pending payment' ELSE 'Already paid' END
The same with apoc.case function. Instead of equal 0, we can use as above IS NULL
OPTIONAL MATCH p = (s)-[:PAID]->(c:Charged)
CALL apoc.case([length(p) IS NULL, "RETURN 'pending payment'"], "RETURN 'Already paid'") YIELD value
RETURN value
So to recap, we have to use MATCH when we know the path exist and OPTIONAL MATCH when we do not have certainty of the existence
There is nothing wrong. Actually is the function that I will use it but I was curious why it wasn't working the path approach. Also, I want it to have noted that case for the future, if I have the similar problem. No worries, you solved my problem, so thanks for your time!