文章目錄
- JSR303校驗
- 普通校驗
- 區域例外處理BindResult
- 統一例外處理
- 分組校驗功能(多場景校驗)
- 自定義校驗注解
- Elasticsearch
- 初步檢索
- 1、檢索es資訊
- 2、新增檔案
- PUT和POST區別
- 3、查看檔案
- 4、更新檔案_update
- 5、洗掉檔案或索引
- 洗掉索引
- 6、ES的批量操作——bulk
- 7、樣本測驗資料
谷粒商城_01_環境搭建
谷粒商城_02_Nacos、網關
谷粒商城_03_前端基礎
谷粒商城_04_商品CRUD
谷粒商城_05_阿里云OSS和前端校驗
JSR303校驗
問題引入:填寫form時應該有前端校驗,后端也應該有校驗
前端的校驗是element-ui表單驗證:https://element.eleme.cn/#/zh-CN/component/form
-
Form 組件提供了表單驗證的功能,只需要通過
rules屬性傳入約定的驗證規則,并將 Form-Item 的prop屬性設定為需校驗的欄位名即可,校驗規則參見 async-validator -
使用自定義校驗規則可以解決字母限制、密碼不一致、非整數限制等等的問題
-
基本使用
// dataForm:表單的資料、dataRule:所有檢驗的規則 <el-form :model="dataForm" :rules="dataRule"/> // 表單的某一項用prop指定校驗的目標即可使用 <el-form-item label="密碼" prop="checkPass"> // data() { return { dataRule: { // 密碼校驗的欄位checkPass,validator: validatePass指向校驗的具體方法,既可以將其替換成方法使用 checkPass: [ { validator: validatePass, trigger: 'blur' } ], } } } var validatePass = (rule, value, callback) => { if (value === '') { callback(new Error('請再次輸入密碼')); // dataForm表單的資料 } else if (value !== this.dataForm.pass) { callback(new Error('兩次輸入密碼不一致!')); } else { callback(); } }; -
后端:@NotNull、@NotBank、@URL等等
普通校驗
1、使用校驗注解
在Java中提供了一系列的校驗方式,它這些校驗方式在“javax.validation.constraints、org.hibernate.validator.constraints”包中,提供了如@Email、@NotNull、@URL等注解,
- 主要看注解原始碼檔案來了解其中使用
<!--jsr3引數校驗器-->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-validation</artifactId>
<version>2.6.1</version>
</dependency>
2、@Valid內置例外
這里內置例外的意思是發生例外時回傳的json不是我們的R物件,而是mvc的內置類
在controller類上加:@Validated,方法引數中加校驗注解:@Valid,開啟校驗,
@RequestMapping("/save")
public R save(@Valid @RequestBody BrandEntity brand){
brandService.save(brand);
return R.ok();
}
測驗: http://localhost:88/api/product/brand/save,在postman種發送上面的請求,發現回傳的是json物件,但不是我們的R物件
// 其中
"defaultMessage": "不能為空",
“defaultMessage”: “不能為空”,這些錯誤訊息定義在“hibernate-validator”的“\org\hibernate\validator\ValidationMessages_zh_CN.properties”檔案中,在該檔案中定義了很多的錯誤規則:
javax.validation.constraints.AssertFalse.message = 只能為false
javax.validation.constraints.AssertTrue.message = 只能為true
javax.validation.constraints.DecimalMax.message = 必須小于或等于{value}
javax.validation.constraints.DecimalMin.message = 必須大于或等于{value}
javax.validation.constraints.Digits.message = 數字的值超出了允許范圍(只允許在{integer}位整數和{fraction}位小數范圍內)
javax.validation.constraints.Email.message = 不是一個合法的電子郵件地址
javax.validation.constraints.Future.message = 需要是一個將來的時間
javax.validation.constraints.FutureOrPresent.message = 需要是一個將來或現在的時間
javax.validation.constraints.Max.message = 最大不能超過{value}
javax.validation.constraints.Min.message = 最小不能小于{value}
javax.validation.constraints.Negative.message = 必須是負數
javax.validation.constraints.NegativeOrZero.message = 必須是負數或零
javax.validation.constraints.NotBlank.message = 不能為空
javax.validation.constraints.NotEmpty.message = 不能為空
javax.validation.constraints.NotNull.message = 不能為null
javax.validation.constraints.Null.message = 必須為null
javax.validation.constraints.Past.message = 需要是一個過去的時間
javax.validation.constraints.PastOrPresent.message = 需要是一個過去或現在的時間
javax.validation.constraints.Pattern.message = 需要匹配正則運算式"{regexp}"
javax.validation.constraints.Positive.message = 必須是正數
javax.validation.constraints.PositiveOrZero.message = 必須是正數或零
javax.validation.constraints.Size.message = 個數必須在{min}和{max}之間
org.hibernate.validator.constraints.CreditCardNumber.message = 不合法的信用卡號碼
org.hibernate.validator.constraints.Currency.message = 不合法的貨幣 (必須是{value}其中之一)
org.hibernate.validator.constraints.EAN.message = 不合法的{type}條形碼
org.hibernate.validator.constraints.Email.message = 不是一個合法的電子郵件地址
org.hibernate.validator.constraints.Length.message = 長度需要在{min}和{max}之間
org.hibernate.validator.constraints.CodePointLength.message = 長度需要在{min}和{max}之間
org.hibernate.validator.constraints.LuhnCheck.message = ${validatedValue}的校驗碼不合法, Luhn模10校驗和不匹配
org.hibernate.validator.constraints.Mod10Check.message = ${validatedValue}的校驗碼不合法, 模10校驗和不匹配
org.hibernate.validator.constraints.Mod11Check.message = ${validatedValue}的校驗碼不合法, 模11校驗和不匹配
org.hibernate.validator.constraints.ModCheck.message = ${validatedValue}的校驗碼不合法, ${modType}校驗和不匹配
org.hibernate.validator.constraints.NotBlank.message = 不能為空
org.hibernate.validator.constraints.NotEmpty.message = 不能為空
org.hibernate.validator.constraints.ParametersScriptAssert.message = 執行腳本運算式"{script}"沒有回傳期望結果
org.hibernate.validator.constraints.Range.message = 需要在{min}和{max}之間
org.hibernate.validator.constraints.SafeHtml.message = 可能有不安全的HTML內容
org.hibernate.validator.constraints.ScriptAssert.message = 執行腳本運算式"{script}"沒有回傳期望結果
org.hibernate.validator.constraints.URL.message = 需要是一個合法的URL
org.hibernate.validator.constraints.time.DurationMax.message = 必須小于${inclusive == true ? '或等于' : ''}${days == 0 ? '' : days += '天'}${hours == 0 ? '' : hours += '小時'}${minutes == 0 ? '' : minutes += '分鐘'}${seconds == 0 ? '' : seconds += '秒'}${millis == 0 ? '' : millis += '毫秒'}${nanos == 0 ? '' : nanos += '納秒'}
org.hibernate.validator.constraints.time.DurationMin.message = 必須大于${inclusive == true ? '或等于' : ''}${days == 0 ? '' : days += '天'}${hours == 0 ? '' : hours += '小時'}${minutes == 0 ? '' : minutes += '分鐘'}${seconds == 0 ? '' : seconds += '秒'}${millis == 0 ? '' : millis += '毫秒'}${nanos == 0 ? '' : nanos += '納秒'}
想要自定義錯誤訊息,可以覆寫默認的錯誤提示資訊,如@NotBlank的默認message是
public @interface NotBlank {
String message() default "{javax.validation.constraints.NotBlank.message}";
}
可以在添加注解的時候,修改message:
@NotBlank(message = "品牌名必須非空")
private String name;
當再次發送請求時,得到的錯誤提示資訊:
"defaultMessage": "品牌名必須非空",
但是回傳的錯誤不是R物件,影響接收端的接收,我們可以通過區域例外處理或者統一一次處理解決
區域例外處理BindResult
- 給校驗的Bean后,緊跟一個BindResult,就可以獲取到校驗的結果,拿到校驗的結果,就可以自定義的封裝,
@RequestMapping("/save")
public R save(@Valid @RequestBody BrandEntity brand,
BindingResult result){ // 手動處理例外
if( result.hasErrors()){
Map<String,String> map=new HashMap<>();
//1.獲取錯誤的校驗結果
result.getFieldErrors().forEach((item)->{
//獲取發生錯誤時的message,提示資訊
String message = item.getDefaultMessage();
//獲取發生錯誤的屬性的名字
String field = item.getField();
map.put(field,message);
});
return R.error(400,"提交的資料不合法").put("data",map);
}else {
}
brandService.save(brand);
return R.ok();
}
這種是針對于該請求設定了一個內容校驗,如果針對于每個請求都單獨進行配置,顯然不是太合適,實際上可以統一的對于例外進行處理,
統一例外處理
@ExceptionHandler
- @ ExceptionHandler 需要進行例外處理的方法必須與出錯的方法在同一個Controller里面,那么當代碼加入了 @ControllerAdvice,則不需要必須在同一個 controller 中了,這也是 Spring 3.2 帶來的新特性, 也就是說,@controlleradvice + @ ExceptionHandler 也可以實作全域的例外捕捉,
1、抽取一個例外處理類
@ControllerAdvice標注在類上,通過“basePackages”能夠說明處理哪些路徑下的例外,@ExceptionHandler(value = 例外型別.class)標注在方法上- 這里的ConstraintViolationException例外我和專案中不一樣,但是可以通過原始碼定位到里面的屬性,然后獲取例外資訊放入map
/**
* @author ljy
* @version 1.0.0
* @Description 集中處理所有例外
* @createTime 2021年12月14日 19:22:00
*/
@Slf4j
// @RestControllerAdvice和@ControllerAdvice的關系類似于@RestController
@RestControllerAdvice(basePackages = "com.liu.gulimall.product.controller")// 管理的controller
public class GulimallExceptionControllerAdvice {
@ExceptionHandler(value = ConstraintViolationException.class) // 感知精確例外
// 也可以回傳ModelAndView
// exception是controller中的例外,精確匹配ConstraintViolationException這個例外
// MethodArgumentNotValidException
public R handleValidException(ConstraintViolationException exception){
Map<String,String> map=new HashMap<>();
// 獲取資料校驗的錯誤結果,和之前一樣BindingResult
exception.getConstraintViolations().forEach(item->{
String message = item.getMessage();
Path propertyPath = item.getPropertyPath();
map.put(propertyPath.toString(),message);
});
log.error("資料校驗出現問題{},例外型別{}",exception.getMessage(),exception.getClass());
return R.error(400,"資料校驗出現問題").put("data",map);
}
@ExceptionHandler(value = Throwable.class)//例外的范圍更大
public R handleException(Throwable throwable){
log.error("未知例外{},例外型別{}",
throwable.getMessage(),
throwable.getClass());
return R.error(BizCodeEnum.UNKNOW_EXEPTION.getCode(),
BizCodeEnum.UNKNOW_EXEPTION.getMsg());
}
}
(2)測驗: http://localhost:9999/product/brand/save

(3)默認例外處理
@ExceptionHandler(value = Throwable.class)// 例外的范圍更大
public R handleException(Throwable throwable){
log.error("未知例外{},例外型別{}",
throwable.getMessage(),
throwable.getClass());
return R.error(BizCodeEnum.UNKNOW_EXEPTION.getCode(),
BizCodeEnum.UNKNOW_EXEPTION.getMsg());
}
(4)錯誤狀態碼
正規開發程序中,錯誤狀態碼有著嚴格的定義規則,在專案中我們的錯誤狀態碼定義
上面的用法主要是通過@Controller+@ExceptionHandler來進行例外攔截處理,單獨定義一個列舉類,用來存盤這些錯誤狀態碼
/***
* 錯誤碼和錯誤資訊定義類
* 1. 錯誤碼定義規則為5為數字
* 2. 前兩位表示業務場景,最后三位表示錯誤碼,例如:10001,10:通用 001:系統未知例外
* 3. 維護錯誤碼后需要維護錯誤描述,將他們定義為列舉形式
* 錯誤碼串列:
* 10: 通用
* 001:引數格式校驗
* 11: 商品
* 12: 訂單
* 13: 購物車
* 14: 物流
*/
/**
* @author ljy
* @version 1.0.0
* @Description TODO
* @createTime 2021年12月14日 19:23:00
*/
public enum BizCodeEnum {
UNKNOW_EXEPTION(10000,"系統未知例外"),
VALID_EXCEPTION( 10001,"引數格式校驗失敗");
private int code;
private String msg;
BizCodeEnum(int code, String msg) {
this.code = code;
this.msg = msg;
}
public int getCode() {
return code;
}
public String getMsg() {
return msg;
}
}
分組校驗功能(多場景校驗)
前面解決了統一例外處理,但是同一物體比如id,修改的時候不能為空,添加的時候為空,那怎么來校驗呢?
我們采取分組的方式
1、定義分組介面,A(添加分組)、B(洗掉分組),介面只是標識
2、在controller方法中添加的方法中使用 @Validated(A.class)
// 表示添加的時候采用A分組策略
public R save(@Validated({A.class}) @RequestBody BrandEntity brand){
3、在物體屬性上,比如id,@NotNull(message = “修改id不為空”,groups = {B.class})、@Null(message = “新增id必須為空”,groups = {A.class})
@NotNull(message = "修改必須定制品牌id", groups = {UpdateGroup.class})
@Null(message = "新增不能指定id", groups = {AddGroup.class})
@TableId
private Long brandId;
在這種情況下,沒有指定分組的校驗注解,默認是不起作用的,想要起作用就必須要加groups,
- controller接收到之后,根據@Validated表明的分組資訊,然后確定品牌對應的校驗注解,
總結:
package com.liu.common.valid;
/**
* @author ljy
* @version 1.0.0
* @Description TODO
* @createTime 2021年12月14日 20:49:00
*/
public interface addGroup {
}
========================
/**
* 保存
*/
@RequestMapping("/save")
public R save(@Validated({addGroup.class}) @RequestBody BrandEntity brand, BindingResult result){
brandService.save(brand);
return R.ok();
}
========================
/**
* 品牌名
*/
@NotBlank(message = "品牌名不能為空", groups = {addGroup.class})
private String name;
========================
{
"msg": "提交的資料不合法",
"code": 400,
"data": {
"name": "品牌名不能為空"
}
}
自定義校驗注解
Hibernate Validator提供了一系列內置的校驗注解,可以滿足大部分的校驗需求,但是,仍然有一部分校驗需要特殊定制
比如:要校驗showStatus的0/1狀態,只能是0,1兩個值
1、添加依賴
<!--校驗-->
<dependency>
<groupId>javax.validation</groupId>
<artifactId>validation-api</artifactId>
<version>2.1.0.Final</version>
</dependency>
<dependency>
<groupId>org.hibernate</groupId>
<artifactId>hibernate-validator</artifactId>
<version>5.4.1.Final</version>
</dependency>
<!--高版本需要javax.el-->
<dependency>
<groupId>org.glassfish</groupId>
<artifactId>javax.el</artifactId>
<version>3.0.1-b08</version>
</dependency>
2、自定義注解
/**
* @author ljy
* @version 1.0.0
* @Description 自定義注解,模仿其他的檢驗注解即可
* @createTime 2021年12月14日 20:57:00
*/
@Documented
@Constraint(validatedBy = { ListValueConstraintValidator.class}) // 校驗器,指定校驗器,需要我們自己定義
@Target({ METHOD, FIELD, ANNOTATION_TYPE, CONSTRUCTOR, PARAMETER }) // 在哪可以標注此注解
@Retention(RUNTIME)
public @interface ListValue {
// 必須有3個屬性
// 使用該屬性去Validation.properties中取
String message() default "{com.liu.common.valid.ListValue.message}"; // 錯誤資訊
Class<?>[] groups() default { }; // 分組校驗
Class<? extends Payload>[] payload() default { }; // 自定義負載資訊
// 陣列,需要用戶自己指定
int[] value() default {};
}
因為上面的message值對應的最終字串需要去ValidationMessages.properties中獲得,所以我們在common中新建檔案ValidationMessages.properties
3、ValidationMessages.properties
com.liu.common.valid.ListValue.message=必須提交指定的值 [0,1]
4、自定義校驗器
- 通過原始碼:@Constraint注解的validatedBy是一個ConstraintValidator型別,并且里面包含了注解和校驗型別,所以我們自定義實作ConstraintValidator,放入我們的注解和型別
/**
* @author ljy
* @version 1.0.0
* @Description TODO
* @createTime 2021年12月14日 21:06:00
*/
public class ListValueConstraintValidator implements ConstraintValidator<ListValue,Integer> {
// 存盤所有可能的值
private Set<Integer> set=new HashSet<Integer>();
// 初始化,你可以獲取注解上的內容并進行處理
public void initialize(ListValue constraintAnnotation) {
// 獲取后端寫好的限制 // 這個value就是ListValue里的value,我們寫的注解是@ListValue(value={0,1})
int[] value = constraintAnnotation.value();
for (int i : value) {
set.add(i);
}
}
/**
* 覆寫驗證邏輯
* @param value 需要校驗的值
* @param context
* @return
*/
public boolean isValid(Integer value, ConstraintValidatorContext context) {
// 看是否在限制的值里,是回傳true
return set.contains(value);
}
}
5、使用
/**
* 顯示狀態[0-不顯示;1-顯示]
*/
@ListValue(value = {0,1},groups ={addGroup.class})
private Integer showStatus;
6、測驗
{
"msg": "提交的資料不合法",
"code": 400,
"data": {
"showStatus": "必須提交指定的值 [0,1]"
}
}

Elasticsearch
初步檢索
1、檢索es資訊
(1)GET /_cat/nodes:查看所有節點 :http://localhost:9200/_cat/nodes
(2)GET /_cat/health:查看es健康狀況:green表示健康值正常
(3)GET /_cat/master:查看主節點
(4)GET/_cat/indicies:查看所有索引 ,等價于mysql資料庫的show databases;
2、新增檔案
保存一個資料,保存在哪個索引的哪個型別下(哪張資料庫哪張表下),保存時用唯一標識指定
# 在customer索引下的external型別下保存1號資料
PUT customer/external/1
{
"name":"John Doe"
}
PUT和POST區別
- POST新增,如果不指定id,會自動生成id,指定id就會修改這個資料,并新增版本號;
- 可以不指定id,不指定id時永遠為創建
- 指定不存在的id為創建
- 指定存在的id為更新,而版本號會根據內容變沒變而覺得版本號遞增與否
- PUT可以新增也可以修改,PUT必須指定id;由于PUT需要指定id,我們一般用來做修改操作,不指定id會報錯,
- 必須指定id
- 版本號總會增加
seq_no和version的區別:
- 每個檔案的版本號"
_version" 起始值都為1 每次對當前檔案成功操作后都加1- 而序列號"
_seq_no"則可以看做是索引的資訊 在第一次為索引插入資料時為0,每對索引內資料操作成功一次sqlNO加1, 并且檔案會記錄是第幾次操作使它成為現在的情況的
下面是在postman中選用POST方式的測驗資料:
創建資料成功后,顯示201 created表示插入記錄成功,
回傳資料:
帶有下劃線開頭的,稱為元資料,反映了當前的基本資訊,
{
"_index": "customer", 表明該資料在哪個資料庫下;
"_type": "external", 表明該資料在哪個型別下;
"_id": "1", 表明被保存資料的id;
"_version": 1, 被保存資料的版本
"result": "created", 這里是創建了一條資料,如果重新put一條資料,則該狀態會變為updated,并且版本號也會發生變化,
"_shards": {
"total": 2,
"successful": 1,
"failed": 0
},
"_seq_no": 0,
"_primary_term": 1
}
12345678910111213141516
下面選用POST方式:
添加資料的時候,不指定ID,會自動的生成id,并且型別是新增:
{
"_index": "customer",
"_type": "external",
"_id": "5MIjvncBKdY1wAQm-wNZ",
"_version": 1,
"result": "created",
"_shards": {
"total": 2,
"successful": 1,
"failed": 0
},
"_seq_no": 11,
"_primary_term": 6
}
1234567891011121314
再次使用POST插入資料,不指定ID,仍然是新增的:
{
"_index": "customer",
"_type": "external",
"_id": "5cIkvncBKdY1wAQmcQNk",
"_version": 1,
"result": "created",
"_shards": {
"total": 2,
"successful": 1,
"failed": 0
},
"_seq_no": 12,
"_primary_term": 6
}
添加資料的時候,指定ID,會使用該id,并且型別是新增:
{
"_index": "customer",
"_type": "external",
"_id": "2",
"_version": 1,
"result": "created",
"_shards": {
"total": 2,
"successful": 1,
"failed": 0
},
"_seq_no": 13,
"_primary_term": 6
}
再次使用POST插入資料,指定同樣的ID,型別為updated
{
"_index": "customer",
"_type": "external",
"_id": "2",
"_version": 2,
"result": "updated",
"_shards": {
"total": 2,
"successful": 1,
"failed": 0
},
"_seq_no": 14,
"_primary_term": 6
}
3、查看檔案
GET /customer/external/1
{
"_index": "customer",
"_type": "external",
"_id": "1",
"_version": 10,
"_seq_no": 18,//并發控制欄位,每次更新都會+1,用來做樂觀鎖
"_primary_term": 6,//同上,主分片重新分配,如重啟,就會變化
"found": true,
"_source": {
"name": "John Doe"
}
}
123456789101112
樂觀鎖用法:通過“
if_seq_no=1&if_primary_term=1”,當序列號匹配的時候,才進行修改,否則不修改,
實體:將id=1的資料更新為name=1,然后再次更新為name=2,起始1_seq_no=18,_primary_term=6
(1)將name更新為1
PUT http://localhost:9200/customer/external/1?if_seq_no=18&if_primary_term=6
(2)將name更新為2,更新程序中使用seq_no=18
PUT http://localhost:9200/customer/external/1?if_seq_no=18&if_primary_term=6
結果為:出現更新錯誤,
(3)查詢新的資料
GET http://localhost:9200/customer/external/1
{
"_index": "customer",
"_type": "external",
"_id": "1",
"_version": 11,
"_seq_no": 19,
"_primary_term": 6,
"found": true,
"_source": {
"name": "1"
}
}
能夠看到_seq_no變為19
(4)再次更新,更新成功
4、更新檔案_update
POST customer/externel/1/_update
{
"doc":{
"name":"111"
}
}
或者
POST customer/externel/1
{
"doc":{
"name":"222"
}
}
或者
PUT customer/externel/1
{
"doc":{
"name":"222"
}
}
不同:帶有update情況下
- POST操作會對比源檔案資料,如果相同不會有什么操作,檔案version不增加,
- PUT操作總會重新保存并增加version版本
POST時帶_update對比元資料如果一樣就不進行任何操作,
看場景:
- 對于大并發更新,不帶update
- 對于大并發查詢偶爾更新,帶update;對比更新,重新計算分配規則
(1)POST更新檔案,帶有_update
如果再次執行更新,則不執行任何操作,序列號也不發生變化
回傳
{
"_index": "customer",
"_type": "external",
"_id": "1",
"_version": 12,
"result": "noop", // 無操作
"_shards": {
"total": 0,
"successful": 0,
"failed": 0
},
"_seq_no": 20,
"_primary_term": 6
}
POST更新方式,會對比原來的資料,和原來的相同,則不執行任何操作(version和_seq_no)都不變,
(2)POST更新檔案,不帶_update,和put一樣
在更新程序中,重復執行更新操作,資料也能夠更新成功,不會和原來的資料進行對比,
{
"_index": "customer",
"_type": "external",
"_id": "1",
"_version": 13,
"result": "updated",
"_shards": {
"total": 2,
"successful": 1,
"failed": 0
},
"_seq_no": 21,
"_primary_term": 6
}
5、洗掉檔案或索引
DELETE customer/external/1
DELETE customer // 洗掉索引
注:elasticsearch并沒有提供洗掉型別的操作,只提供了洗掉索引和檔案的操作,
實體:洗掉id=1的資料,洗掉后繼續查詢
DELETE http://localhost:9200/customer/external/1
{
"_index": "customer",
"_type": "external",
"_id": "1",
"_version": 14,
"result": "deleted",
"_shards": {
"total": 2,
"successful": 1,
"failed": 0
},
"_seq_no": 22,
"_primary_term": 6
}
再次執行DELETE http://localhost:9200/customer/external/1
{
"_index": "customer",
"_type": "external",
"_id": "1",
"_version": 15,
"result": "not_found",
"_shards": {
"total": 2,
"successful": 1,
"failed": 0
},
"_seq_no": 23,
"_primary_term": 6
}
GET http://localhost:9200/customer/external/1
{
"_index": "customer",
"_type": "external",
"_id": "1",
"found": false
}
123456
洗掉索引
實體:洗掉整個costomer索引資料
洗掉前,所有的索引http://localhost:9200/_cat/indices
green open .kibana_task_manager_1 DhtDmKrsRDOUHPJm1EFVqQ 1 0 2 0 31.3kb 31.3kb
green open .apm-agent-configuration vxzRbo9sQ1SvMtGkx6aAHQ 1 0 0 0 283b 283b
green open .kibana_1 rdJ5pejQSKWjKxRtx-EIkQ 1 0 8 3 28.8kb 28.8kb
yellow open customer mG9XiCQISPmfBAmL1BPqIw 1 1 9 1 8.6kb 8.6kb
洗掉“ customer ”索引
DELTE http://localhost:9200/customer
回應
{
"acknowledged": true
}
洗掉后,所有的索引 http://localhost:9200/_cat/indices
green open .kibana_task_manager_1 DhtDmKrsRDOUHPJm1EFVqQ 1 0 2 0 31.3kb 31.3kb
green open .apm-agent-configuration vxzRbo9sQ1SvMtGkx6aAHQ 1 0 0 0 283b 283b
green open .kibana_1 rdJ5pejQSKWjKxRtx-EIkQ 1 0 8 3 28.8kb 28.8kb
6、ES的批量操作——bulk
匹配匯入資料
POST http://localhost:9200/customer/external/_bulk
兩行為一個整體
{"index":{"_id":"1"}}
{"name":"a"}
{"index":{"_id":"2"}}
{"name":"b"}
注意格式json和text均不可,要去kibana里Dev Tools
語法格式:
{action:{metadata}}\n
{request body }\n
{action:{metadata}}\n
{request body }\n
這里的批量操作,當發生某一條執行發生失敗時,其他的資料仍然能夠接著執行,也就是說彼此之間是獨立的,
bulk api以此按順序執行所有的action(動作),如果一個單個的動作因任何原因失敗,它將繼續處理它后面剩余的動作,當bulk api回傳時,它將提供每個動作的狀態(與發送的順序相同),所以您可以檢查是否一個指定的動作是否失敗了,
實體1: 執行多條資料
POST /customer/external/_bulk
{"index":{"_id":"1"}}
{"name":"John Doe"}
{"index":{"_id":"2"}}
{"name":"John Doe"}
12345
執行結果
#! Deprecation: [types removal] Specifying types in bulk requests is deprecated.
{
"took" : 318, 花費了多少ms
"errors" : false, 沒有發生任何錯誤
"items" : [ 每個資料的結果
{
"index" : { 保存
"_index" : "customer", 索引
"_type" : "external", 型別
"_id" : "1", 檔案
"_version" : 1, 版本
"result" : "created", 創建
"_shards" : {
"total" : 2,
"successful" : 1,
"failed" : 0
},
"_seq_no" : 0,
"_primary_term" : 1,
"status" : 201 新建完成
}
},
{
"index" : { 第二條記錄
"_index" : "customer",
"_type" : "external",
"_id" : "2",
"_version" : 1,
"result" : "created",
"_shards" : {
"total" : 2,
"successful" : 1,
"failed" : 0
},
"_seq_no" : 1,
"_primary_term" : 1,
"status" : 201
}
}
]
}
實體2:對于整個索引執行批量操作
POST /_bulk
{"delete":{"_index":"website","_type":"blog","_id":"123"}}
{"create":{"_index":"website","_type":"blog","_id":"123"}}
{"title":"my first blog post"}
{"index":{"_index":"website","_type":"blog"}}
{"title":"my second blog post"}
{"update":{"_index":"website","_type":"blog","_id":"123"}}
{"doc":{"title":"my updated blog post"}}
7、樣本測驗資料
準備了一份顧客銀行賬戶資訊的虛構的JSON檔案樣本,每個檔案都有下列的schema(模式),
{
"account_number": 1,
"balance": 39225,
"firstname": "Amber",
"lastname": "Duke",
"age": 32,
"gender": "M",
"address": "880 Holmes Lane",
"employer": "Pyrami",
"email": "amberduke@pyrami.com",
"city": "Brogan",
"state": "IL"
}
https://github.com/elastic/elasticsearch/blob/master/docs/src/test/resources/normalized-T1117-AtomicRed-regsvr32.json ,匯入測驗資料,
POST bank/account/_bulk
上面的資料
http://localhost:9200/_cat/indices
付訓入了1000條
yellow open bank 99m64ElxRuiH46wV7RjXZA 1 1 1000 0 427.8kb 427.8kb
轉載請註明出處,本文鏈接:https://www.uj5u.com/qita/386525.html
標籤:其他
