行百里er 行百里er
首页
  • 分类
  • 标签
  • 归档
设计模式
  • JVM
  • Java基础
MySQL
Elastic Stack
Redis
  • Kafka
  • RocketMQ
分布式
Spring Cloud Alibaba
云原生
数据结构与算法
关于
GitHub (opens new window)

行百里er

Java程序员一枚
首页
  • 分类
  • 标签
  • 归档
设计模式
  • JVM
  • Java基础
MySQL
Elastic Stack
Redis
  • Kafka
  • RocketMQ
分布式
Spring Cloud Alibaba
云原生
数据结构与算法
关于
GitHub (opens new window)
  • Elasticsearch初体验-第一次使用就感觉他很勇,搜索界的扛把子!
  • 近距离感受一下Elasticsearch的CRUD:ES Java API之增删改查
    • Transport Client
      • 引入jar包
      • 创建到ES的连接
      • Index API
      • 生成JSON文档
      • 增删改查API
      • Create 创建索引、文档相关API
      • GET API 查询单个、所有文档相关API
      • Update API
      • Delete API
  • 这些 Elasticsearch 7 部署的问题,你遇到过吗
  • 10分钟部署一个ELK日志采集系统
  • 比快更快的 ELK 8 安装使用指南-Elasticsearch,Kibana,Logstash
  • Elastic Stack
行百里er
2020-08-23
目录

近距离感受一下Elasticsearch的CRUD:ES Java API之增删改查

作者:行百里er

博客:https://chendapeng.cn (opens new window)

提示

这里是 行百里er 的博客:行百里者半九十,凡事善始善终,吾将上下而求索!

在基本了解并在Kibana Dev Tools控制台操作Elasticsearch的查询语法之后,是时候在实际应用中使用ES了。那么怎么在Java中使用ES呢?

可以有下面几种方式来实现:

  • Transport Client
  • Java High Level REST Client
  • Spring Data Elasticsearch

TransportClient可用于老版本的Elasticsearch;新版本建议使用Java High Level REST Client(向下兼容);当然还可以使用Spring Data提供的Spring Data Elasticsearch。

本文先只介绍一下Transport ClientAPI,后面慢慢来REST Client和Spring Data Elasticsearch。

# Transport Client

注意:在7.0.0中弃用。不推荐使用TransportClient,而推荐使用Java High Level REST Client,并将在Elasticsearch 8.0中将其删除。

Elasticsearch 8.x版本将会删除TransportClient。这里为什么还要介绍一下它的API呢?毕竟有些老铁用的还是以前的版本,而且API很多地方是相通的,那就多学习一点吧!

# 引入jar包

<dependency>
    <groupId>org.elasticsearch.client</groupId>
    <artifactId>transport</artifactId>
    <version>7.9.0</version>
</dependency>
1
2
3
4
5

注意版本号,一定要和你安装的Elasticsearch的版本号一致。

# 创建到ES的连接

必须得先连接到ES才能进行一系列的API测试,连接的代码如下:

// 创建连接
TransportClient client = new PreBuiltTransportClient(Settings.EMPTY)
        .addTransportAddress(
                new TransportAddress(
                        InetAddress.getByName("localhost"), 9300));
//一系列操作...

//关闭连接
client.close();
1
2
3
4
5
6
7
8
9

image.png

可以看到,TransportClient 是deprecated,弃用了,我用的是ES 7.9版本,它在7.0.0中被弃用。

注意:

  1. InetAddress.getByName("localhost"), 9300) 这里绑定的端口 9300 是通讯端口,不是服务端口(服务端口是9200)
  2. 如果使用与 Elasticsearch 不同的集群名称,则必须设置集群名称:
Settings settings = Settings.builder()
        .put("cluster.name", "myClusterName").build();
TransportClient client = new PreBuiltTransportClient(settings);

//Add transport addresses and do something with the client...
1
2
3
4
5

比如我的:

image.png

单节点ES默认的集群名称就是 elasticsearch 。

# Index API

索引API允许将输入的JSON文档索引到特定索引中并使之可搜索。

# 生成JSON文档

生成JSON文档有很多种方法,比如:

  • 手动构造
String json = "{" +
    "\"user\":\"kimchy\"," +
    "\"postDate\":\"2013-01-30\"," +
    "\"message\":\"trying out Elasticsearch\"" +
"}";
1
2
3
4
5
  • 使用Map
Map<String, Object> json = new HashMap<String, Object>();
json.put("user","kimchy");
json.put("postDate",new Date());
json.put("message","trying out Elasticsearch");
1
2
3
4

Map是一个key:values对集合。它可以表示一个JSON结构。

  • Jackson

可以使用Jackson将bean序列化为JSON。

import com.fasterxml.jackson.databind.*;

// instance a json mapper
ObjectMapper mapper = new ObjectMapper(); // create once, reuse

// generate json
byte[] json = mapper.writeValueAsBytes(yourbeaninstance);
1
2
3
4
5
6
7
  • fastjson

com.alibaba.fastjson.JSONObject

它的转换方法,包括Java对象转成JSON串、JSON对象,JSON串转成java对象、JSON对象,JSON对象转换Java对象、JSON串等。

String stuString = "{\"age\":2,\"name\":\"公众号行百里er\",\"sex\":\"m\"}";

//JSON字符串转换成JSON对象
JSONObject jsonObject1 = JSONObject.parseObject(stuString);
1
2
3
4
  • 等等

当然,Elasticsearch 也提供了内置的帮助器以生成JSON内容:

XContentBuilder builder = jsonBuilder()
    .startObject()
        .field("user", "kimchy")
        .field("postDate", new Date())
        .field("message", "trying out Elasticsearch")
    .endObject()
1
2
3
4
5
6

# 增删改查API

# Create 创建索引、文档相关API

向索引添加文档,如果索引不存在,则该API会自动给我们创建索引

@Test
@SneakyThrows
void esCRUD() {
    // 创建连接
    TransportClient client = new PreBuiltTransportClient(Settings.EMPTY)
            .addTransportAddress(
                    new TransportAddress(
                            InetAddress.getByName("localhost"), 9300));

    //增
    //create(client);
    //查
    //get(client);
    //getAll(client);
    //改
    //update(client);
    //删
    delete(client);
}

@SneakyThrows
void create(TransportClient client){
    for (int i = 0; i < 5; i++) {
        XContentBuilder builder = XContentFactory.jsonBuilder()
                .startObject()
                .field("empName", "name" + i)
                .field("age", new Random().nextInt(100))
                .field("createTime", new Date())
                .endObject();
        IndexResponse response = client.prepareIndex("emp", "_doc", String.valueOf(i))
                .setSource(builder)
                .get();
//                //还可以不指定id
//                IndexResponse response = client.prepareIndex("emp", "_doc")
//                        .setSource(builder)
//                        .get();
        System.out.println(response.getResult());
    }
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39

这里我用prepareIndex指定id和不指定id分别执行了一遍,所以应该有10条文档产生。

通过Kibana控制台验证一下执行结果:

image.png

结果是执行成功的!

正好,用查询API来验证一下。

# GET API 查询单个、所有文档相关API

代码生成的时候,又生成id为0~4的文档,就查一下id为3的吧先:

private void get(TransportClient client) {
    GetResponse response = client.prepareGet("emp", "_doc", "3").get();
    String index = response.getIndex();//获取索引名称
    String type = response.getType();//获取索引类型
    String id = response.getId();//获取索引id
    System.out.println("index:" + index);
    System.out.println("type:" + type);
    System.out.println("id:" + id);
    System.out.println(response.getSourceAsString());
}
1
2
3
4
5
6
7
8
9
10

image.png

执行成功!

查询所有的API试一下:

private void getAll(TransportClient client) {
    SearchResponse response = client.prepareSearch("emp").get();
    SearchHits searchHits = response.getHits();
    SearchHit[] hits = searchHits.getHits();
    for (SearchHit hit : hits) {
        String res = hit.getSourceAsString();
        System.out.println("res" + res);
    }
}
1
2
3
4
5
6
7
8
9

image.png

OK,成功查询出所有文档。

这里可以对比Kibana Dev Tools控制台返回的json结果,

{
  "took" : 134,
  "timed_out" : false,
  "_shards" : {
    "total" : 1,
    "successful" : 1,
    "skipped" : 0,
    "failed" : 0
  },
  "hits" : {
    "total" : {
      "value" : 10,
      "relation" : "eq"
    },
    "max_score" : 1.0,
    "hits" : [
      {
        "_index" : "emp",
        "_type" : "_doc",
        "_id" : "ze2qFnQBZf6fz3EOVZFP",
        "_score" : 1.0,
        "_source" : {
          "empName" : "name0",
          "age" : 35,
          "createTime" : "2020-08-22T14:54:54.999Z"
        }
      },
      // 中间的结果略...
      {
        "_index" : "emp",
        "_type" : "_doc",
        "_id" : "4",
        "_score" : 1.0,
        "_source" : {
          "empName" : "name4",
          "age" : 56,
          "createTime" : "2020-08-22T15:05:58.480Z"
        }
      }
    ]
  }
}

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43

image.png

Java API的一些方法名和ES查询结果JSON先关字段一般能对的上,如果平时控制台操作比较熟悉的话,再来使用API其实很简单了!

# Update API

修改id为3的记录,将其name改为鲁班7号:

private void update(TransportClient client) {
    try {
        UpdateResponse response = client.prepareUpdate("emp", "_doc", "3")
                .setDoc(XContentFactory.jsonBuilder()
                        .startObject()
                        .field("name", "鲁班7号")
                        .endObject())
                .get();
        System.out.println(response.getResult());
    } catch (IOException e) {
        e.printStackTrace();
    }
}
1
2
3
4
5
6
7
8
9
10
11
12
13

验证一下:

image.png

# Delete API

删除id为3的文档记录:

private void delete(TransportClient client) {
    DeleteResponse response = client.prepareDelete("emp", "_doc", "3").get();
    System.out.println(response.getResult());
}
1
2
3
4

首发公众号 行百里er ,欢迎老铁们关注阅读指正。

#Elasticsearch
上次更新: 2022/09/05, 15:54:38
Elasticsearch初体验-第一次使用就感觉他很勇,搜索界的扛把子!
这些 Elasticsearch 7 部署的问题,你遇到过吗

← Elasticsearch初体验-第一次使用就感觉他很勇,搜索界的扛把子! 这些 Elasticsearch 7 部署的问题,你遇到过吗→

最近更新
01
重要数据不能丢!MySQL数据库定期备份保驾护航!
05-22
02
分布式事务解决方案之 Seata(二):Seata AT 模式
09-09
03
Seata 番外篇:使用 docker-compose 部署 Seata Server(TC)及 K8S 部署 Seata 高可用
09-05
更多文章>
Theme by Vdoing | Copyright © 2020-2023 行百里er | MIT License | 豫ICP备2022020385号-1
  • 跟随系统
  • 浅色模式
  • 深色模式
  • 阅读模式