如何通过neo4j REST API正确地创build数千个cypher节点?

我需要在cypher <3.0.0中通过node.js创build很多节点(比如50.000)。 我正在使用async.times发布所有密码查询。 不过看起来REST API正在崩溃(并死亡),因为可能有太多的请求通过。 我想继续使用节点,而不是使用LOAD CSV。 我的代码如下:

var createStyles = function (data, cb) { var distinctData = ...; console.log("creating styles"); ... var create = function (id, callback) { console.log("creating st " + id); var req = ... styles.addOrUpdate(req, null, function (err, node) { callback(null, node); }); } // call the same function multiple times with a different index async.times(distinctData.length - 1, function (n, next) { create(n, function (err, st) { next(err, st) }) }, function (err, result) { console.log("styles created"); createdStyles = result; cb(null, result); }); }; 

addOrUpdate函数如下所示:

 exports.addOrUpdate = function (req, res, cb) { if (req.body.styleName === undefined) req.body.styleName = "N/A"; if (req.body.description === undefined) req.body.description = ""; if (req.body.price === undefined) req.body.price = 0; var styleName = req.body.styleName.replace(/\\/g,"\\\\").replace(/'/g, "\\'"); var styleNum = req.body.styleNum.toString().replace(/'/g, "").replace(/\\/g,""); var desc = req.body.description.replace(/'/g, "").replace(/\\/g,""); var dts = dateHelper.getDTS(); var styleID = uuid.v4(); if (req.body.styleID !== undefined && req.body.styleID != "") styleID = req.body.styleID; var query = "" + " MATCH (c:Customer {customerID: '" + req.body.customerID + "'}) " + " MATCH (c)<-[r:DEPT_OF]-(dept:Dept {deptID: '" + req.body.departmentID + "'}) " + " MATCH (dept)<-[r1:IN_DEPT]-(pt:ProductType {productTypeID: '" + req.body.productTypeID + "'}) " + " MERGE (st:Style {styleNum: '" + styleNum + "'}) " + " ON MATCH " + " SET " + " st.styleNum = '" + styleNum + "', " + " st.name = '" + styleName + "', " + " st.desc = '" + desc + "', " + " st.price = " + req.body.price + ", " + " st.modifiedDTS = " + dts + " ON CREATE " + " SET " + " st.styleID = '" + styleID + "', " + " st.styleNum = '" + styleNum + "', " + " st.name = '" + styleName + "', " + " st.desc = '" + desc + "', " + " st.price = " + req.body.price + ", " + " st.modifiedDTS = " + dts + ", " + " st.createdDTS = " + dts + " " + " WITH pt, st " + " MERGE (pt)<-[r2:OF_TYPE]-(st) " + " return st;"; console.log(query); db.cypherQuery(query, function (err, node) { if (err) { return cb(err, node); } else { cb(err, node.data[0]); } }); }; 

有没有什么我可以做到这一点,而不窒息neo4j?

  1. 使用参数
  2. 使用async.series
  3. 你为什么要做MATCH SET?
  4. 确保你有所有的索引/ constrraints(例如客户{customerID})
  5. Neo4j <3.0使用RULE规划器进行更新,这在复杂的更新查询中可能performance不佳,

所以你可以将你的查询拆分成一个匹配的查询,然后只返回id的pt ,然后把它传递给更新查询,这个查询做了合并和产品types的by-id查询

  1. 使用PROFILE / EXPLAIN与您的查询,看看他们是否确实执行高并发负载
  2. 考虑批量查询,例如在一次交易中更新10k到100k