目录
- 一、ES的别名
- 二、ES的分片
- 三、ES的别名的增删改查
- 3.1、创建别名/分片的代码示例
- 3.2、CRUD代码示例
一、ES的别名
为什么使用ES别名?
灵活的扩容。
动态的滚动查询。 例如“在不同的索引创建窗口”。
进行索引分组。
使用别名过滤器来屏蔽文档,他们可以对正在执行的查询自动地实施过滤。
结合别名和路由,在查询或索引的时候自动地使用路由值。
二、ES的分片
分片作用:
(1)、更好的分布式存储、扩展。
(2)、高效地平行查询。
副本的作用:
(1)、保证数据完整性,节点出现异常时,充当主分片。
(2)、优化查询效率,副本的数据和主分片一致,可以充分发挥查询时的效率。
集群索引出现创建、搜索慢,如何解决?
硬件上进行节点的增加;
重建索引,重新划分主副节点数量【可以使用别名来平滑的操作】;
三、ES的别名的增删改查
插入数据
插入数据时,按照“具体index”来插入数据,同时可以设置别名。
查询数据
根据id/其他属性去搜索“具体index”。—可以查询
根据“别名”来查询所有索引的数据。—可以查询
删除数据
根据“具体index”删除,deleteByQuery方式删除;—可以删除
根据“别名”删除,deleteByQuery方式删除;—可以删除
【----原因:根据条件查询到具体索引的记录,然后对查询到的数据按照“具体index”进行删除。】
根据“具体index”及主键id,先查询数据,然后“具体index”删除。—可以删除
根据“别名”及主键id,先查询数据,然后“具体index”删除。—可以删除
3.1、创建别名/分片的代码示例
public String getIndexName(String index, String type) {if ("month".equals(type)) {String yyyyMM = new SimpleDateFormat("yyyyMM").format(new Date());return index + "-" + yyyyMM;}if ("quarter".equals(type)) {return getQuarterFirstMonth(index);}if ("year".equals(type)) {String yyyy = new SimpleDateFormat("yyyy").format(new Date());return index + "-" + yyyy;}return "";}public String insert(T entity) throws Exception {//确定当前ES的索引是否需要 按时间生成新的String newIndexName = getIndexName(entity.getIndex(),"year"); //默认生成 todoentity.setIndex(newIndexName);//生成 n个分片+副分片、并生成别名//例如 Index为test_file-2023,别名是test_fileString alias = entity.getIndex().substring(0,entity.getIndex().lastIndexOf("-"));if(!checkIndexExist(newIndexName)){ //校验具体索引是否已经创建createIndexWithAlias(newIndexName,alias); //创建有别名的索引,并进行分片}IndexRequest request = new IndexRequest(newIndexName);request.id(entity.getId()).source(JSONObject.toJSONString(entity), XContentType.JSON).create(false);IndexResponse response = client.index(request, RequestOptions.DEFAULT);String name = response == null ? null : response.getResult().name();log.info("ES执行插入:index:{},type:{},id:{}", newIndexName, request.type(), request.id());return name;}
校验索引是否已经创建
public boolean checkIndexExist(String index) throws Exception {GetIndexRequest getIndexRequest = new GetIndexRequest(index);boolean exists = client.indices().exists(getIndexRequest, RequestOptions.DEFAULT);if (exists) {return true;}return false;}
创建别名/分片。
public boolean createIndexWithAlias(String index,String alias) throws IOException {CreateIndexRequest indexRequest = new CreateIndexRequest(index);indexRequest.settings(Settings.builder().put("index.number_of_shards", 2).put("index.number_of_replicas", 1));if(StringUtils.isNotBlank(alias)){indexRequest.alias(new Alias(alias));}CreateIndexResponse response = client.indices().create(indexRequest, RequestOptions.DEFAULT);return response.isAcknowledged();}
3.2、CRUD代码示例
public Object testTransfer( Map<String, Object> itemMap){List<String> dmcIds = (List<String>)itemMap.get("dmc_ids");String scene = (String)itemMap.get("scene");List<String> ids = (List<String>)itemMap.get("ids");JSONObject testDoc = (JSONObject)itemMap.get("file_transfer");TransferEsDo transferDoc = JSONObject.parseObject(JSON.toJSONString(testDoc),TransferEsDo.class);/*** 事先有别名 file_transfer_wwy ,索引有 file_transfer_wwy-2022、file_transfer_wwy-2023*///ES分片的插入数据if("1".equals(scene)){try{transferElasticRepository.insert(transferDoc);}catch (Exception e){log.error("testTransfer scene=1 ");}}//从ES查询记录if("2".equals(scene)){//根据实际Index查询或别名查询BoolQueryBuilder boolBuilder = new BoolQueryBuilder();if(org.apache.commons.collections4.CollectionUtils.isNotEmpty(ids)){BoolQueryBuilder idBuilder = new BoolQueryBuilder().must(QueryBuilders.termsQuery("_id",ids));boolBuilder.should(idBuilder);}if(org.apache.commons.collections4.CollectionUtils.isNotEmpty(dmcIds)){BoolQueryBuilder fileIdBuilder = new BoolQueryBuilder().must(QueryBuilders.termsQuery("file_id.keyword",dmcIds));boolBuilder.should(fileIdBuilder);}SearchSourceBuilder searchSourceBuilder = new SearchSourceBuilder();searchSourceBuilder.query(boolBuilder);searchSourceBuilder.from(0);searchSourceBuilder.size(100);SearchRequest searchRequest = new SearchRequest(transferDoc.getIndex());searchRequest.source(searchSourceBuilder);List<TransferEsDo> transferReList = new ArrayList<>();try {SearchResponse searchResponse = restHighLevelClient.search(searchRequest, RequestOptions.DEFAULT);for (SearchHit searchHit : searchResponse.getHits()) {transferReList.add(JSON.parseObject(searchHit.getSourceAsString(), TransferEsDo.class));}} catch (Exception e){log.error("testTransfer dmcIds:{},ex:{}", JSON.toJSONString(dmcIds),e.getMessage());}}if("3".equals(scene)){ //根据别名或实际index删除DeleteByQueryRequest request = new DeleteByQueryRequest(transferDoc.getIndex());request.setQuery(QueryBuilders.termsQuery("file_id.keyword",transferDoc.getFileId()));try{restHighLevelClient.deleteByQuery(request, RequestOptions.DEFAULT);}catch (Exception e){log.error("testTransfer fileId deleteByQuery ex:{}",e.getMessage());return false;}}if("4".equals(scene)){ //根据别名或实际index删除try{//还是根据id,index或别名获取到记录,然后按照实际的indexName和id进行删除SearchSourceBuilder sourceBuilder = new SearchSourceBuilder();sourceBuilder.query(QueryBuilders.termsQuery("id", Arrays.asList(transferDoc.getId())));sourceBuilder.size(10000);SearchRequest searchRequest = new SearchRequest(transferDoc.getIndex());searchRequest.source(sourceBuilder);SearchResponse searchResponse = restHighLevelClient.search(searchRequest, RequestOptions.DEFAULT);SearchHits hits = searchResponse.getHits();List<TransferEsDo> result = new ArrayList<>();for (SearchHit hit : hits.getHits()) {result.add(JSON.parseObject(JSON.toJSONString(hit.getSourceAsMap()), TransferEsDo.class));}DeleteRequest request = new DeleteRequest(result.get(0).getIndex(), result.get(0).getId());DeleteResponse response = restHighLevelClient.delete(request, RequestOptions.DEFAULT);}catch (Exception e){log.error("testTransfer fileId deleteByQuery ex:{}",e.getMessage());return false;}}return false;}