Java调用Neo4j常用方式

本文档详细介绍了如何通过Spring Data Neo4j和Neo4j引擎API进行图数据库操作,包括节点创建、关系建立、查询等。首先,演示了直接使用Neo4j引擎API创建Domain节点,并通过Spring Boot集成Spring Data Neo4j,创建VulEntity和AssetsEntity实体,实现节点和关系的CRUD操作,最后展示了查询节点和自定义Cypher查询的方法。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >



前言

传统数据库难以处理复杂多跳的关系运算。需要一种支持海量、复杂、且结构灵活的关系运算数据库,图数据库应运而生,Neo4j是一个高性能的,NOSQL图形数据库。


1、使用Neo4j引擎包调用Api

1.1 引入Neo4j引擎Jar包


	<dependency>
            <groupId>org.neo4j.driver</groupId>
            <artifactId>neo4j-java-driver</artifactId>
            <version>4.4.5</version>
   </dependency>

1.2 调用Neo4j引擎Api

	public static void main(String[] args) {
	        Driver driver = GraphDatabase.driver("bolt://192.168.104.118:7687", 	AuthTokens.basic("neo4j", "admin123"));
        Session session = driver.session();
        session.run("CREATE (n:Domain {ip: $ip,port: $port})",
                parameters( "ip", "192.168.100.1", "port", "80" ));
        session.run("CREATE (n:Domain {ip: $ip,port: $port})",
                parameters( "ip", "192.168.100.2", "port", "80" ));
        session.run("CREATE (n:Domain {ip: $ip,port: $port})",
                parameters( "ip", "192.168.100.3", "port", "80" ));
        session.run("CREATE (n:Domain {ip: $ip,port: $port})",
                parameters( "ip", "192.168.100.1", "port", "90" ));
        session.run("CREATE (n:Domain {ip: $ip,port: $port})",
                parameters( "ip", "192.168.100.2", "port", "90" ));
        session.run("CREATE (n:Domain {ip: $ip,port: $port})",
                parameters( "ip", "192.168.100.3", "port", "90" ));
        Result result = session.run( "MATCH (n:Domain) WHERE n.ip = $ip " +
                        "RETURN n.ip as ip, n.port as port",
                parameters( "ip", "192.168.100.1"));
        while (result.hasNext()) {
            Record record = result.next();
            System.out.println(record.get("ip") +":"+ record.get("port"));
        }
        session.close();
        driver.close();
    }

代码输出:

"192.168.100.1":"80" 
"192.168.100.1":"90"

查看Neo4j可视化窗口节点显示
在这里插入图片描述


2、使用Spring-Data-Neo4j调用Api

2.1 集成Spring-Data-Neo4j

2.1.1 Maven引入spring-boot-starter-data-neo4j的jar包


	<!-- version需要跟springboot使用同version -->
	<dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-data-neo4j</artifactId>
        <version>${spring-boot.version}</version>
    </dependency>

2.1.2 Spring配置文件添加Neo4j连接配置

spring:
	neo4j:
		authentication:
  			password: admin123
  			username: neo4j
		uri: bolt://192.168.104.118:7687

2.2 创建Neo4jEntity

2.2.1 VulEntity


package com.kg.neo4jEntity;

import lombok.Data;
import org.springframework.data.neo4j.core.schema.Id;
import org.springframework.data.neo4j.core.schema.Node;
import org.springframework.data.neo4j.core.schema.Relationship;

import java.util.List;

@Node("Vul")
@Data
public class VulEntity {

    @Id
    private String code;

    private String name;

    private String cveCode;

    private String level;

    private String dataSourceCode;

    private String type;

    private String source;

    private String cvss;

    private String introduction;

    private String translation;

    private String affectedEntity;

    private String referenceUrl;

    private String patch;

    private String label;

    private String vendor;

    private String poc;

    @Relationship(type = "影响资产", direction = Relationship.Direction.OUTGOING)
    private List<AssetsEntity> assetsEntityList;

}

2.2.2 AssetsEntity

package com.kg.neo4jEntity;

import lombok.Data;
import lombok.NoArgsConstructor;
import org.springframework.data.neo4j.core.schema.Id;
import org.springframework.data.neo4j.core.schema.Node;
import org.springframework.data.neo4j.core.schema.Relationship;

import java.util.List;

@Node("Assets")
@Data
@NoArgsConstructor
public class AssetsEntity {

    @Id
    private String id;

    private String name;

    private String local;

    private String source;

    private String type;

    private String version;

    @Relationship(type = "存在漏洞", direction = Relationship.Direction.OUTGOING)
    private List<VulEntity> vulEntityList;

}

2.2 创建Spring-data-Neo4j的DAO接口

2.2.1 VulRepository


package com.kg.repository;

import com.kg.neo4jEntity.VulEntity;
import org.springframework.data.neo4j.repository.Neo4jRepository;
import org.springframework.stereotype.Repository;

@Repository
public interface VulRepository extends Neo4jRepository<VulEntity,String> {

}

2.2.2 AssetsRepository

package com.kg.repository;

import com.kg.neo4jEntity.AssetsEntity;
import org.springframework.data.neo4j.repository.Neo4jRepository;
import org.springframework.stereotype.Repository;

@Repository
public interface AssetsRepository extends Neo4jRepository<AssetsEntity,String> {

}

2.3 测试

2.3.1 添加vul节点


  @Test
public void saveVulNode() {
    // vul1节点
    VulEntity vulEntity1 = new VulEntity();
    vulEntity1.setCode(UUID.randomUUID().toString());
    vulEntity1.setCveCode("CVE-2022-00002");
    vulEntity1.setCvss("9.1");
    vulEntity1.setIntroduction("添加vul1节点");
    vulEntity1.setLabel("测试节点1");
    vulEntity1 = vulRepository.save(vulEntity1);
    if(vulEntity1 != null){
        System.out.println("vulEntity1---save---success");
    }else{
        System.out.println("vulEntity1---save---fail");
    }
    // vul2节点
    VulEntity vulEntity2 = new VulEntity();
    vulEntity2.setCode(UUID.randomUUID().toString());
    vulEntity2.setCveCode("CVE-2022-00001");
    vulEntity2.setCvss("9.1");
    vulEntity2.setIntroduction("添加vul2节点");
    vulEntity2.setLabel("测试节点2");
    vulEntity2 = vulRepository.save(vulEntity2);
    if(vulEntity2 != null){
        System.out.println("vulEntity2---save---success");
    }else{
        System.out.println("vulEntity2---save---fail");
    }
}

代码输出:vulEntity1—save—success vulEntity2—save—success

查看Neo4j可视化窗口节点显示
在这里插入图片描述

2.3.2 添加assets节点

@Test
    public void saveAssetsNode() {
        AssetsEntity assetsEntity1 = new AssetsEntity();
        assetsEntity1.setId(UUID.randomUUID().toString());
        assetsEntity1.setName("测试资产1");
        assetsEntity1.setSource("CNNVD");
        assetsEntity1 = assetsRepository.save(assetsEntity1);
        if(assetsEntity1 != null){
            System.out.println("assetsEntity1---save---success");
        }else{
            System.out.println("assetsEntity1---save---fail");
        }
        AssetsEntity assetsEntity2 = new AssetsEntity();
        assetsEntity2.setId(UUID.randomUUID().toString());
        assetsEntity2.setName("测试资产2");
        assetsEntity2.setSource("CNNVD");
        assetsEntity2 = assetsRepository.save(assetsEntity2);
        if(assetsEntity2 != null){
            System.out.println("assetsEntity2---save---success");
        }else{
            System.out.println("assetsEntity2---save---fail");
        }
    }

代码输出:assetsEntity1—save—success assetsEntity2—save—success

查看Neo4j可视化窗口节点显示
在这里插入图片描述

2.3.3 添加vul节点与assets节点关系

@Test
public void saveAssetsVul(){
    AssetsEntity assetsEntity = new AssetsEntity();
    assetsEntity.setName("测试资产");
    List<AssetsEntity> assetsEntityList = assetsRepository.findAll(Example.of(assetsEntity, ExampleMatcher.matching().withMatcher(
            "name", ExampleMatcher.GenericPropertyMatchers.contains()
    )));
    VulEntity vulEntity = new VulEntity();
    vulEntity.setLabel("测试节点");
    List<VulEntity> vulEntityList = vulRepository.findAll(Example.of(vulEntity, ExampleMatcher.matching().withMatcher(
            "label", ExampleMatcher.GenericPropertyMatchers.contains()
    )));
    List<VulEntity> finalVulEntityList = vulEntityList;
    assetsEntityList.forEach(assets -> {
        assets.setVulEntityList(finalVulEntityList);
    });
    assetsEntityList = assetsRepository.saveAll(assetsEntityList);
    if(assetsEntityList !=null && assetsEntityList.size() > 0){
        System.out.println("assetsEntityList---saveAll---success");
    }else{
        System.out.println("assetsEntityList---saveAll---fail");
    }
    List<AssetsEntity> finalAssetsEntityList = assetsEntityList;
    vulEntityList.forEach(vul -> {
        vul.setAssetsEntityList(finalAssetsEntityList);
    });
    vulEntityList = vulRepository.saveAll(vulEntityList);
    if(vulEntityList !=null && vulEntityList.size() > 0){
        System.out.println("vulEntityList---saveAll---success");
    }else{
        System.out.println("vulEntityList---saveAll---fail");
    }
}

代码输出:assetsEntityList—saveAll—success,vulEntityList—saveAll—success

查看Neo4j可视化窗口节点显示

关联节点

2.3.4 spring-data-neo4j自带方法查询节点

@Test
public void findNeo4j(){
    //查询全部
    List<VulEntity> vulEntityList = vulRepository.findAll();
    System.out.println("vulEntityList:"+vulEntityList);
    //根据id查询
    Optional<VulEntity> byId = vulRepository.findById("bc5db88c-2f9d-4573-b1d5-5153ba89cbe8");
    System.out.println("byId:"+byId);
    //根据条件查询 需要Example对象,Example对象包含查询条件与对应条件的类型,以下查询条件字段为label,值为"测试节点"
    // ExampleMatcher.GenericPropertyMatchers.contains()代表此字段只需要包含就查出,相当于like
    VulEntity vulEntity = new VulEntity();
    vulEntity.setLabel("测试节点");
    List<VulEntity> vulEntityListByLabel = vulRepository.findAll(Example.of(vulEntity, ExampleMatcher.matching().withMatcher(
            "label", ExampleMatcher.GenericPropertyMatchers.contains()
    )));
    System.out.println("vulEntityListByLabel:"+vulEntityListByLabel);
}

代码输出:

vulEntityList:[VulEntity(code=bc5db88c-2f9d-4573-b1d5-5153ba89cbe8, name=null, cveCode=CVE-2022-00002, level=null, dataSourceCode=null, type=null, source=null, cvss=9.1, introduction=添加vul1节点, translation=null, affectedEntity=null, referenceUrl=null, patch=null, label=测试节点1, vendor=null, poc=null), VulEntity(code=2db9025e-c649-42fe-a7d0-e2d21d103878, name=null, cveCode=CVE-2022-00001, level=null, dataSourceCode=null, type=null, source=null, cvss=9.1, introduction=添加vul2节点, translation=null, affectedEntity=null, referenceUrl=null, patch=null, label=测试节点2, vendor=null, poc=null)]
byId:Optional[VulEntity(code=bc5db88c-2f9d-4573-b1d5-5153ba89cbe8, name=null, cveCode=CVE-2022-00002, level=null, dataSourceCode=null, type=null, source=null, cvss=9.1, introduction=添加vul1节点, translation=null, affectedEntity=null, referenceUrl=null, patch=null, label=测试节点1, vendor=null, poc=null)]
vulEntityListByLabel:[VulEntity(code=bc5db88c-2f9d-4573-b1d5-5153ba89cbe8, name=null, cveCode=CVE-2022-00002, level=null, dataSourceCode=null, type=null, source=null, cvss=9.1, introduction=添加vul1节点, translation=null, affectedEntity=null, referenceUrl=null, patch=null, label=测试节点1, vendor=null, poc=null), VulEntity(code=2db9025e-c649-42fe-a7d0-e2d21d103878, name=null, cveCode=CVE-2022-00001, level=null, dataSourceCode=null, type=null, source=null, cvss=9.1, introduction=添加vul2节点, translation=null, affectedEntity=null, referenceUrl=null, patch=null, label=测试节点2, vendor=null, poc=null)]

2.3.5 使用cypher语法查询

2.3.5.1 自定义cql
package com.kg.repository;

import com.kg.neo4jEntity.VulEntity;
import org.springframework.data.neo4j.repository.Neo4jRepository;
import org.springframework.data.neo4j.repository.query.Query;
import org.springframework.data.repository.query.Param;
import org.springframework.stereotype.Repository;

import java.util.List;

@Repository
public interface VulRepository extends Neo4jRepository<VulEntity,String> {

    @Query("MATCH (n:Vul) where n.label contains $label RETURN n")
    List<VulEntity> getVulEntityByLabel(@Param("label") String label);

}
2.3.5.2 测试
@Test
public void queryNeo4j(){
    List<VulEntity> vulEntityListByLabel = vulRepository.getVulEntityByLabel("测试节点");
    System.out.println("vulEntityListByLabel:"+vulEntityListByLabel);
}

代码输出:

vulEntityListByLabel:[VulEntity(code=bc5db88c-2f9d-4573-b1d5-5153ba89cbe8, name=null, cveCode=CVE-2022-00002, level=null, dataSourceCode=null, type=null, source=null, cvss=9.1, introduction=添加vul1节点, translation=null, affectedEntity=null, referenceUrl=null, patch=null, label=测试节点1, vendor=null, poc=null), VulEntity(code=2db9025e-c649-42fe-a7d0-e2d21d103878, name=null, cveCode=CVE-2022-00001, level=null, dataSourceCode=null, type=null, source=null, cvss=9.1, introduction=添加vul2节点, translation=null, affectedEntity=null, referenceUrl=null, patch=null, label=测试节点2, vendor=null, poc=null)]
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值