2
votes

I am building an app that give users the ability to construct there own graphs. I have been using parameters for all queries and creates. But when I want to give users the ability to create a node where they can also Label it anything they want(respecting neo4j restrictions on empty string labels). How would I parameterize this type of transaction?

I tried this:

.CREATE("(a:{dynamicLabel})").WithParams(new {dynamicLabel = dlabel})... 

But this yields a syntax error with neo. I am tempted to concatenate, but am worried that this may expose an injection risk to my application.

I am tempted to build up my-own class that reads the intended string and rejects any type of neo syntax, but this would limit my users a bit and I would rather not.

3

3 Answers

1
votes

There is an open neo4j issue 4334, which is a feature request for adding the ability to parameterize labels during CREATE.So, this is not yet possible.

That issue contains a comment that suggests generating CREATE statements with hardcoded labels, which will work. It is, unfortunately, not as performant as using parameters (should it ever be supported in this case).

0
votes

If you are using a Java client, then you can do it like this.

        Node node = GraphDatabaseService.createNode();

        Label label = new Label() {                 
            @Override
            public String name() {
                return dynamicLabelVal;
            }
        };

        node.addLabel(label);

You can then have a LabelCache which will avoid Label object creation for every node.

0
votes

I searched like hell and finally found it out. you can do it like that:

// create or update nodes with dynamic label from import data
WITH "file:///query.json" AS url
call apoc.load.json(url) YIELD value as u
UNWIND u.cis as ci
CALL apoc.merge.node([ ci.label ], {Id:ci.Id}, {}, {}) YIELD node
RETURN node;

The JSON looks like that:

{
   "cis": [
     {
       "label": "Computer",
       "Id": "1"
     },
     {
       "label": "Service",
       "Id": "2"
     },
     {
       "label": "Person",
       "Id": "3"
     }
   ],
   "relations": [
     {
       "end1Id": "1",
       "Id": "4",
       "end2Id": "2",
       "label": "USES"
     },
     {
       "end1Id": "3",
       "Id": "5",
       "end2Id": "1",
       "label": "MANAGED_BY"
     }
   ]
 }