我有一个如下所示的Java类(GeoPoint是一个Elasticsearch类型):
private Long id;
private Integer genre;
private String cityName;
private GeoPoint geoPoint;
private Date lastUpdate;
private Double lat;
private Double lon;
我使用的Elasticsearch映射是:
{
"location": {
"properties": {
"id": {"type": "long"},
"genre": {"type": "integer"},
"cityName": {"type": "string"},
"geoPoint": {
"type": "geo_point",
"geohash": true,
"geohash_prefix": true,
"geohash_precision": 7
},
"lastUpdate": {"type": "date", format: "yyyy/MM/dd HH:mm:ss"}
}
}
}
当尝试对其进行索引时,我得到以下异常:
org.elasticsearch。ElasticsearchParseException:字段必须为lat/lon或geohash
异常从GeoUtils类的第381行抛出。它发生在映射类中检查双lat和lon字段之后,就像地球点属性一样。
正如ElasticSearch文档所建议的,我不明白为什么它不起作用,因为我将geoPoint的字段类型设置为geo_point。
更新 1
Java类。
public class UserLocation implements Serializable {
private Long id;
private Integer genre;
private String cityName;
private GeoPoint geoPoint;
private Date lastUpdate;
public UserLocation () {
}
public UserLocation (UserLocationLite userLocationLite) {
this.id = userLocationLite.getId();
this.genre = userLocationLite.getGenre();
this.cityName = userLocationLite.getCity();
this.geoPoint =
new GeoPoint(userLocationLite.getLatitude(), userLocationLite.getLongitude());
this.lastUpdate = userLocationLite.getActivity();
}
public Long getId() {
return id;
}
public void setId(Long id) {
this.id = id;
}
public Integer getGenre() {
return genre;
}
public void setGenre(Integer genre) {
this.genre = genre;
}
public String getCityName() {
return cityName;
}
public void setCityName(String cityName) {
this.cityName = cityName;
}
public GeoPoint getGeoPoint() {
return geoPoint;
}
public void setGeoPoint(GeoPoint geoPoint) {
this.geoPoint = geoPoint;
}
public Date getLastUpdate() {
return lastUpdate;
}
public void setLastUpdate(Date lastUpdate) {
this.lastUpdate = lastUpdate;
}
}
方法进行索引。
@Override
public boolean save(String id, R r) {
try {
return this.transportClient.prepareIndex(this.index, this.type, id)
.setSource(this.objectMapper.writeValueAsString(r))
.execute().actionGet().isCreated();
} catch (JsonProcessingException e) {
e.printStackTrace();
}
return false;
}
其中R是为另一个类实现的一种泛型类型,在这种情况下是Userplace类,其序列化如下。
{"id":40,"genre":1,"cityName":"Madrid","geoPoint":{"lat":42.626595,"lon":-0.488439,"geohash":"ezrm5c0vx832"},"lastUpdate":1402144560000}
更新2
现在Java类结构工作得很好。
public class UserLocationSearch implements Serializable {
private Long id;
private Integer genre;
private String cityName;
@JsonIgnore
private GeoPoint geoPoint;
private Date lastUpdate;
public UserLocationSearch() {
this.geoPoint = new GeoPoint();
}
public UserLocationSearch(UserLocationLite userLocationLite) {
this.id = userLocationLite.getId();
this.genre = userLocationLite.getGenre();
this.cityName = userLocationLite.getCity();
this.geoPoint =
new GeoPoint(userLocationLite.getLatitude(), userLocationLite.getLongitude());
this.lastUpdate = userLocationLite.getActivity();
}
public Long getId() {
return id;
}
public void setId(Long id) {
this.id = id;
}
public Integer getGenre() {
return genre;
}
public void setGenre(Integer genre) {
this.genre = genre;
}
public String getCityName() {
return cityName;
}
public void setCityName(String cityName) {
this.cityName = cityName;
}
public GeoPoint getGeoPoint() {
return geoPoint;
}
public void setGeoPoint(GeoPoint geoPoint) {
this.geoPoint = geoPoint;
}
public String getGeohash() {
return this.geoPoint.getGeohash();
}
public void setGeohash(String geohash) {
this.geoPoint.resetFromGeoHash(geohash);
}
public Date getLastUpdate() {
return lastUpdate;
}
public void setLastUpdate(Date lastUpdate) {
this.lastUpdate = lastUpdate;
}
}
但是现在我有另一个问题。
如果拿到文件。
获取 /用户/位置/40
{
"_index": "user",
"_type": "location",
"_id": "40",
"_version": 7,
"found": true,
"_source": {
"id": 40,
"genre": 1,
"cityName": "Madrid",
"lastUpdate": 1402144560000,
"geohash": "ezrm5c28d9x0"
}
}
地理哈希值有 12 个字符,但在映射中,地理哈希精度设置为 7...
获取/用户/位置/_映射
{
"user": {
"mappings": {
"location": {
"properties": {
"cityName": {
"type": "string"
},
"genre": {
"type": "integer"
},
"geoPoint": {
"type": "geo_point",
"geohash": true,
"geohash_prefix": true,
"geohash_precision": 7
},
"geohash": {
"type": "string"
},
"id": {
"type": "long"
},
"lastUpdate": {
"type": "date",
"format": "yyyy/MM/dd HH:mm:ss"
}
}
}
}
}
}
这意味着它的工作是错误的?
更新3
当前类。
public class UserLocationSearch implements Serializable {
private Long id;
private Integer genre;
private String cityName;
private Location location;
private GeoPoint geoPoint;
private Date lastUpdate;
public UserLocationSearch() {
}
public UserLocationSearch(UserLocationLite userLocationLite) {
this.id = userLocationLite.getId();
this.genre = userLocationLite.getGenre();
this.cityName = userLocationLite.getCity();
this.location = new Location(userLocationLite.getLatitude(), userLocationLite.getLongitude());
this.geoPoint = new GeoPoint(this.location.getGeohash());
this.lastUpdate = userLocationLite.getActivity();
}
public Long getId() {
return id;
}
public void setId(Long id) {
this.id = id;
}
public Integer getGenre() {
return genre;
}
public void setGenre(Integer genre) {
this.genre = genre;
}
public String getCityName() {
return cityName;
}
public void setCityName(String cityName) {
this.cityName = cityName;
}
public Location getLocation() {
return location;
}
public void setLocation(Location location) {
this.location = location;
}
public GeoPoint getGeoPoint() {
return geoPoint;
}
public void setGeoPoint(GeoPoint geoPoint) {
this.geoPoint = geoPoint;
}
public Date getLastUpdate() {
return lastUpdate;
}
public void setLastUpdate(Date lastUpdate) {
this.lastUpdate = lastUpdate;
}
public static class GeoPoint{
private String geohash;
public GeoPoint() {
}
public GeoPoint(String geohash) {
this.geohash = geohash;
}
public String getGeohash() {
return geohash;
}
public void setGeohash(String geohash) {
this.geohash = geohash;
}
}
public static class Location{
private Double lat;
private Double lon;
public Location() {
}
public Location(Double lat, Double lon) {
this.lat = lat;
this.lon = lon;
}
public Double getLat() {
return lat;
}
public void setLat(Double lat) {
this.lat = lat;
}
public Double getLon() {
return lon;
}
public void setLon(Double lon) {
this.lon = lon;
}
@JsonIgnore
public String getGeohash(){
return new org.elasticsearch.common.geo.GeoPoint(this.lat, this.lon).getGeohash();
}
}
}
它的映射。
{
"location": {
"properties": {
"id": {"type": "long"},
"genre": {"type": "integer"},
"cityName": {"type": "string"},
"location": {
"type": "geo_point",
"geohash": false
},
"geoPoint": {
"type": "geo_point",
"geohash": true,
"geohash_prefix": true,
"geohash_precision": 7
},
"lastUpdate": {"type": "date", format: "yyyy/MM/dd HH:mm:ss"}
}
}
}
搜索。
按距离(工作正常)。
获取/用户/位置/_搜索
{
"query": {
"match_all": {}
},
"filter": {
"geo_distance": {
"distance": "100km",
"location": {
"lat": 42.5,
"lon": -0.49
}
}
}
}
通过geohash(工作也很好,超过7的精度被忽略,因为它被映射为“geohash_precision:7”)。
获取/用户/位置/_搜索
{
"query": {
"filtered": {
"filter": {
"geohash_cell": {
"geoPoint": {
"geohash": "ezrm5c0y5rh8"
},
"neighbors": true,
"precision": 7
}
}
}
}
}
结论
我不明白为什么org.elasticsearch.common.geo.GeoHashUtils.GeoPoint类与实际的Elastic版本不兼容。
但是,按照@jkbkot提供的思路,我决定实现自己的GeoPoint和Location类,以获得完全的兼容性。
以下Sense脚本应该会让您知道该怎么做:
DELETE location
PUT location
PUT location/location/_mapping
{
"location": {
"properties": {
"id": {"type": "long"},
"genre": {"type": "integer"},
"cityName": {"type": "string"},
"geoPoint": {
"type": "geo_point",
"geohash": true,
"geohash_prefix": true,
"geohash_precision": 7
},
"lastUpdate": {"type": "date", format: "yyyy/MM/dd HH:mm:ss"}
}
}
}
GET location/location/_mapping
PUT location/location/1
{"id":40,"genre":1,"cityName":"Madrid","geoPoint":{"geohash":"ezrm5c0vx832"},"lastUpdate":1402144560000}
GET /location/location/_search
{
"query" : {
"match_all": {}
},
"filter" : {
"geo_distance" : {
"distance" : "40km",
"geoPoint" : {
"lat" : 42.5,
"lon" : -0.49
}
}
}
}
您必须将保存文档的 Java 类转换为 JSON,其结构类似于:
{
"id": 40,
"genre": 1,
"cityName": "Madrid",
"geoPoint": {
"geohash": "ezrm5c0vx832"
},
"lastUpdate": 1402144560000
}
或
{
"id": 40,
"genre": 1,
"cityName": "Madrid",
"geoPoint": {
"lat": 42.626595,
"lon": -0.488439
},
"lastUpdate": 1402144560000
}
因此,要么你必须从Java类中删除私有的GeoPoint geoPoint;
并在那里保留lat
和lon
(或者相反),要么你必须改变你如何将类序列化为JSON字符串 - 省略geoPoint或lat和lon。
问题内容: 我正在尝试在ES 1.0.0上设置geo_point对象,并对它运行简单的概念证明查询,但是查询无法返回任何匹配。这是我的设置步骤: 1)创建映射: 2)验证映射: 3)添加一条数据 4)查询该数据: 我的预期结果是,我将返回一击,但查询未返回任何内容。 提前致谢! 问题答案: 我认为您缺少请求的“查询”部分。 我刚刚测试了您的步骤,然后进行更改返回了文档。
问题内容: 我正在研究Elastic-Search v1.1.1,我遇到了搜索查询问题。我想知道如何解决以下障碍 这是我的地图 索引记录中的数据是 我的搜索是 我想要记录的完全匹配,可以使用该查询来获取记录的完全匹配 我用queryString()检查了一下,然后确定了它对于精确匹配没有用 请建议我 问题答案: 您可以在字符串两边加上引号以进行完全匹配: 如果您不想在上述字符串索引上进行部分匹配,
问题内容: 我试图了解我正在制作的一个小程序的PrintWriter,而且我似乎无法让Java来制作文件然后在上面写。当我执行下面的程序时,它在第9行显示Filenotfoundexeption错误。它也无法在我指定的目录中创建文件。我对此并不陌生,因此请尝试使答案保持简单。我正在使用Eclipse。 问题答案: 如果该目录不存在,则需要创建它。Java不会自己创建它,因为该类只是到一个实体的链接
问题内容: 我遍历了许多博客和网站,了解如何配置Elasticsearch for MongoDB来索引MongoDB中的集合,但是它们都不是直接的。 请向我说明逐步安装Elasticsearch的过程,其中应包括: 组态 在浏览器中运行 我将Node.js与express.js结合使用,因此请相应地提供帮助。 问题答案: 这个答案应该足以使您开始按照本教程使用MongoDB,Elasticsea
问题内容: 以下是我正在使用的最新版本的logstash和elasticsearch的问题的可复制示例。 我正在使用logstash将来自csv的地理空间数据作为geo_points输入到elasticsearch。 CSV如下所示: 我创建了一个映射模板,如下所示: 并有一个logstash配置文件,如下所示: 然后运行以下命令: 但是,当查看索引base_map_simple时,它表明文档中没
我有以下三个类:我尝试制作1和2的例程,并使用tjava调用主类和来自1和2的方法,但我无法获取这些方法。 1) 我在Talend中为上面的代码(1)和2)做了例程,然后用tjava调用方法,但是不能这样做。我还尝试对所有的tjava都使用,并且在每个tjava上都做了onSubjob ok。我如何在Talend中调用这些类并调用方法呢?