使用 Jest 或 Java API 有没有办法告诉 Elasticsearch 从 json 创建文档作为字符串?
Using Jest or Java API is there a way to tell Elasticsearch to create documents from json as a String?
鉴于此 POJO:
public class People {
String sex;
long age;
String names;
}
"names" 属性 将是一个 json 字符串,我需要为其创建嵌套文档。这是我需要使用 Jest Client 保存到 Elasticsearch 的实例示例:
People people = new People();
people.setSex("Male");
people.setAge(21);
people.setNames("[{\"fname\": \"Bob\",\"lname\": \"Smith\"},[{\"fname\": \"Mike\",\"lname\": \"Johnson\"}");
Index index = new Index.Builder(people).index("indexName").type("aType").build();
jestClient.execute(index);
ES 中的结果文档如下所示:
"_source" : {
"sex" : "Male",
"age" : 21,
"names" : "[{\"fname\": \"Bob\",\"lname\": \"Smith\"},{\"fname\": \"Mike\",\"lname\": \"Johnson\"}]"
}
所以它采用字符串名称并将其作为文字字符串插入,这是有道理的,但实际上我需要从每个名称对象创建文档。换句话说,我希望它看起来像这样:
"_source" : {
"sex" : "Male",
"age" : 21,
"names" : [{
"fname": "Bob",
"lname": "Smith"
}, {
"fname": "Mike",
"lname": "Johnson"
}]
}
我尝试添加一个映射来告诉 ES 将其视为 "nested",但随后我得到一个 Mapper Parsing Exception 说 "tried to parse field [names] as object, but found a concrete value".
我知道如果我创建一个实际的 Name POJO 对象并拥有它们的列表,我应该能够做到这一点,但不幸的是,由于要求我无法做到这一点。我必须使用上面指定格式提供的 JSON 字符串。
解决方案:
感谢 Vishal Rao 为我指明了正确的方向。
解决方案是将 "names" 类型更改为 JsonArray (Google GSON)。然后使用 Google GSON 解析器:
People people = new People();
people.setSex("Male");
people.setAge(21);
String json = "[{\"fname\": \"Bob\",\"lname\": \"Smith\"},[{\"fname\": \"Mike\",\"lname\": \"Johnson\"}"
JsonParser jsonParser = new JsonParser();
JsonElement jsonElement = jsonParser.parse(json);
JsonArray jsonArray = jsonElement.getAsJsonArray();
people.setNames(jsonArray);
Index index = new Index.Builder(people).index("indexName").type("aType").build();
jestClient.execute(index);
此外,我还有一个将名称 属性 设置为嵌套类型的映射。
您可能想先尝试将字符串转换为 JSON 对象,这可能就是您收到该错误的原因。 Elasticsearch 尝试将其解析为一个对象,但在那里找到了一个字符串。
也许做这样的事情:
JSONObject jsonObj = new JSONObject(names);
然后使用该对象。
鉴于此 POJO:
public class People {
String sex;
long age;
String names;
}
"names" 属性 将是一个 json 字符串,我需要为其创建嵌套文档。这是我需要使用 Jest Client 保存到 Elasticsearch 的实例示例:
People people = new People();
people.setSex("Male");
people.setAge(21);
people.setNames("[{\"fname\": \"Bob\",\"lname\": \"Smith\"},[{\"fname\": \"Mike\",\"lname\": \"Johnson\"}");
Index index = new Index.Builder(people).index("indexName").type("aType").build();
jestClient.execute(index);
ES 中的结果文档如下所示:
"_source" : {
"sex" : "Male",
"age" : 21,
"names" : "[{\"fname\": \"Bob\",\"lname\": \"Smith\"},{\"fname\": \"Mike\",\"lname\": \"Johnson\"}]"
}
所以它采用字符串名称并将其作为文字字符串插入,这是有道理的,但实际上我需要从每个名称对象创建文档。换句话说,我希望它看起来像这样:
"_source" : {
"sex" : "Male",
"age" : 21,
"names" : [{
"fname": "Bob",
"lname": "Smith"
}, {
"fname": "Mike",
"lname": "Johnson"
}]
}
我尝试添加一个映射来告诉 ES 将其视为 "nested",但随后我得到一个 Mapper Parsing Exception 说 "tried to parse field [names] as object, but found a concrete value".
我知道如果我创建一个实际的 Name POJO 对象并拥有它们的列表,我应该能够做到这一点,但不幸的是,由于要求我无法做到这一点。我必须使用上面指定格式提供的 JSON 字符串。
解决方案:
感谢 Vishal Rao 为我指明了正确的方向。
解决方案是将 "names" 类型更改为 JsonArray (Google GSON)。然后使用 Google GSON 解析器:
People people = new People();
people.setSex("Male");
people.setAge(21);
String json = "[{\"fname\": \"Bob\",\"lname\": \"Smith\"},[{\"fname\": \"Mike\",\"lname\": \"Johnson\"}"
JsonParser jsonParser = new JsonParser();
JsonElement jsonElement = jsonParser.parse(json);
JsonArray jsonArray = jsonElement.getAsJsonArray();
people.setNames(jsonArray);
Index index = new Index.Builder(people).index("indexName").type("aType").build();
jestClient.execute(index);
此外,我还有一个将名称 属性 设置为嵌套类型的映射。
您可能想先尝试将字符串转换为 JSON 对象,这可能就是您收到该错误的原因。 Elasticsearch 尝试将其解析为一个对象,但在那里找到了一个字符串。 也许做这样的事情:
JSONObject jsonObj = new JSONObject(names);
然后使用该对象。