Kit Kit - 1 month ago 8
reST (reStructuredText) Question

Neo4j REST multiple statements request with same query & different paramerters

I use Neo4j Transactional Cypher HTTP endpoint.

http://neo4j.com/docs/developer-manual/3.0/http-api/#rest-api-execute-multiple-statements

I need to do a request with multiple statements where cypher query is the same for all statements, but parameters is different:

{
"statements" : [ {
"statement" : "MATCH path=shortestPath(
(p:Person {idp:123})-[*..10]-(p2:Person {idp:{idp2}}) )
RETURN reduce(x={
last_idp: +head(nodes(path)).idp,
str:"" +head(nodes(path)).idp },
r IN relationships(path) |
{
last_idp: CASE WHEN x.last_idp = startnode(r).idp THEN endnode(r).idp ELSE startnode(r).idp END,
str: CASE WHEN x.last_idp = startnode(r).idp
THEN x.str +"-" +type(r)+"->"+ endnode(r).idp
ELSE x.str +"<-"+type(r)+"-" + startnode(r).idp
END
}
).str AS rpath",

"parameters" : {"idp2": 1234}
}, {
"statement" : "<the same chypher query as above>",
"parameters" : {"idp2": 1234}
}, {
"statement" : "<the same chypher query as above>",
"parameters" : {"idp2": 1235}
},
...
{
"statement" : "<the same chypher query as above>",
"parameters" : {"idp2": 1255}
} ]
}


How can I simplify the request to avoid pointless repetition of the cypher query string?

And I would like to avoid unnecessary costs to parsing & planning the same query.
Is it possible?

Answer

You can just pass all the idp2 parameter values in a single collection, and add an UNWINDclause to the top of your Cypher query. That will cause the query to be executed for each idp2 value.

For example:

{
  "statements" : [ {
    "statement" :
      "UNWIND {idp2s} AS idp2
      MATCH path=shortestPath((p:Person {idp:123})-[*..10]-(p2:Person {idp:idp2})) 
      RETURN reduce(
        x={
          last_idp: +head(nodes(path)).idp,
          str:""    +head(nodes(path)).idp },
        r IN relationships(path)  |
        {
          last_idp: CASE WHEN x.last_idp = startnode(r).idp THEN endnode(r).idp ELSE startnode(r).idp END,
          str: CASE WHEN x.last_idp = startnode(r).idp 
            THEN x.str +"-" +type(r)+"->"+ endnode(r).idp
            ELSE x.str +"<-"+type(r)+"-" + startnode(r).idp 
            END
        }
      ).str AS rpath",

    "parameters" : {"idp2s": [1234,1235,1236,1255]}
  }]
}
Comments