从Java执行对neo4j数据库的查询,解析结果

时间:2017-06-08 16:00:51

标签: java neo4j cypher

我通过GraphDatabaseService访问neo4j数据库。我添加了一些节点和关系,并希望进行查询。我的目标是让所有与endnode具有Calling关系的节点。所以我有这个节点的全部路径。 (例如:node1 -calling-> node2 -calling * - > nodeX -calling-> endnode)

我试过这样的事情:

GraphDatabaseService _graphDatabase; // db is running and working fine
Node node;//given by the function call

HashMap<String, Object> properties = Maps.newHashMap();
properties.put("name", getPropertyFromNode(node, "name"));
String query = "MATCH p=(startnode)-[rel:CALLING*]->(endnode) WHERE endnode.name = {name} RETURN p";

Result result = _graphDatabase.execute(query, properties);
while (result.hasNext()) {
    Map<String, Object> next = result.next();
    next.forEach((k, v) -> {
        System.out.println(k + " : " + v.toString());
        if (v instanceof PathImpl) {
            PathImpl pathImpl = (PathImpl) v;
            String startNodeName = getPropertyFromNode(pathImpl.startNode(), "name");
            String endNodeName = getPropertyFromNode(pathImpl.endNode(), "name");
            System.out.println(startNodeName + " -calling-> " + endNodeName);
        }
    });
}

public String getPropertyFromNode(Node node, String propertyName) {
    String result = null;
    try (Transaction transaction = _graphDatabase.beginTx()) {
        result =node.getProperty(propertyName).toString();
        transaction.success();
    }
    return result;
}

问题在于,结果是Map&lt;'String,Object&gt;,我想要获取关系中节点的id或名称。我试图将Object转换为PathImpl,因为这是返回的类型(通过调试计算出来),但它接口就像这个类在不同的类加载器中,因此语句instanceof返回false。 v.toString()返回id为的喜欢节点的String表示形式(例如:p:(24929) - [CALLING,108061] - &gt;(24930))

我的问题是,我能以更好的方式访问这些信息,或者我如何更改classLoader(如果这是问题,我正在gradle项目中使用eclipse)来进行转换。 我不想解析String以获取id并通过该属性从db获取节点,它的接缝对我来说很难看。

2 个答案:

答案 0 :(得分:1)

如果要获取起始节点和结束节点的名称,则应修改Cypher代码以返回它们(而不是路径),这将大大简化从响应中提取数据所需的代码。例如:

MATCH p=(startnode)-[rel:CALLING*]->(endnode)
WHERE endnode.name = {name}
RETURN startnode.name AS s_name, endnode.name AS e_name, p;

答案 1 :(得分:0)

在尝试使用cybersam的有效答案来更改密码查询后,我发现了另一种不改变查询的方式,更适合我的目标。 对我来说,目标是获得整个路径不仅是链接节点的名称/ ID。该信息正是我想要的参数'p'(参见查询),但我无法转换该类型。 原因是Neo4j正在使用PathImpl的内部实现。 为了使我的解决方案在问题工作中,我必须使用Path而不是PathImpl,所以我不必导入实习生类型。所以我改变了进口:

import org.neo4j.graphalgo.impl.util.PathImpl;

import org.neo4j.graphdb.Path;

并测试Path而不是PathImpl。

if (v instanceof Path) {
    Path path = (Path) v;
    Iterable<Node> nodes = path.nodes();
    nodes.forEach(n -> System.out.println(n.toString()));
}

现在我可以访问整个路径了。希望这也能帮助其他人。