java应用零停机,时间索引重建(reindex)
一个field的设置是不能被修改的,如果要修改一个Field,那么应该重新按照新的mapping,建立一个index,然后将数据批量查询出来,重新用bulk api写入index中
批量查询的时候,建议采用scroll api,并且采用多线程并发的方式来reindex数据,每次scoll就查询指定日期的一段数据,交给一个线程即可
(1)一开始,依靠dynamic mapping,插入数据,但是不小心有些数据是2017-01-01这种日期格式的,所以title这种field被自动映射为了date类型,实际上它应该是string类型的
PUT /my_index/my_type/3
{
    "title": "2017-01-03"
}
{
    "my_index": {
        "mappings": {
            "my_type": {
                "properties": {
                    "title": {
                        "type": "date"
                    }
                }
            }
        }
    }
}
(2)当后期向索引中加入string类型的title值的时候,就会报错
PUT /my_index/my_type/4
{
    "title": "my first article"
}
{
    "error": {
        "root_cause": [{
              "type": "mapper_parsing_exception",
              "reason": "failed to parse [title]"
          }],
        "type": "mapper_parsing_exception",
        "reason": "failed to parse [title]",
        "caused_by": {
            "type": "illegal_argument_exception",
            "reason": "Invalid format: \"my first article\""
        }
    },
    "status": 400
}
(3)如果此时想修改title的类型,是不可能的
PUT /my_index/_mapping/my_type
{
    "properties": {
        "title": {
            "type": "text"
        }
    }
}
{
    "error": {
        "root_cause": [{
              "type": "illegal_argument_exception",
              "reason": "mapper [title] of different type, current_type [date], merged_type [text]"
          }],
        "type": "illegal_argument_exception",
        "reason": "mapper [title] of different type, current_type [date], merged_type [text]"
    },
    "status": 400
}
(4)此时,唯一的办法,就是进行reindex,也就是说,重新建立一个索引,将旧索引的数据查询出来,再导入新索引
(5)如果说旧索引的名字,是old_index,新索引的名字是new_index,终端java应用,已经在使用old_index在操作了,难道还要去停止java应用,修改使用的index为new_index,才重新启动java应用吗?这个过程中,就会导致java应用停机,可用性降低
(6)所以说,给java应用一个别名,这个别名是指向旧索引的,java应用先用着,java应用先用goods_index alias来操作,此时实际指向的是旧的my_index
PUT /my_index/_alias/goods_index
(7)新建一个index,调整其title的类型为string
PUT /my_index_new
{
    "mappings": {
        "my_type": {
            "properties": {
                "title": {
                    "type": "text"
                }
            }
        }
    }
}
(8)使用scroll api将数据批量查询出来
GET /my_index/_search?scroll=1m
{
      "query": {
            "match_all": {}
      },
      "sort": ["_doc"],
      "size":  1
}
{
    "_scroll_id":"DnF1ZXJ5VGhlbkZldGNoBQAAAAAAADpAFjRvbnNUWVZaVGpHdklqOV9zcFd6MncAAAAAAAA6QRY0b25zVFlWWlRqR3ZJajlfc3BXejJ3AAAAAAAAOkIWNG9uc1RZVlpUakd2SWo5X3NwV3oydwAAAAAAADpDFjRvbnNUWVZaVGpHdklqOV9zcFd6MncAAAAAAAA6RBY0b25zVFlWWlRqR3ZJajlfc3BXejJ3",
    "took": 1,
    "timed_out": false,
    "_shards": {
        "total": 5,
        "successful": 5,
        "failed": 0
    },
    "hits": {
        "total": 3,
        "max_score": null,
        "hits": [{
              "_index": "my_index",
              "_type": "my_type",
              "_id": "2",
              "_score": null,
              "_source": {
                  "title": "2017-01-02"
              },
              "sort": [0]
          }]
    }
}
(9)采用bulk api将scoll查出来的一批数据,批量写入新索引
POST /_bulk
{ "index":  { "_index": "my_index_new", "_type": "my_type", "_id": "2" }}
{ "title":    "2017-01-02" }
(10)反复循环8~9,查询一批又一批的数据出来,采取bulk api将每一批数据批量写入新索引
(11)将goods_index alias切换到my_index_new上去,java应用会直接通过index别名使用新的索引中的数据,java应用程序不需要停机,零提交,高可用
POST /_aliases
{
      "actions": [
            { "remove": { "index": "my_index", "alias": "goods_index" }},
            { "add":    { "index": "my_index_new", "alias": "goods_index" }}
      ]
}
(12)直接通过goods_index别名来查询,是否ok
GET /goods_index/my_type/_search
java应用零停机,时间索引重建(reindex)的更多相关文章
- es之零停机重新索引数据
		
实际生产,对于文档的操作,偶尔会遇到这种问题: 某一个字段的类型不符合后期的业务了,但是当前的索引已经创建了,我们知道es在字段的mapping建立后就不可再次修改mapping的值 比如: 1): ...
 - Elasticsearch系列---实战零停机重建索引
		
前言 我们使用Elasticsearch索引文档时,最理想的情况是文档JSON结构是确定的,数据源源不断地灌进来即可,但实际情况中,没人能够阻拦需求的变更,在项目的某个版本,可能会对原有的文档结构造成 ...
 - ElasticSearch(三十)基于scoll+bulk+索引别名实现零停机重建索引
		
1.为什么要重建索引? 总结,一个type下的mapping中的filed不能被修改,所以如果需要修改,则需要重建索引 2.怎么zero time重建索引? 一个field的设置是不能被修改的,如果要 ...
 - 66.零停机下reindex
		
主要知识点: 理解reindex的使用场景和必要性 学会reindex 一.理解reindex的使用场景和必要性 假设:在某一个index中依靠dynamic mapping插入数据, ...
 - SQL Server中是否可以准确获取最后一次索引重建的时间?
		
在SQL Server中,我们能否找到索引的创建时间?最后一次索引重建(Index Rebuild)的时间? 最后一次索引重组(INDEX REORGANIZE)的时间呢? 答案是我们无法准确的找到 ...
 - elasticsearch 5.x 系列之七  基于索引别名的零停机升级服务
		
一,写在前面的话,elasticsearch 建立索引时的Mapping 设置 建议你在设计索引的初期,就把索引的各个字段设计好,因为,elasticsearch 的各个字段,定义好类型后,就无法进行 ...
 - Elasticsearch如何修改Mapping结构并实现业务零停机
		
Elasticsearch 版本:6.4.0 一.疑问 在项目中后期,如果想调整索引的 Mapping 结构,比如将 ik_smart 修改为 ik_max_word 或者 增加分片数量 等,但 El ...
 - SQL Server 2014新特性:分区索引重建
		
<single_partition_rebuild_index_option> ::= { SORT_IN_TEMPDB = { ON | OFF } | MAXDOP = m ...
 - Oracle索引重建
		
一.前言 Oracle建议对于索引深度超过4级以及已删除的索引条目至少占有现有索引条目总数的20% 这2种情形下需要重建索引.有人持不同观点,就是强烈建议不要定期重建索引.索引重建是一个争论不休被不断 ...
 
随机推荐
- JAVA常用基础知识点[继承,抽象,接口,静态,枚举,反射,泛型,多线程...]
			
类的继承 Java只支持单继承,不允许多重继承- 一个子类只能有一个父类- 一个父类可以派生出多个子类这里写图片描述子类继承了父类,就继承了父类的方法和属性.在子类中,可以使用父类中定义的方法和属性, ...
 - CentOS7 yum方式安装MariaDB 10.2.13-1
			
注:以下步骤都是以root身份运行. 一.建立mariadb.repo 1,编辑新文件,命令:vim /etc/yum.repos.d/mariadb.repo 2,输入如下内容,保存退出 [mar ...
 - 【代码审计】大米CMS_V5.5.3 任意文件删除及代码执行漏洞分析
			
0x00 环境准备 大米CMS官网:http://www.damicms.com 网站源码版本:大米CMS_V5.5.3试用版(更新时间:2017-04-15) 程序源码下载:http://www ...
 - lsass 病毒手动清除方法
			
病毒症状进程里面有2个lsass.exe进程,一个是system的,一个是当前用户名的(该进程为病毒).双击D:盘打不开,只能通过右击选择打开来打开.用kaspersky扫描可以扫描出来,并且可以杀掉 ...
 - MassTransit入门
			
.NET平台ESB框架的中文资料少的可怜,NServiceBus的有几篇,MassTransit的根本找不到,只好硬着头皮看官方的英文文档,顺便翻译出来加深理解. 欢迎拍砖. MassTransit是 ...
 - struts2,spring,ibatis学习
			
1.1 什么是struts2? MVC思想给网站设计带来了巨大的好处,但是MVC毕竟只是一种思想,不同的程序员写出来的基于MVC思想的应用,风格可能不一样.影响程序的标准化,Struts是为了规范MV ...
 - MFC打开文件选择框和多选框,保存文件夹的选择,保存文件路径的选择
			
CString defaultDir = "C:\\"; //默认打开的文件路径 CString fileName = ""; //默认打开的文件名 CStri ...
 - ubuntu下安装Python3
			
到www.python.org网站下载python3.3.2 Gzipped source tar ball (3.3.2) (sig), ~ 16 MB 解压tar vxzf Python3.3.2 ...
 - Spark RDD 默认分区数量 - repartitions和coalesce异同
			
RDD.getNumPartitions()方法可以获得一个RDD分区数量, 1.默认由文件读取的话,本地文件会进行shuffle,hdfs文件默认会按照dfs分片来设定. 2.计算生成后,默认会按照 ...
 - select2 javascript控件 如何设置指定的值
			
$("#id").select2("data") 这样的方法无效 要使用$("#selectNull").val("") ...