();
24 | mappings.put(getSpecializedIndexName(), params.getProperty(getSpecializedIndexSuffix() + ".mappings"));
25 | endpoint.getIndexAdminService().createIndex(getSpecializedIndexName(), shards, replicas, mappings);
26 | }
27 |
28 | /**
29 | * @return A {@link Client} connected to elasticsearch to execute requests.
30 | */
31 | protected Client getClient() {
32 | return endpoint.getClient();
33 | }
34 |
35 | /**
36 | * @return An {@link EntityDao} instance to ease the access to the main
37 | * entity index.
38 | */
39 | protected EntityDao getEntityDao() {
40 | return endpoint.getEntityDao();
41 | }
42 |
43 | /**
44 | * @return A {@link Parameters} object to access plugin's parameters.
45 | */
46 | protected Parameters getParameters() {
47 | return params;
48 | }
49 |
50 | /**
51 | * @return The specialized index name to use
52 | */
53 | public String getSpecializedIndexName() {
54 | return getEntityIndexName() + "-" + getSpecializedIndexSuffix();
55 | }
56 |
57 | /**
58 | * @return The Entity index name to use
59 | */
60 | protected String getEntityIndexName() {
61 | return params.getProperty(Parameters.INDEX_NAME);
62 | }
63 |
64 | /**
65 | * This method should return a short name describing the index to create.
66 | *
67 | * It will be appended to the indexName provided by the user.
68 | *
69 | * @return A {@link String}
70 | */
71 | public abstract String getSpecializedIndexSuffix();
72 |
73 | /**
74 | * This method should construct the specialized index.
75 | *
76 | * It is called after the OSM index was built and the specialized index was
77 | * created (using {@link #getSpecializedIndexSuffix()} and
78 | * {@link #getIndexConfig()} methods).
79 | */
80 | public abstract void buildIndex();
81 |
82 | }
83 |
--------------------------------------------------------------------------------
/src/main/java/org/openstreetmap/osmosis/plugin/elasticsearch/client/ElasticsearchClientBuilder.java:
--------------------------------------------------------------------------------
1 | package org.openstreetmap.osmosis.plugin.elasticsearch.client;
2 |
3 | import java.net.InetAddress;
4 | import java.net.UnknownHostException;
5 | import java.util.logging.Logger;
6 |
7 | import org.elasticsearch.action.admin.cluster.health.ClusterHealthResponse;
8 | import org.elasticsearch.client.Client;
9 | import org.elasticsearch.client.transport.TransportClient;
10 | import org.elasticsearch.common.settings.Settings;
11 | import org.elasticsearch.common.transport.InetSocketTransportAddress;
12 | import org.elasticsearch.node.Node;
13 | import org.elasticsearch.node.NodeBuilder;
14 |
15 | public class ElasticsearchClientBuilder {
16 |
17 | private static final Logger LOG = Logger.getLogger(ElasticsearchClientBuilder.class.getName());
18 |
19 | private String clusterName;
20 | private String hosts;
21 | private boolean nodeClient;
22 |
23 | private ElasticsearchClientBuilder() {}
24 |
25 | public static ElasticsearchClientBuilder newClient() {
26 | return new ElasticsearchClientBuilder();
27 | }
28 |
29 | public String getClusterName() {
30 | return clusterName;
31 | }
32 |
33 | public ElasticsearchClientBuilder setClusterName(String clusterName) {
34 | this.clusterName = clusterName;
35 | return this;
36 | }
37 |
38 | public String getHosts() {
39 | return hosts;
40 | }
41 |
42 | public ElasticsearchClientBuilder setHosts(String hosts) {
43 | this.hosts = hosts;
44 | return this;
45 | }
46 |
47 | public boolean isNodeClient() {
48 | return nodeClient;
49 | }
50 |
51 | public ElasticsearchClientBuilder setNodeClient(boolean nodeClient) {
52 | this.nodeClient = nodeClient;
53 | return this;
54 | }
55 |
56 | public Client build() {
57 | // Build the elasticsearch client
58 | Client client = nodeClient ? buildNodeClient() : buildTransportClient();
59 | // Ensure client is connected
60 | checkConnection(client);
61 | // Return valid client
62 | return client;
63 | }
64 |
65 | protected Client buildNodeClient() {
66 | LOG.info(String.format("Connecting to elasticsearch cluster '%s' via [%s]" +
67 | " using NodeClient", clusterName, hosts));
68 | // Connect as NodeClient (member of the cluster), see Gists:
69 | // https://gist.github.com/2491022 and https://gist.github.com/2491022
70 | // http://www.elasticsearch.org/guide/reference/modules/discovery/zen.html
71 | Settings settings = Settings.settingsBuilder()
72 | .put("node.local", false) // Disable local JVM discovery
73 | .put("node.data", false) // Disable data on this node
74 | .put("node.master", false) // Never elected as master
75 | .put("node.client", true) // Various client optim
76 | .put("cluster.name", clusterName) // Join clusterName
77 | .put("discovery.type", "zen") // Use zen discovery
78 | // Connect to 1 master node min
79 | .put("discovery.zen.minimum_master_nodes", 1)
80 | // Disable multicast discovery
81 | .put("discovery.zen.ping.multicast.enabled", false)
82 | // Add one or more host to join
83 | .putArray("discovery.zen.ping.unicast.hosts", hosts.split(","))
84 | .build();
85 | Node node = NodeBuilder.nodeBuilder()
86 | .settings(settings)
87 | .node();
88 | return node.client();
89 | }
90 |
91 | protected Client buildTransportClient() {
92 | LOG.info(String.format("Connecting to elasticsearch cluster '%s' via [%s]" +
93 | " using TransportClient", clusterName, hosts));
94 | // Connect as TransportClient (proxy of the cluster)
95 | Settings settings = Settings.settingsBuilder()
96 | .put("cluster.name", clusterName)
97 | .put("client.transport.sniff", true)
98 | .build();
99 | TransportClient transportClient = TransportClient.builder().settings(settings).build();
100 | // Add specified TransportAddresses
101 | for (String host : hosts.split(",")) {
102 | String[] params = host.split(":");
103 | String hostname = params[0];
104 | int port = (params.length == 2) ? Integer.valueOf(params[1]) : 9300;
105 | try {
106 | transportClient.addTransportAddress(new InetSocketTransportAddress(InetAddress.getByName(hostname), port));
107 | } catch (UnknownHostException e) {
108 | // TODO Auto-generated catch block
109 | e.printStackTrace();
110 | }
111 | }
112 | return transportClient;
113 | }
114 |
115 | protected void checkConnection(Client client) {
116 | ClusterHealthResponse health = client.admin().cluster()
117 | .prepareHealth().execute().actionGet();
118 | if (health.getNumberOfDataNodes() == 0) throw new RuntimeException("Unable to connect to elasticsearch");
119 | LOG.info(String.format("Connected to %d data node(s) with cluster status %s",
120 | health.getNumberOfDataNodes(), health.getStatus().name()));
121 | }
122 |
123 | }
124 |
--------------------------------------------------------------------------------
/src/main/java/org/openstreetmap/osmosis/plugin/elasticsearch/dao/DaoException.java:
--------------------------------------------------------------------------------
1 | package org.openstreetmap.osmosis.plugin.elasticsearch.dao;
2 |
3 | public class DaoException extends RuntimeException {
4 |
5 | private static final long serialVersionUID = 6120808051925518379L;
6 |
7 | public DaoException() {
8 | super();
9 | }
10 |
11 | public DaoException(String message) {
12 | super(message);
13 | }
14 |
15 | public DaoException(Throwable throwable) {
16 | super(throwable);
17 | }
18 |
19 | public DaoException(String message, Throwable throwable) {
20 | super(message, throwable);
21 | }
22 |
23 | }
--------------------------------------------------------------------------------
/src/main/java/org/openstreetmap/osmosis/plugin/elasticsearch/dao/EntityDao.java:
--------------------------------------------------------------------------------
1 | package org.openstreetmap.osmosis.plugin.elasticsearch.dao;
2 |
3 | import java.util.*;
4 | import java.util.logging.Logger;
5 |
6 | import org.elasticsearch.action.bulk.BulkItemResponse;
7 | import org.elasticsearch.action.bulk.BulkRequestBuilder;
8 | import org.elasticsearch.action.bulk.BulkResponse;
9 | import org.elasticsearch.action.get.GetResponse;
10 | import org.elasticsearch.action.get.MultiGetItemResponse;
11 | import org.elasticsearch.action.get.MultiGetRequest.Item;
12 | import org.elasticsearch.action.get.MultiGetRequestBuilder;
13 | import org.elasticsearch.action.get.MultiGetResponse;
14 | import org.elasticsearch.client.Client;
15 | import org.openstreetmap.osmosis.core.domain.v0_6.*;
16 | import org.openstreetmap.osmosis.plugin.elasticsearch.model.entity.ESEntity;
17 | import org.openstreetmap.osmosis.plugin.elasticsearch.model.entity.ESEntityType;
18 | import org.openstreetmap.osmosis.plugin.elasticsearch.model.entity.ESNode;
19 | import org.openstreetmap.osmosis.plugin.elasticsearch.model.entity.ESWay;
20 | import org.openstreetmap.osmosis.plugin.elasticsearch.model.shape.ESShape;
21 | import org.openstreetmap.osmosis.plugin.elasticsearch.model.shape.ESShape.ESShapeBuilder;
22 |
23 | public class EntityDao {
24 |
25 | private static final Logger LOG = Logger.getLogger(EntityDao.class.getName());
26 |
27 | private final String indexName;
28 | private final Client client;
29 |
30 | public EntityDao(String indexName, Client client) {
31 | this.indexName = indexName;
32 | this.client = client;
33 | }
34 |
35 | /**
36 | * Save (index) an OSM Entity.
37 | *
38 | * Warning: please note that saving {@link Relation} and
39 | * {@link Bound} is not yet supported. Trying to save such {@link Entity}
40 | * causes this method to throw an {@link DaoException}.
41 | *
42 | * @param entity
43 | * the Entity object to save
44 | * @throws DaoException
45 | * if something was wrong during the save process
46 | */
47 | public void save(Entity entity) {
48 | if (entity == null) throw new IllegalArgumentException("You must provide a non-null Entity");
49 | saveAll(Arrays.asList(entity));
50 | }
51 |
52 | /**
53 | * Save (index) all OSM Entities using a bulk request.
54 | *
55 | * All errors caught during the bulk request building or entities indexing
56 | * are handled silently, i.e. logged and ignored.
57 | *
58 | * Warning: please note that saving {@link Relation} and
59 | * {@link Bound} is not yet supported. Trying to save such {@link Entity}
60 | * causes this method to ignore it silently.
61 | *
62 | * @param entities
63 | * the List of Entity objects to save
64 | * @throws DaoException
65 | * if something was wrong during the save process
66 | */
67 | public void saveAll(List entities) {
68 | if (entities == null || entities.isEmpty()) return;
69 | List nodes = new ArrayList();
70 | List ways = new ArrayList();
71 | for (T entity : entities) {
72 | if (entity == null) continue;
73 | switch (entity.getType()) {
74 | case Node:
75 | nodes.add((Node) entity);
76 | break;
77 | case Way:
78 | ways.add((Way) entity);
79 | break;
80 | case Relation:
81 | case Bound:
82 | default:
83 | LOG.warning(String.format("Unable to add Entity %s to bulk request, " +
84 | "cause: save %s is not yet supported", entity, entity.getType()));
85 | }
86 | }
87 | if (!nodes.isEmpty()) saveAllNodes(nodes);
88 | if (!ways.isEmpty()) saveAllWays(ways);
89 | }
90 |
91 | protected void saveAllNodes(List nodes) {
92 | BulkRequestBuilder bulkRequest = client.prepareBulk();
93 | for (Node node : nodes) {
94 | try {
95 | ESNode esNode = ESNode.Builder.buildFromEntity(node);
96 | bulkRequest.add(client.prepareIndex(indexName, esNode.getEntityType().getIndiceName(), esNode.getIdString())
97 | .setSource(esNode.toJson()));
98 | } catch (Exception exception) {
99 | LOG.warning(String.format("Unable to add Entity %s to bulk request, cause: %s",
100 | node.getId(), exception.getMessage()));
101 | }
102 | }
103 | executeBulkRequest(bulkRequest);
104 | }
105 |
106 | protected void saveAllWays(List ways) {
107 | Iterator iterator = getNodeItems(ways);
108 | BulkRequestBuilder bulkRequest = client.prepareBulk();
109 | for (Way way : ways) {
110 | try {
111 | int size = way.getWayNodes().size();
112 | ESShape shape = getShape(iterator, size);
113 | ESWay esWay = ESWay.Builder.buildFromEntity(way, shape);
114 | bulkRequest.add(client.prepareIndex(indexName, esWay.getEntityType().getIndiceName(), esWay.getIdString())
115 | .setSource(esWay.toJson()));
116 | } catch (Exception e) {
117 | LOG.warning(String.format("Unable to add Entity %s to bulk request, cause: %s",
118 | way.getId(), e.getMessage()));
119 | }
120 | }
121 | executeBulkRequest(bulkRequest);
122 | }
123 |
124 | protected Iterator getNodeItems(List ways) {
125 | MultiGetRequestBuilder request = client.prepareMultiGet();
126 | for (Way way : ways) {
127 | for (WayNode wayNode : way.getWayNodes()) {
128 | request.add(new Item(indexName, ESEntityType.NODE.getIndiceName(),
129 | String.valueOf(wayNode.getNodeId())));
130 | }
131 | }
132 | MultiGetResponse responses = request.execute().actionGet();
133 | Iterator iterator = responses.iterator();
134 | return iterator;
135 | }
136 |
137 | protected ESShape getShape(Iterator iterator, int size) {
138 | ESShapeBuilder shapeBuilder = new ESShapeBuilder(size);
139 | for (int i = 0; i < size; i++) {
140 | GetResponse response = iterator.next().getResponse();
141 | if (!response.isExists()) continue;
142 | @SuppressWarnings("unchecked")
143 | Map shape = (Map) response.getSource().get("shape");
144 | @SuppressWarnings("unchecked")
145 | List coordinates = (List) shape.get("coordinates");
146 | shapeBuilder.addLocation(coordinates.get(1), coordinates.get(0));
147 | }
148 | return shapeBuilder.build();
149 | }
150 |
151 | protected void executeBulkRequest(BulkRequestBuilder bulkRequest) {
152 | if (bulkRequest.numberOfActions() == 0) return;
153 | BulkResponse bulkResponse = bulkRequest.execute().actionGet();
154 | if (!bulkResponse.hasFailures()) return;
155 | for (BulkItemResponse response : bulkResponse) {
156 | if (!response.isFailed()) continue;
157 | LOG.warning(String.format("Unable to save Entity %s in %s/%s, cause: %s",
158 | response.getId(), response.getIndex(), response.getType(), response.getFailureMessage()));
159 | }
160 | }
161 |
162 | /**
163 | * Find an OSM entity.
164 | *
165 | * Warning: please note that finding {@link Relation} and
166 | * {@link Bound} is not yet supported. Trying to find such {@link Entity}
167 | * causes this method to throw an {@link UnsupportedOperationException}.
168 | *
169 | * @param entityClass
170 | * the class (among {@link Node}, {@link Way}, {@link Relation}
171 | * and {@link Bound}) of the Entity
172 | * @param osmId
173 | * the OSM id that identifies the Entity
174 | * @return The Entity object, null if not found
175 | * @throws IllegalArgumentException
176 | * if the provided entityClass is null or invalid
177 | * @throws DaoException
178 | * if something was wrong during the elasticsearch request
179 | */
180 | public T find(Class entityClass, long osmId) {
181 | return findAll(entityClass, osmId).get(0);
182 | }
183 |
184 | /**
185 | * Find all OSM entities.
186 | *
187 | * Warning: all objects are retrieved from elasticsearch and mounted
188 | * in memory. In case of large OSM data sets, ensure you have allocated
189 | * enough heap. If you already know what ids to retrieve, please consider
190 | * the {@link #findAll(Class, long...)} method instead.
191 | *
192 | * Warning: please note that finding all {@link Relation} and
193 | * {@link Bound} is not yet supported. Trying to find such {@link Entity}
194 | * causes this method to throw an {@link UnsupportedOperationException}.
195 | *
196 | * @param entityClass
197 | * the class (among {@link Node}, {@link Way}, {@link Relation}
198 | * and {@link Bound}) of the Entities
199 | * @param osmIds
200 | * an array of OSM id that identifies the Entities. if null, all
201 | * Entities will be retrieved (be aware of your heap size)
202 | * @return The Entity objects as list if all ids was found
203 | * @throws IllegalArgumentException
204 | * if the provided entityClass is null or invalid
205 | * @throws DaoException
206 | * if something was wrong during the elasticsearch request
207 | */
208 | public List findAll(Class entityClass, long... osmIds) {
209 | if (osmIds == null || osmIds.length == 0) return Collections.unmodifiableList(new ArrayList(0));
210 | try {
211 | MultiGetRequestBuilder request = buildMultiGetRequest(entityClass, osmIds);
212 | return executeMultiGetRequest(entityClass, request);
213 | } catch (Exception e) {
214 | if (e instanceof DaoException) throw (DaoException) e;
215 | String indiceName = ESEntityType.valueOf(entityClass).getIndiceName();
216 | throw new DaoException("Unable to find all " + indiceName + " entities", e);
217 | }
218 | }
219 |
220 | protected MultiGetRequestBuilder buildMultiGetRequest(Class entityClass, long... osmIds) {
221 | ESEntityType type = ESEntityType.valueOf(entityClass);
222 | MultiGetRequestBuilder request = client.prepareMultiGet();
223 | for (long osmId : osmIds) {
224 | request.add(new Item(indexName, type.getIndiceName(), String.valueOf(osmId)));
225 | }
226 | return request;
227 | }
228 |
229 | protected List executeMultiGetRequest(Class entityClass, MultiGetRequestBuilder request) {
230 | MultiGetResponse responses = request.execute().actionGet();
231 | List entities = new ArrayList();
232 | for (MultiGetItemResponse item : responses) {
233 | entities.add(buildEntityFromGetResponse(entityClass, item));
234 | }
235 | return Collections.unmodifiableList(entities);
236 | }
237 |
238 | @SuppressWarnings("unchecked")
239 | protected T buildEntityFromGetResponse(Class entityClass, MultiGetItemResponse item) {
240 | GetResponse response = item.getResponse();
241 | if (!response.isExists()) throw new DaoException(String.format(
242 | "Entity %s does not exist in %s/%s", response.getId(),
243 | response.getIndex(), response.getType()));
244 | if (entityClass == null) throw new IllegalArgumentException("Provided Entity class is null");
245 | else if (entityClass.equals(ESNode.class)) return (T) ESNode.Builder.buildFromGetReponse(response);
246 | else if (entityClass.equals(ESWay.class)) return (T) ESWay.Builder.buildFromGetReponse(response);
247 | else throw new IllegalArgumentException(entityClass.getSimpleName() + " is not a known Entity");
248 | }
249 |
250 | /**
251 | * Delete an OSM entity.
252 | *
253 | * Warning: please note that deleting {@link Relation} and
254 | * {@link Bound} is not yet supported. Trying to delete such {@link Entity}
255 | * causes this method to throw an {@link UnsupportedOperationException}.
256 | *
257 | * @param osmId
258 | * the OSM id that identifies the Entity
259 | * @param entityClass
260 | * the class (among {@link Node}, {@link Way}, {@link Relation}
261 | * and {@link Bound}) of the Entity
262 | * @return True if the Entity was deleted, false otherwise (i.e. the Entity
263 | * was not found)
264 | * @throws IllegalArgumentException
265 | * if the provided entityClass is null or invalid
266 | * @throws DaoException
267 | * if something was wrong during the elasticsearch request
268 | */
269 | public boolean delete(Class entityClass, long osmId) {
270 | try {
271 | String indiceName = ESEntityType.valueOf(entityClass).getIndiceName();
272 | return client.prepareDelete(indexName, indiceName, Long.toString(osmId))
273 | .execute().actionGet().isFound();
274 | } catch (Exception e) {
275 | String indiceName = ESEntityType.valueOf(entityClass).getIndiceName();
276 | String message = String.format("Unable to delete entity %s in %s/%s",
277 | osmId, indexName, indiceName);
278 | throw new DaoException(message, e);
279 | }
280 | }
281 |
282 | }
283 |
--------------------------------------------------------------------------------
/src/main/java/org/openstreetmap/osmosis/plugin/elasticsearch/model/entity/ESEntity.java:
--------------------------------------------------------------------------------
1 | package org.openstreetmap.osmosis.plugin.elasticsearch.model.entity;
2 |
3 | import java.util.HashMap;
4 | import java.util.Map;
5 |
6 | import org.openstreetmap.osmosis.core.domain.v0_6.Entity;
7 | import org.openstreetmap.osmosis.core.domain.v0_6.Tag;
8 | import org.openstreetmap.osmosis.plugin.elasticsearch.model.shape.ESLocation;
9 | import org.openstreetmap.osmosis.plugin.elasticsearch.model.shape.ESShapeType;
10 |
11 | public abstract class ESEntity {
12 |
13 | private final long id;
14 | private final Map tags;
15 |
16 | protected ESEntity(Entity entity) {
17 | this.id = entity.getId();
18 | this.tags = new HashMap();
19 | for (Tag tag : entity.getTags()) {
20 | this.tags.put(tag.getKey(), tag.getValue());
21 | }
22 | }
23 |
24 | protected ESEntity(long id, Map tags) {
25 | this.id = id;
26 | this.tags = tags;
27 | }
28 |
29 | public abstract ESEntityType getEntityType();
30 |
31 | public abstract ESShapeType getShapeType();
32 |
33 | public abstract ESLocation getCentroid();
34 |
35 | public abstract double getLenght();
36 |
37 | public abstract double getArea();
38 |
39 | public abstract String toJson();
40 |
41 | public long getId() {
42 | return id;
43 | }
44 |
45 | public String getIdString() {
46 | return Long.toString(id);
47 | }
48 |
49 | public Map getTags() {
50 | return tags;
51 | }
52 |
53 | @Override
54 | public int hashCode() {
55 | final int prime = 31;
56 | int result = 1;
57 | result = prime * result + (int) (id ^ (id >>> 32));
58 | result = prime * result + ((tags == null) ? 0 : tags.hashCode());
59 | return result;
60 | }
61 |
62 | @Override
63 | public boolean equals(Object obj) {
64 | if (this == obj) return true;
65 | if (obj == null) return false;
66 | if (getClass() != obj.getClass()) return false;
67 | ESEntity other = (ESEntity) obj;
68 | if (id != other.id) return false;
69 | if (tags == null) {
70 | if (other.tags != null) return false;
71 | } else if (!tags.equals(other.tags)) return false;
72 | return true;
73 | }
74 |
75 | }
76 |
--------------------------------------------------------------------------------
/src/main/java/org/openstreetmap/osmosis/plugin/elasticsearch/model/entity/ESEntityType.java:
--------------------------------------------------------------------------------
1 | package org.openstreetmap.osmosis.plugin.elasticsearch.model.entity;
2 |
3 | public enum ESEntityType {
4 |
5 | BOUND, NODE, WAY, RELATION;
6 |
7 | public String getIndiceName() {
8 | return this.name().toLowerCase();
9 | }
10 |
11 | public static ESEntityType valueOf(Class entityClass) {
12 | if (entityClass == null) throw new IllegalArgumentException("Provided Entity class is null");
13 | else if (entityClass.equals(ESNode.class)) return NODE;
14 | else if (entityClass.equals(ESWay.class)) return WAY;
15 | else throw new IllegalArgumentException(entityClass.getSimpleName() + " is not a valid Entity");
16 | }
17 |
18 | }
19 |
--------------------------------------------------------------------------------
/src/main/java/org/openstreetmap/osmosis/plugin/elasticsearch/model/entity/ESNode.java:
--------------------------------------------------------------------------------
1 | package org.openstreetmap.osmosis.plugin.elasticsearch.model.entity;
2 |
3 | import static org.elasticsearch.common.xcontent.XContentFactory.jsonBuilder;
4 |
5 | import java.io.IOException;
6 | import java.util.HashMap;
7 | import java.util.List;
8 | import java.util.Map;
9 |
10 | import org.elasticsearch.action.get.GetResponse;
11 | import org.elasticsearch.common.xcontent.XContentBuilder;
12 | import org.openstreetmap.osmosis.core.domain.v0_6.Node;
13 | import org.openstreetmap.osmosis.plugin.elasticsearch.model.shape.ESLocation;
14 | import org.openstreetmap.osmosis.plugin.elasticsearch.model.shape.ESShapeType;
15 |
16 | public class ESNode extends ESEntity {
17 |
18 | private final double latitude;
19 | private final double longitude;
20 |
21 | private ESNode(Node node) {
22 | super(node);
23 | this.latitude = node.getLatitude();
24 | this.longitude = node.getLongitude();
25 | }
26 |
27 | private ESNode(Builder builder) {
28 | super(builder.id, builder.tags);
29 | this.latitude = builder.latitude;
30 | this.longitude = builder.longitude;
31 | }
32 |
33 | @Override
34 | public ESEntityType getEntityType() {
35 | return ESEntityType.NODE;
36 | }
37 |
38 | @Override
39 | public ESShapeType getShapeType() {
40 | return ESShapeType.POINT;
41 | }
42 |
43 | @Override
44 | public ESLocation getCentroid() {
45 | return new ESLocation(latitude, longitude);
46 | }
47 |
48 | @Override
49 | public double getLenght() {
50 | return 0;
51 | }
52 |
53 | @Override
54 | public double getArea() {
55 | return 0;
56 | }
57 |
58 | public double getLatitude() {
59 | return latitude;
60 | }
61 |
62 | public double getLongitude() {
63 | return longitude;
64 | }
65 |
66 | @Override
67 | public String toJson() {
68 | XContentBuilder builder = null;
69 | try {
70 | builder = jsonBuilder();
71 | builder.startObject();
72 | builder.field("centroid", new double[] { longitude, latitude });
73 | builder.startObject("shape")
74 | .field("type", "point")
75 | .field("coordinates", new double[] { longitude, latitude })
76 | .endObject();
77 | builder.field("tags", getTags());
78 | builder.endObject();
79 | return builder.string();
80 | } catch (IOException e) {
81 | throw new RuntimeException("Unable to serialize Node to Json", e);
82 | } finally {
83 | if (builder != null) builder.close();
84 | }
85 | }
86 |
87 | @Override
88 | public int hashCode() {
89 | final int prime = 31;
90 | int result = super.hashCode();
91 | long temp;
92 | temp = Double.doubleToLongBits(latitude);
93 | result = prime * result + (int) (temp ^ (temp >>> 32));
94 | temp = Double.doubleToLongBits(longitude);
95 | result = prime * result + (int) (temp ^ (temp >>> 32));
96 | return result;
97 | }
98 |
99 | @Override
100 | public boolean equals(Object obj) {
101 | if (this == obj) return true;
102 | if (!super.equals(obj)) return false;
103 | if (getClass() != obj.getClass()) return false;
104 | ESNode other = (ESNode) obj;
105 | if (Double.doubleToLongBits(latitude) != Double.doubleToLongBits(other.latitude)) return false;
106 | if (Double.doubleToLongBits(longitude) != Double.doubleToLongBits(other.longitude)) return false;
107 | return true;
108 | }
109 |
110 | @Override
111 | public String toString() {
112 | StringBuilder builder = new StringBuilder();
113 | builder.append("ESNode [id=");
114 | builder.append(getId());
115 | builder.append(", lat=");
116 | builder.append(latitude);
117 | builder.append(", lon=");
118 | builder.append(longitude);
119 | builder.append(", tags=");
120 | builder.append(getTags());
121 | builder.append("]");
122 | return builder.toString();
123 | }
124 |
125 | public static class Builder {
126 |
127 | private long id;
128 | private double latitude;
129 | private double longitude;
130 | private Map tags = new HashMap();
131 |
132 | private Builder() {}
133 |
134 | public static Builder create() {
135 | return new Builder();
136 | }
137 |
138 | @SuppressWarnings("unchecked")
139 | public static ESNode buildFromGetReponse(GetResponse response) {
140 | if (!response.getType().equals(ESEntityType.NODE.getIndiceName())) throw new IllegalArgumentException("Provided GetResponse is not a Node");
141 | Builder builder = new Builder();
142 | builder.id = Long.valueOf(response.getId());
143 | builder.tags = (Map) response.getSource().get("tags");
144 | Map shape = (Map) response.getSource().get("shape");
145 | List location = (List) shape.get("coordinates");
146 | builder.latitude = location.get(1);
147 | builder.longitude = location.get(0);
148 | return builder.build();
149 | }
150 |
151 | public static ESNode buildFromEntity(Node node) {
152 | return new ESNode(node);
153 | }
154 |
155 | public Builder id(long id) {
156 | this.id = id;
157 | return this;
158 | }
159 |
160 | public Builder location(double latitude, double longitude) {
161 | this.latitude = latitude;
162 | this.longitude = longitude;
163 | return this;
164 | }
165 |
166 | public Builder addTag(String key, String value) {
167 | this.tags.put(key, value);
168 | return this;
169 | }
170 |
171 | public ESNode build() {
172 | return new ESNode(this);
173 | }
174 |
175 | }
176 |
177 | }
178 |
--------------------------------------------------------------------------------
/src/main/java/org/openstreetmap/osmosis/plugin/elasticsearch/model/entity/ESWay.java:
--------------------------------------------------------------------------------
1 | package org.openstreetmap.osmosis.plugin.elasticsearch.model.entity;
2 |
3 | import static org.elasticsearch.common.xcontent.XContentFactory.jsonBuilder;
4 |
5 | import java.io.IOException;
6 | import java.util.HashMap;
7 | import java.util.List;
8 | import java.util.Map;
9 |
10 | import org.elasticsearch.action.get.GetResponse;
11 | import org.elasticsearch.common.xcontent.XContentBuilder;
12 | import org.openstreetmap.osmosis.core.domain.v0_6.Way;
13 | import org.openstreetmap.osmosis.plugin.elasticsearch.model.shape.ESLocation;
14 | import org.openstreetmap.osmosis.plugin.elasticsearch.model.shape.ESShape;
15 | import org.openstreetmap.osmosis.plugin.elasticsearch.model.shape.ESShape.ESShapeBuilder;
16 | import org.openstreetmap.osmosis.plugin.elasticsearch.model.shape.ESShapeType;
17 |
18 | public class ESWay extends ESEntity {
19 |
20 | private final ESShape shape;
21 |
22 | private ESWay(Way way, ESShape shape) {
23 | super(way);
24 | double[][] locations = shape.getGeoJsonArray();
25 | if (locations.length != way.getWayNodes().size()) throw new IllegalArgumentException(String.format(
26 | "Incorrect size! WayNodes: %d, Shape: %d", way.getWayNodes().size(), locations.length));
27 | this.shape = shape;
28 | }
29 |
30 | private ESWay(Builder builder) {
31 | super(builder.id, builder.tags);
32 | this.shape = builder.shape;
33 | }
34 |
35 | @Override
36 | public ESEntityType getEntityType() {
37 | return ESEntityType.WAY;
38 | }
39 |
40 | public double[][] getCoordinates(){
41 | return shape.getGeoJsonArray();
42 | }
43 |
44 | @Override
45 | public ESShapeType getShapeType() {
46 | return shape.getShapeType();
47 | }
48 |
49 | @Override
50 | public ESLocation getCentroid() {
51 | return shape.getCentroid();
52 | }
53 |
54 | @Override
55 | public double getArea() {
56 | return shape.getAreaKm2();
57 | }
58 |
59 | @Override
60 | public double getLenght() {
61 | return shape.getLengthKm();
62 | }
63 |
64 | @Override
65 | public String toJson() {
66 | XContentBuilder builder = null;
67 | try {
68 | builder = jsonBuilder();
69 | builder.startObject();
70 | ESLocation centroid = shape.getCentroid();
71 | builder.field("centroid", new double[] { centroid.getLongitude(), centroid.getLatitude() });
72 | builder.field("lengthKm", shape.getLengthKm());
73 | builder.field("areaKm2", shape.getAreaKm2());
74 | builder.startObject("shape");
75 | builder.field("type", shape.isClosed() ? "polygon" : "linestring");
76 | builder.startArray("coordinates");
77 | if (shape.isClosed()) builder.startArray();
78 | for (double[] location : shape.getGeoJsonArray()) {
79 | builder.startArray().value(location[0]).value(location[1]).endArray();
80 | }
81 | if (shape.isClosed()) builder.endArray();
82 | builder.endArray();
83 | builder.endObject();
84 | builder.field("tags", getTags());
85 | builder.endObject();
86 | return builder.string();
87 | } catch (IOException e) {
88 | throw new RuntimeException("Unable to serialize Way to Json", e);
89 | } finally {
90 | if (builder != null) builder.close();
91 | }
92 | }
93 |
94 | @Override
95 | public int hashCode() {
96 | final int prime = 31;
97 | int result = super.hashCode();
98 | result = prime * result + ((shape == null) ? 0 : shape.hashCode());
99 | return result;
100 | }
101 |
102 | @Override
103 | public boolean equals(Object obj) {
104 | if (this == obj) return true;
105 | if (!super.equals(obj)) return false;
106 | if (getClass() != obj.getClass()) return false;
107 | ESWay other = (ESWay) obj;
108 | if (shape == null) {
109 | if (other.shape != null) return false;
110 | } else if (!shape.equals(other.shape)) return false;
111 | return true;
112 | }
113 |
114 | @Override
115 | public String toString() {
116 | StringBuilder builder = new StringBuilder();
117 | builder.append("ESWay [id=");
118 | builder.append(getId());
119 | builder.append(", shape=");
120 | builder.append(shape);
121 | builder.append(", tags=");
122 | builder.append(getTags());
123 | builder.append("]");
124 | return builder.toString();
125 | }
126 |
127 | public static class Builder {
128 |
129 | private ESShapeBuilder shapeBuilder = new ESShapeBuilder();
130 |
131 | private long id;
132 | private ESShape shape;
133 | private Map tags = new HashMap();
134 |
135 | private Builder() {}
136 |
137 | public static Builder create() {
138 | return new Builder();
139 | }
140 |
141 | @SuppressWarnings("unchecked")
142 | public static ESWay buildFromGetReponse(GetResponse response) {
143 | if (!response.getType().equals(ESEntityType.WAY.getIndiceName())) throw new IllegalArgumentException("Provided GetResponse is not a Way");
144 |
145 | Builder builder = new Builder();
146 | builder.id = Long.valueOf(response.getId());
147 | builder.tags = (Map) response.getSource().get("tags");
148 | Map shape = (Map) response.getSource().get("shape");
149 | String type = (String) shape.get("type");
150 | if ("linestring".equals(type)) {
151 | List> locations = (List>) shape.get("coordinates");
152 | for (List location : locations) {
153 | builder.addLocation(location.get(1), location.get(0));
154 | }
155 | } else {
156 | List>> locations = (List>>) shape.get("coordinates");
157 | for (List location : locations.get(0)) {
158 | builder.addLocation(location.get(1), location.get(0));
159 | }
160 | }
161 |
162 | List centroid = (List) response.getSource().get("centroid");
163 | builder.shapeBuilder.setCentroid(new ESLocation(centroid.get(1), centroid.get(0)));
164 | Double length = (Double) response.getSource().get("lengthKm");
165 | builder.shapeBuilder.setLength(length);
166 | Double area = (Double) response.getSource().get("areaKm2");
167 | builder.shapeBuilder.setArea(area);
168 |
169 | builder.shape = builder.shapeBuilder.buildFast();
170 | return new ESWay(builder);
171 | }
172 |
173 | public static ESWay buildFromEntity(Way way, ESShape locationArrayBuilder) {
174 | return new ESWay(way, locationArrayBuilder);
175 | }
176 |
177 | public Builder id(long id) {
178 | this.id = id;
179 | return this;
180 | }
181 |
182 | public Builder addLocation(double latitude, double longitude) {
183 | shapeBuilder.addLocation(latitude, longitude);
184 | return this;
185 | }
186 |
187 | public Builder addTag(String key, String value) {
188 | this.tags.put(key, value);
189 | return this;
190 | }
191 |
192 | public ESWay build() {
193 | this.shape = shapeBuilder.build();
194 | return new ESWay(this);
195 | }
196 |
197 | }
198 |
199 | }
200 |
--------------------------------------------------------------------------------
/src/main/java/org/openstreetmap/osmosis/plugin/elasticsearch/model/shape/ESLocation.java:
--------------------------------------------------------------------------------
1 | package org.openstreetmap.osmosis.plugin.elasticsearch.model.shape;
2 |
3 | public class ESLocation {
4 |
5 | private final double latitude;
6 | private final double longitude;
7 |
8 | public ESLocation(double latitude, double longitude) {
9 | this.latitude = latitude;
10 | this.longitude = longitude;
11 | }
12 |
13 | public ESLocation(double[] geoJsonArray) {
14 | if (geoJsonArray.length != 2) throw new IllegalArgumentException("Invalid array");
15 | this.latitude = geoJsonArray[1];
16 | this.longitude = geoJsonArray[0];
17 | }
18 |
19 | public double getLatitude() {
20 | return latitude;
21 | }
22 |
23 | public double getLongitude() {
24 | return longitude;
25 | }
26 |
27 | public double[] toGeoJsonArray() {
28 | return new double[] { longitude, latitude };
29 | }
30 |
31 | @Override
32 | public int hashCode() {
33 | final int prime = 31;
34 | int result = 1;
35 | long temp;
36 | temp = Double.doubleToLongBits(latitude);
37 | result = prime * result + (int) (temp ^ (temp >>> 32));
38 | temp = Double.doubleToLongBits(longitude);
39 | result = prime * result + (int) (temp ^ (temp >>> 32));
40 | return result;
41 | }
42 |
43 | @Override
44 | public boolean equals(Object obj) {
45 | if (this == obj) return true;
46 | if (obj == null) return false;
47 | if (getClass() != obj.getClass()) return false;
48 | ESLocation other = (ESLocation) obj;
49 | if (Double.doubleToLongBits(latitude) != Double.doubleToLongBits(other.latitude)) return false;
50 | if (Double.doubleToLongBits(longitude) != Double.doubleToLongBits(other.longitude)) return false;
51 | return true;
52 | }
53 |
54 | @Override
55 | public String toString() {
56 | return "Location [latitude=" + latitude + ", longitude=" + longitude + "]";
57 | }
58 |
59 | }
60 |
--------------------------------------------------------------------------------
/src/main/java/org/openstreetmap/osmosis/plugin/elasticsearch/model/shape/ESShape.java:
--------------------------------------------------------------------------------
1 | package org.openstreetmap.osmosis.plugin.elasticsearch.model.shape;
2 |
3 | import java.util.ArrayList;
4 | import java.util.Arrays;
5 | import java.util.List;
6 |
7 | import com.spatial4j.core.distance.DistanceUtils;
8 | import com.vividsolutions.jts.geom.*;
9 |
10 | import static org.elasticsearch.common.geo.builders.ShapeBuilder.SPATIAL_CONTEXT;
11 |
12 | public class ESShape {
13 |
14 | private final ESShapeType esShapeType;
15 | private final ESLocation centroid;
16 | private final double length;
17 | private final double area;
18 | private final double[][] geoJsonArray;
19 |
20 | private ESShape(ESShapeBuilder builder) {
21 | this.esShapeType = builder.esShapeType;
22 | this.area = builder.area;
23 | this.length = builder.length;
24 | this.centroid = builder.centroid;
25 | this.geoJsonArray = builder.geoJsonArray;
26 | }
27 |
28 | public ESShapeType getShapeType() {
29 | return esShapeType;
30 | }
31 |
32 | public boolean isClosed() {
33 | switch (esShapeType) {
34 | case POINT:
35 | return true;
36 | case LINESTRING:
37 | return false;
38 | case POLYGON:
39 | return true;
40 | default:
41 | return false;
42 | }
43 | }
44 |
45 | public ESLocation getCentroid() {
46 | return centroid;
47 | }
48 |
49 | public double getLengthKm() {
50 | return length;
51 | }
52 |
53 | public double getAreaKm2() {
54 | return area;
55 | }
56 |
57 | public double[][] getGeoJsonArray() {
58 | return geoJsonArray;
59 | }
60 |
61 | @Override
62 | public int hashCode() {
63 | final int prime = 31;
64 | int result = 1;
65 | long temp;
66 | temp = Double.doubleToLongBits(area);
67 | result = prime * result + (int) (temp ^ (temp >>> 32));
68 | result = prime * result + ((centroid == null) ? 0 : centroid.hashCode());
69 | result = prime * result + ((esShapeType == null) ? 0 : esShapeType.hashCode());
70 | result = prime * result + Arrays.hashCode(geoJsonArray);
71 | temp = Double.doubleToLongBits(length);
72 | result = prime * result + (int) (temp ^ (temp >>> 32));
73 | return result;
74 | }
75 |
76 | @Override
77 | public boolean equals(Object obj) {
78 | if (this == obj) return true;
79 | if (obj == null) return false;
80 | if (getClass() != obj.getClass()) return false;
81 | ESShape other = (ESShape) obj;
82 | if (Double.doubleToLongBits(area) != Double.doubleToLongBits(other.area)) return false;
83 | if (centroid == null) {
84 | if (other.centroid != null) return false;
85 | } else if (!centroid.equals(other.centroid)) return false;
86 | if (esShapeType != other.esShapeType) return false;
87 | if (!Arrays.deepEquals(geoJsonArray, other.geoJsonArray)) return false;
88 | if (Double.doubleToLongBits(length) != Double.doubleToLongBits(other.length)) return false;
89 | return true;
90 | }
91 |
92 | @Override
93 | public String toString() {
94 | StringBuilder builder = new StringBuilder();
95 | builder.append("ESShape [esShapeType=");
96 | builder.append(esShapeType);
97 | builder.append(", isClosed=");
98 | builder.append(isClosed());
99 | builder.append(", centroid=");
100 | builder.append(centroid);
101 | builder.append(", lenght=");
102 | builder.append(length);
103 | builder.append(", area=");
104 | builder.append(area);
105 | builder.append(", geoJsonArray=");
106 | builder.append(Arrays.deepToString(geoJsonArray));
107 | builder.append("]");
108 | return builder.toString();
109 | }
110 |
111 | public static class ESShapeBuilder {
112 |
113 | private ESShapeType esShapeType;
114 | private double area;
115 | private double length;
116 | private ESLocation centroid;
117 | private double[][] geoJsonArray;
118 |
119 | /*
120 | * REGULAR BUILDER
121 | */
122 |
123 | public void setArea(double area) {
124 | this.area = area;
125 | }
126 |
127 | public void setLength(double length) {
128 | this.length = length;
129 | }
130 |
131 | public void setCentroid(ESLocation centroid) {
132 | this.centroid = centroid;
133 | }
134 |
135 | public ESShape buildFast() {
136 | this.esShapeType = getShapeType();
137 | this.geoJsonArray = toGeoJsonArray();
138 | return new ESShape(this);
139 | }
140 |
141 | /*
142 | * SPECIALIZED BUILDER (FROM LOCATIONS)
143 | */
144 |
145 | private final List locations;
146 |
147 | public ESShapeBuilder() {
148 | this.locations = new ArrayList();
149 | }
150 |
151 | public ESShapeBuilder(int size) {
152 | this.locations = new ArrayList(size);
153 | }
154 |
155 | public ESShapeBuilder addLocation(double latitude, double longitude) {
156 | locations.add(new ESLocation(latitude, longitude));
157 | return this;
158 | }
159 |
160 | public ESShape build() {
161 | this.esShapeType = getShapeType();
162 | Geometry geometry = buildGeometry();
163 | this.area = degree2ToKm2(geometry.getArea());
164 | this.length = degreeToKm(geometry.getLength());
165 | Point centroid = geometry.getCentroid();
166 | this.centroid = new ESLocation(centroid.getY(), centroid.getX());
167 | this.geoJsonArray = toGeoJsonArray();
168 | return new ESShape(this);
169 | }
170 |
171 | private boolean isClosed() {
172 | ESLocation first = locations.get(0);
173 | ESLocation last = locations.get(locations.size() - 1);
174 | return first.equals(last);
175 | }
176 |
177 | private ESShapeType getShapeType() {
178 | if (locations.isEmpty()) {
179 | throw new IllegalStateException("This builder contains no location");
180 | } else if (locations.size() == 1) {
181 | return ESShapeType.POINT;
182 | } else if (!isClosed()) {
183 | return ESShapeType.LINESTRING;
184 | } else {
185 | return ESShapeType.POLYGON;
186 | }
187 | }
188 |
189 | private Geometry buildGeometry() {
190 | Coordinate[] coordinates = new Coordinate[locations.size()];
191 | for (int i = 0; i < locations.size(); i++) {
192 | coordinates[i] = new Coordinate(
193 | locations.get(i).getLongitude(),
194 | locations.get(i).getLatitude());
195 | }
196 | GeometryFactory factory = SPATIAL_CONTEXT.getGeometryFactory();
197 | CoordinateSequence sequence = factory.getCoordinateSequenceFactory().create(coordinates);
198 | switch (getShapeType()) {
199 | case POINT:
200 | return new Point(sequence, factory);
201 | case LINESTRING:
202 | return new LineString(sequence, factory);
203 | case POLYGON:
204 | LinearRing shell = new LinearRing(sequence, factory);
205 | return new Polygon(shell, null, factory);
206 | default:
207 | throw new IllegalStateException("Unrecognized geometry");
208 | }
209 | }
210 |
211 | private double[][] toGeoJsonArray() {
212 | double[][] array = new double[locations.size()][2];
213 | for (int i = 0; i < locations.size(); i++) {
214 | array[i] = locations.get(i).toGeoJsonArray();
215 | }
216 | return array;
217 | }
218 |
219 | private static double degree2ToKm2(double degree2Area) {
220 | double degreeArea = Math.sqrt(degree2Area);
221 | double kmArea = DistanceUtils.degrees2Dist(degreeArea, DistanceUtils.EARTH_MEAN_RADIUS_KM);
222 | double km2Area = Math.pow(kmArea, 2);
223 | return km2Area;
224 | }
225 |
226 | private static double degreeToKm(double degreeLength) {
227 | return DistanceUtils.degrees2Dist(degreeLength, DistanceUtils.EARTH_MEAN_RADIUS_KM);
228 | }
229 |
230 | }
231 |
232 | }
--------------------------------------------------------------------------------
/src/main/java/org/openstreetmap/osmosis/plugin/elasticsearch/model/shape/ESShapeType.java:
--------------------------------------------------------------------------------
1 | package org.openstreetmap.osmosis.plugin.elasticsearch.model.shape;
2 |
3 | public enum ESShapeType {
4 | POINT, LINESTRING, POLYGON
5 | }
6 |
--------------------------------------------------------------------------------
/src/main/java/org/openstreetmap/osmosis/plugin/elasticsearch/service/IndexAdminService.java:
--------------------------------------------------------------------------------
1 | package org.openstreetmap.osmosis.plugin.elasticsearch.service;
2 |
3 | import java.util.HashMap;
4 | import java.util.Map;
5 |
6 | import org.elasticsearch.client.Client;
7 | import org.elasticsearch.common.xcontent.XContentBuilder;
8 | import org.elasticsearch.common.xcontent.XContentFactory;
9 |
10 | public class IndexAdminService {
11 |
12 | private final Client client;
13 |
14 | public IndexAdminService(Client client) {
15 | this.client = client;
16 | }
17 |
18 | public void createIndex(String name, int shards, int replicas, Map mappings) {
19 | try {
20 | if (mappings == null) mappings = new HashMap();
21 | // Delete previous existing index
22 | if (indexExists(name)) deleteIndex(name);
23 | // Build index configuration
24 | XContentBuilder jsonBuilder = XContentFactory.jsonBuilder();
25 | jsonBuilder.startObject();
26 | // Add settings
27 | jsonBuilder.startObject("settings")
28 | .field("number_of_shards", shards)
29 | .field("number_of_replicas", replicas)
30 | .endObject();
31 | // Add mappings
32 | jsonBuilder.startObject("mappings");
33 | for (String indiceName : mappings.keySet()) {
34 | jsonBuilder.rawField(indiceName, mappings.get(indiceName).getBytes());
35 | }
36 | jsonBuilder.endObject();
37 | // Build JSON
38 | String configuration = jsonBuilder.endObject().string();
39 | // https://github.com/elasticsearch/elasticsearch/issues/2897
40 | //.replaceAll("\\{,", "\\{");
41 | // Create the new index
42 | client.admin().indices().prepareCreate(name)
43 | .setSource(configuration)
44 | .execute().actionGet();
45 | } catch (Exception e) {
46 | throw new RuntimeException("Unable to create index " + name, e);
47 | }
48 | }
49 |
50 | public boolean indexExists(String... indices) {
51 | return client.admin().indices().prepareExists(indices)
52 | .execute().actionGet().isExists();
53 | }
54 |
55 | public void index(String index, String type, long id, XContentBuilder sourceBuilder) {
56 | client.prepareIndex(index, type, Long.toString(id))
57 | .setSource(sourceBuilder)
58 | .execute().actionGet();
59 | }
60 |
61 | public void index(String index, String type, long id, String source) {
62 | client.prepareIndex(index, type, Long.toString(id))
63 | .setSource(source)
64 | .execute().actionGet();
65 | }
66 |
67 | public void deleteIndex(String... indices) {
68 | client.admin().indices().prepareDelete(indices)
69 | .execute().actionGet();
70 | }
71 |
72 | public void deleteDocument(String indexName, String type, String id) {
73 | client.prepareDelete()
74 | .setIndex(indexName)
75 | .setType(type)
76 | .setId(id)
77 | .execute().actionGet();
78 | }
79 |
80 | public void refresh(String... indices) {
81 | client.admin().indices().prepareRefresh(indices)
82 | .execute().actionGet();
83 | }
84 |
85 | }
86 |
--------------------------------------------------------------------------------
/src/main/java/org/openstreetmap/osmosis/plugin/elasticsearch/utils/Endpoint.java:
--------------------------------------------------------------------------------
1 | package org.openstreetmap.osmosis.plugin.elasticsearch.utils;
2 |
3 | import org.elasticsearch.client.Client;
4 | import org.openstreetmap.osmosis.plugin.elasticsearch.dao.EntityDao;
5 | import org.openstreetmap.osmosis.plugin.elasticsearch.service.IndexAdminService;
6 |
7 | public class Endpoint {
8 |
9 | private final Client client;
10 | private final IndexAdminService indexAdminService;
11 | private final EntityDao entityDao;
12 |
13 | public Endpoint(Client client, IndexAdminService indexAdminService, EntityDao entityDao) {
14 | this.client = client;
15 | this.indexAdminService = indexAdminService;
16 | this.entityDao = entityDao;
17 | }
18 |
19 | public Client getClient() {
20 | return client;
21 | }
22 |
23 | public IndexAdminService getIndexAdminService() {
24 | return indexAdminService;
25 | }
26 |
27 | public EntityDao getEntityDao() {
28 | return entityDao;
29 | }
30 |
31 | }
32 |
--------------------------------------------------------------------------------
/src/main/java/org/openstreetmap/osmosis/plugin/elasticsearch/utils/EntityBuffer.java:
--------------------------------------------------------------------------------
1 | package org.openstreetmap.osmosis.plugin.elasticsearch.utils;
2 |
3 | import java.util.ArrayList;
4 | import java.util.List;
5 |
6 | import org.openstreetmap.osmosis.core.domain.v0_6.Entity;
7 | import org.openstreetmap.osmosis.core.domain.v0_6.EntityType;
8 | import org.openstreetmap.osmosis.plugin.elasticsearch.dao.EntityDao;
9 |
10 | public class EntityBuffer {
11 |
12 | private final int size;
13 | private final EntityDao entityDao;
14 | private final List buffer;
15 |
16 | private EntityBuffer(EntityDao entityDao, int size) {
17 | this.size = size;
18 | this.buffer = new ArrayList(size);
19 | this.entityDao = entityDao;
20 | }
21 |
22 | public boolean add(Entity entity) {
23 | buffer.add(entity);
24 | if (buffer.size() == size) {
25 | flush();
26 | return true;
27 | } else return false;
28 | }
29 |
30 | public void flush() {
31 | entityDao.saveAll(buffer);
32 | buffer.clear();
33 | }
34 |
35 | public static class EntityBufferFactory {
36 |
37 | private final EntityDao entityDao;
38 | private final int nodeBulkSize;
39 | private final int wayBulkSize;
40 |
41 | public EntityBufferFactory(EntityDao entityDao, Parameters params) {
42 | this.entityDao = entityDao;
43 | this.nodeBulkSize = Integer.valueOf(params.getProperty(Parameters.CONFIG_NODE_BULK_SIZE));
44 | this.wayBulkSize = Integer.valueOf(params.getProperty(Parameters.CONFIG_WAY_BULK_SIZE));
45 | }
46 |
47 | public EntityBuffer buildForType(EntityType type) {
48 | switch (type) {
49 | case Node:
50 | return new EntityBuffer(entityDao, nodeBulkSize);
51 | case Way:
52 | return new EntityBuffer(entityDao, wayBulkSize);
53 | case Relation:
54 | case Bound:
55 | default:
56 | return new EntityBuffer(entityDao, 10);
57 | }
58 |
59 | }
60 |
61 | }
62 |
63 | }
--------------------------------------------------------------------------------
/src/main/java/org/openstreetmap/osmosis/plugin/elasticsearch/utils/EntityCounter.java:
--------------------------------------------------------------------------------
1 | package org.openstreetmap.osmosis.plugin.elasticsearch.utils;
2 |
3 | import java.util.EnumMap;
4 | import java.util.Map;
5 | import java.util.concurrent.atomic.AtomicInteger;
6 |
7 | import org.openstreetmap.osmosis.core.domain.v0_6.EntityType;
8 |
9 | public class EntityCounter {
10 |
11 | private final Map counters;
12 |
13 | public EntityCounter() {
14 | counters = new EnumMap(EntityType.class);
15 | for (EntityType type : EntityType.values()) {
16 | counters.put(type, new AtomicInteger());
17 | }
18 | }
19 |
20 | public void increment(EntityType type) {
21 | counters.get(type).incrementAndGet();
22 | }
23 |
24 | public int getCount(EntityType type) {
25 | return counters.get(type).get();
26 | }
27 |
28 | }
--------------------------------------------------------------------------------
/src/main/java/org/openstreetmap/osmosis/plugin/elasticsearch/utils/Parameters.java:
--------------------------------------------------------------------------------
1 | package org.openstreetmap.osmosis.plugin.elasticsearch.utils;
2 |
3 | import java.io.FileReader;
4 | import java.io.IOException;
5 | import java.util.Properties;
6 |
7 | public class Parameters {
8 |
9 | public static final String PROPERTIES_FILE = "properties.file";
10 |
11 | public static final String CLUSTER_HOSTS = "cluster.hosts";
12 | public static final String CLUSTER_NAME = "cluster.name";
13 |
14 | public static final String INDEX_NAME = "index.name";
15 | public static final String INDEX_CREATE = "index.create";
16 | public static final String INDEX_SETTINGS_SHARDS = "index.settings.shards";
17 | public static final String INDEX_SETTINGS_REPLICAS = "index.settings.replicas";
18 | public static final String INDEX_MAPPING_NODE = "index.mapping.node";
19 | public static final String INDEX_MAPPING_WAY = "index.mapping.way";
20 |
21 | public static final String INDEX_BUILDERS = "index.builders";
22 |
23 | public static final String CONFIG_QUEUE_SIZE = "config.queue.size";
24 | public static final String CONFIG_NODE_BULK_SIZE = "config.node.bulk.size";
25 | public static final String CONFIG_WAY_BULK_SIZE = "config.way.bulk.size";
26 | public static final String CONFIG_WORKER_POOL_SIZE = "config.worker.pool.size";
27 |
28 | private final Properties params;
29 |
30 | private Parameters(Builder builder) {
31 | this.params = builder.params;
32 | }
33 |
34 | public String getProperty(String key) {
35 | return params.getProperty(key);
36 | }
37 |
38 | public String getProperty(String key, String defaultValue) {
39 | return params.getProperty(key, defaultValue);
40 | }
41 |
42 | public boolean containsKey(String key) {
43 | return params.containsKey(key);
44 | }
45 |
46 | @Override
47 | public String toString() {
48 | return "Parameters [params=" + params + "]";
49 | }
50 |
51 | public static class Builder {
52 |
53 | private Properties params = new Properties();
54 |
55 | public Builder loadResource(String resource) {
56 | try {
57 | params.load(getClass().getClassLoader().getResource(resource).openStream());
58 | return this;
59 | } catch (IOException e) {
60 | throw new RuntimeException("Unable to load properties resource " + resource);
61 | }
62 | }
63 |
64 | public Builder loadFile(String fileName) {
65 | try {
66 | params.load(new FileReader(fileName));
67 | return this;
68 | } catch (IOException e) {
69 | throw new RuntimeException("Unable to load properties file " + fileName);
70 | }
71 | }
72 |
73 | public Builder addParameter(String key, String value) {
74 | params.setProperty(key, value);
75 | return this;
76 | }
77 |
78 | public Parameters build() {
79 | return new Parameters(this);
80 | }
81 |
82 | }
83 |
84 | }
85 |
--------------------------------------------------------------------------------
/src/main/java/org/openstreetmap/osmosis/plugin/elasticsearch/worker/Worker.java:
--------------------------------------------------------------------------------
1 | package org.openstreetmap.osmosis.plugin.elasticsearch.worker;
2 |
3 | import java.util.concurrent.BlockingQueue;
4 | import java.util.concurrent.CountDownLatch;
5 | import java.util.concurrent.TimeUnit;
6 | import java.util.concurrent.atomic.AtomicReference;
7 | import java.util.logging.Logger;
8 |
9 | import org.openstreetmap.osmosis.core.domain.v0_6.Entity;
10 | import org.openstreetmap.osmosis.core.domain.v0_6.EntityType;
11 | import org.openstreetmap.osmosis.plugin.elasticsearch.utils.EntityBuffer;
12 | import org.openstreetmap.osmosis.plugin.elasticsearch.utils.EntityBuffer.EntityBufferFactory;
13 |
14 | public class Worker extends Thread {
15 |
16 | private static final Logger LOG = Logger.getLogger(Worker.class.getName());
17 |
18 | private final BlockingQueue taskQueue;
19 | private final EntityBufferFactory bufferFactory;
20 | private final AtomicReference newTypeNotification;
21 |
22 | private boolean running = true;
23 |
24 | public Worker(String name, BlockingQueue taskQueue, EntityBufferFactory bufferFactory) {
25 | super(name);
26 | this.taskQueue = taskQueue;
27 | this.bufferFactory = bufferFactory;
28 | this.newTypeNotification = new AtomicReference();
29 | }
30 |
31 | @Override
32 | public void run() {
33 | Entity entity = null;
34 | EntityBuffer entityBuffer = null;
35 | NewTypeNotification notification = null;
36 | while (running || !taskQueue.isEmpty()) {
37 | try {
38 | // Check if a NewTypeNotification was triggered
39 | if ((notification = newTypeNotification.getAndSet(null)) != null) {
40 | LOG.fine("NewTypeNotification detected, flushing...");
41 | if (entityBuffer != null) entityBuffer.flush();
42 | entityBuffer = bufferFactory.buildForType(notification.getType());
43 | notification.getLatch().countDown();
44 | }
45 | // Poll the queue
46 | if ((entity = taskQueue.poll(WorkerPool.POLL_INTERVAL, TimeUnit.MILLISECONDS)) != null) {
47 | entityBuffer.add(entity);
48 | }
49 | } catch (InterruptedException e) {
50 | LOG.fine("InterruptedException triggered, leaving...");
51 | }
52 | }
53 | if (entityBuffer != null) entityBuffer.flush();
54 | LOG.fine(String.format("%s shutdown", getName()));
55 | }
56 |
57 | public void notifyNewType(EntityType type) throws InterruptedException {
58 | NewTypeNotification notification = new NewTypeNotification(type);
59 | newTypeNotification.set(notification);
60 | notification.getLatch().await();
61 | }
62 |
63 | public void shutdown() throws InterruptedException {
64 | running = false;
65 | join();
66 | }
67 |
68 | public class NewTypeNotification {
69 |
70 | private final CountDownLatch latch = new CountDownLatch(1);
71 | private final EntityType type;
72 |
73 | public NewTypeNotification(EntityType type) {
74 | this.type = type;
75 | }
76 |
77 | public CountDownLatch getLatch() {
78 | return latch;
79 | }
80 |
81 | public EntityType getType() {
82 | return type;
83 | }
84 |
85 | }
86 |
87 | }
88 |
--------------------------------------------------------------------------------
/src/main/java/org/openstreetmap/osmosis/plugin/elasticsearch/worker/WorkerPool.java:
--------------------------------------------------------------------------------
1 | package org.openstreetmap.osmosis.plugin.elasticsearch.worker;
2 |
3 | import java.util.ArrayList;
4 | import java.util.List;
5 | import java.util.concurrent.ArrayBlockingQueue;
6 | import java.util.concurrent.BlockingQueue;
7 | import java.util.concurrent.TimeUnit;
8 | import java.util.concurrent.atomic.AtomicReference;
9 |
10 | import org.openstreetmap.osmosis.core.domain.v0_6.Entity;
11 | import org.openstreetmap.osmosis.core.domain.v0_6.EntityType;
12 | import org.openstreetmap.osmosis.plugin.elasticsearch.dao.EntityDao;
13 | import org.openstreetmap.osmosis.plugin.elasticsearch.utils.EntityBuffer.EntityBufferFactory;
14 | import org.openstreetmap.osmosis.plugin.elasticsearch.utils.Parameters;
15 |
16 | public class WorkerPool {
17 |
18 | public static final int POLL_INTERVAL = 10;
19 |
20 | private final AtomicReference lastEntityType;
21 | private final BlockingQueue taskQueue;
22 | private final List workers;
23 |
24 | public WorkerPool(EntityDao entityDao, Parameters params) {
25 | this.lastEntityType = new AtomicReference();
26 | int queueSize = Integer.valueOf(params.getProperty(Parameters.CONFIG_QUEUE_SIZE));
27 | this.taskQueue = new ArrayBlockingQueue(queueSize);
28 | int poolSize = Integer.valueOf(params.getProperty(Parameters.CONFIG_WORKER_POOL_SIZE));
29 | this.workers = new ArrayList(poolSize);
30 | EntityBufferFactory factory = new EntityBufferFactory(entityDao, params);
31 | for (int i = 0; i < poolSize; i++) {
32 | String name = "Worker #" + i;
33 | Worker worker = new Worker(name, taskQueue, factory);
34 | workers.add(worker);
35 | worker.start();
36 | }
37 | }
38 |
39 | public synchronized void submit(Entity entity) {
40 | if (!entity.getType().equals(lastEntityType.getAndSet(entity.getType()))) {
41 | notifyNewType(entity.getType());
42 | }
43 | try {
44 | while (!taskQueue.offer(entity, POLL_INTERVAL, TimeUnit.MILLISECONDS));
45 | } catch (InterruptedException e) {
46 | throw new IllegalStateException("InterruptedException caught", e);
47 | }
48 | }
49 |
50 | protected void notifyNewType(EntityType type) {
51 | for (Worker worker : workers) {
52 | try {
53 | worker.notifyNewType(type);
54 | } catch (InterruptedException e) {}
55 | }
56 | }
57 |
58 | public void shutdown() {
59 | for (Worker worker : workers) {
60 | try {
61 | worker.shutdown();
62 | } catch (InterruptedException e) {}
63 | }
64 | }
65 |
66 | }
67 |
--------------------------------------------------------------------------------
/src/main/resources/plugin.properties:
--------------------------------------------------------------------------------
1 | # Connection configuration
2 | cluster.hosts=localhost
3 | cluster.name=elasticsearch
4 |
5 | # Entity index configuration
6 | index.name=osm
7 | index.create=true
8 | index.settings.shards=5
9 | index.settings.replicas=1
10 | index.mapping.node={"_all":{"enabled":false},"dynamic_templates":[{"tags_exceptions":{"path_match":"tags.*","match":"(name.*)","match_pattern":"regex","mapping":{"store":"no","type":"multi_field","fields":{"{name}":{"type":"string","index":"not_analyzed"},"analyzed":{"type":"string","index":"analyzed"}}}}},{"tags_default":{"path_match":"tags.*","mapping":{"index":"not_analyzed","store":"no"}}}],"properties":{"centroid":{"type":"geo_point"},"shape":{"type":"geo_shape"}}}
11 | index.mapping.way={"_all":{"enabled":false},"dynamic_templates":[{"tags_exceptions":{"path_match":"tags.*","match":"(name.*)","match_pattern":"regex","mapping":{"store":"no","type":"multi_field","fields":{"{name}":{"type":"string","index":"not_analyzed"},"analyzed":{"type":"string","index":"analyzed"}}}}},{"tags_default":{"path_match":"tags.*","mapping":{"index":"not_analyzed","store":"no"}}}],"properties":{"centroid":{"type":"geo_point"},"shape":{"type":"geo_shape"}}}
12 | index.builders=
13 |
14 | config.queue.size=100
15 | config.node.bulk.size=5000
16 | config.way.bulk.size=500
17 | config.worker.pool.size=5
18 |
19 | # HighwayIndexBuilder configuration
20 | highway=org.openstreetmap.osmosis.plugin.elasticsearch.builder.highway.HighwayIndexBuilder
21 | highway.settings.shards=5
22 | highway.settings.replicas=1
23 | highway.mappings={"way":{"_all":{"enabled":false},"dynamic_templates":[{"tags_template_1":{"path_match":"tags.*","match":"name*","mapping":{"store":"no","type":"multi_field","fields":{"{name}":{"type":"string","index":"not_analyzed"},"analyzed":{"type":"string","index":"analyzed"}}}}},{"tags_template_2":{"path_match":"tags.*","mapping":{"index":"not_analyzed","store":"no"}}}],"properties":{"line":{"type":"geo_shape"}}}}
24 | highway.bulk.size=500
--------------------------------------------------------------------------------
/src/test/java/org/openstreetmap/osmosis/plugin/elasticsearch/ElasticSearchWriterTaskUTest.java:
--------------------------------------------------------------------------------
1 | package org.openstreetmap.osmosis.plugin.elasticsearch;
2 |
3 | import static org.mockito.Matchers.eq;
4 | import static org.mockito.Mockito.doNothing;
5 | import static org.mockito.Mockito.mock;
6 | import static org.mockito.Mockito.spy;
7 | import static org.mockito.Mockito.times;
8 | import static org.mockito.Mockito.verify;
9 | import static org.mockito.Mockito.when;
10 |
11 | import java.util.Arrays;
12 | import java.util.HashSet;
13 | import java.util.Set;
14 |
15 | import org.elasticsearch.client.Client;
16 | import org.junit.Before;
17 | import org.junit.Test;
18 | import org.openstreetmap.osmosis.core.container.v0_6.EntityContainer;
19 | import org.openstreetmap.osmosis.core.domain.v0_6.Entity;
20 | import org.openstreetmap.osmosis.core.domain.v0_6.EntityType;
21 | import org.openstreetmap.osmosis.plugin.elasticsearch.builder.AbstractIndexBuilder;
22 | import org.openstreetmap.osmosis.plugin.elasticsearch.dao.EntityDao;
23 | import org.openstreetmap.osmosis.plugin.elasticsearch.service.IndexAdminService;
24 | import org.openstreetmap.osmosis.plugin.elasticsearch.utils.Endpoint;
25 | import org.openstreetmap.osmosis.plugin.elasticsearch.utils.Parameters;
26 |
27 | public class ElasticSearchWriterTaskUTest {
28 |
29 | private Client clientMocked;
30 | private IndexAdminService indexAdminServiceMocked;
31 | private EntityDao entityDaoMocked;
32 | private Endpoint endpoint;
33 | private Set indexBuilders;
34 | private Parameters params;
35 |
36 | private ElasticSearchWriterTask elasticSearchWriterTask;
37 |
38 | @Before
39 | public void setUp() throws Exception {
40 | clientMocked = mock(Client.class);
41 | indexAdminServiceMocked = mock(IndexAdminService.class);
42 | entityDaoMocked = mock(EntityDao.class);
43 | endpoint = new Endpoint(clientMocked, indexAdminServiceMocked, entityDaoMocked);
44 | indexBuilders = new HashSet();
45 | params = new Parameters.Builder().loadResource("plugin.properties")
46 | .addParameter(Parameters.CONFIG_QUEUE_SIZE, "1")
47 | .addParameter(Parameters.CONFIG_NODE_BULK_SIZE, "1")
48 | .addParameter(Parameters.CONFIG_WAY_BULK_SIZE, "1")
49 | .addParameter(Parameters.CONFIG_WORKER_POOL_SIZE, "1").build();
50 | elasticSearchWriterTask = spy(new ElasticSearchWriterTask(endpoint, indexBuilders, params));
51 | }
52 |
53 | @Test
54 | public void process() {
55 | // Setup
56 | Entity entityMocked = mock(Entity.class);
57 | when(entityMocked.getType()).thenReturn(EntityType.Node);
58 |
59 | EntityContainer entityContainerMocked = mock(EntityContainer.class);
60 | when(entityContainerMocked.getEntity()).thenReturn(entityMocked);
61 |
62 | // Action
63 | elasticSearchWriterTask.process(entityContainerMocked);
64 | elasticSearchWriterTask.complete();
65 |
66 | // Assert
67 | verify(entityDaoMocked, times(2)).saveAll(eq(Arrays.asList(new Entity[] {})));
68 | }
69 |
70 | @Test
71 | public void complete() {
72 | // Setup
73 | doNothing().when(elasticSearchWriterTask).buildSpecializedIndex();
74 |
75 | // Action
76 | elasticSearchWriterTask.complete();
77 |
78 | // Assert
79 | verify(elasticSearchWriterTask, times(1)).buildSpecializedIndex();
80 | }
81 |
82 | @Test
83 | public void release() {
84 | // Action
85 | elasticSearchWriterTask.release();
86 |
87 | // Assert
88 | verify(clientMocked, times(1)).close();
89 | }
90 |
91 | public class DummyIndexBuilder extends AbstractIndexBuilder {
92 |
93 | public DummyIndexBuilder(Endpoint endpoint, Parameters params) {
94 | super(endpoint, params);
95 | }
96 |
97 | @Override
98 | public String getSpecializedIndexSuffix() {
99 | return "dummy";
100 | }
101 |
102 | @Override
103 | public void createIndex() {}
104 |
105 | @Override
106 | public void buildIndex() {}
107 | }
108 |
109 | }
110 |
--------------------------------------------------------------------------------
/src/test/java/org/openstreetmap/osmosis/plugin/elasticsearch/dao/EntityDaoITest.java:
--------------------------------------------------------------------------------
1 | package org.openstreetmap.osmosis.plugin.elasticsearch.dao;
2 |
3 | import java.io.IOException;
4 | import java.util.ArrayList;
5 | import java.util.Arrays;
6 | import java.util.HashMap;
7 | import java.util.List;
8 |
9 | import junit.framework.Assert;
10 |
11 | import org.elasticsearch.action.get.GetResponse;
12 | import org.junit.Before;
13 | import org.junit.Test;
14 | import org.openstreetmap.osmosis.core.domain.v0_6.Entity;
15 | import org.openstreetmap.osmosis.core.domain.v0_6.Node;
16 | import org.openstreetmap.osmosis.core.domain.v0_6.Way;
17 | import org.openstreetmap.osmosis.plugin.elasticsearch.model.entity.ESEntity;
18 | import org.openstreetmap.osmosis.plugin.elasticsearch.model.entity.ESEntityType;
19 | import org.openstreetmap.osmosis.plugin.elasticsearch.model.entity.ESNode;
20 | import org.openstreetmap.osmosis.plugin.elasticsearch.model.entity.ESWay;
21 | import org.openstreetmap.osmosis.plugin.elasticsearch.service.IndexAdminService;
22 | import org.openstreetmap.osmosis.plugin.elasticsearch.testutils.AbstractElasticSearchInMemoryTest;
23 | import org.openstreetmap.osmosis.plugin.elasticsearch.testutils.OsmDataBuilder;
24 | import org.openstreetmap.osmosis.plugin.elasticsearch.utils.Parameters;
25 |
26 | public class EntityDaoITest extends AbstractElasticSearchInMemoryTest {
27 |
28 | private static final String INDEX_NAME = "osm-test";
29 |
30 | private EntityDao entityDao;
31 |
32 | @Before
33 | public void setUp() throws IOException {
34 | entityDao = new EntityDao(INDEX_NAME, client());
35 | Parameters params = new Parameters.Builder().loadResource("plugin.properties").build();
36 | IndexAdminService indexAdminService = new IndexAdminService(client());
37 | HashMap mappings = new HashMap();
38 | mappings.put(ESEntityType.NODE.getIndiceName(), params.getProperty(Parameters.INDEX_MAPPING_NODE));
39 | mappings.put(ESEntityType.WAY.getIndiceName(), params.getProperty(Parameters.INDEX_MAPPING_WAY));
40 | indexAdminService.createIndex(INDEX_NAME, 1, 0, mappings);
41 | }
42 |
43 | /* save */
44 |
45 | @Test
46 | public void saveNode() {
47 | // Setup
48 | Node node = OsmDataBuilder.buildSampleNode();
49 |
50 | // Action
51 | entityDao.save(node);
52 | refresh(INDEX_NAME);
53 |
54 | // Assert
55 | GetResponse response = client().prepareGet(INDEX_NAME, "node", "1").execute().actionGet();
56 | Assert.assertTrue(response.isExists());
57 | String expected = "{\"centroid\":[2.0,1.0],\"shape\":{\"type\":\"point\",\"coordinates\":[2.0,1.0]},\"tags\":{\"highway\":\"traffic_signals\"}}";
58 | String actual = response.getSourceAsString();
59 | Assert.assertEquals(expected, actual);
60 | }
61 |
62 | @Test
63 | public void saveWay_withPolygon() {
64 | // Setup
65 | ESNode node1 = ESNode.Builder.create().id(1).location(1, 2).build();
66 | ESNode node2 = ESNode.Builder.create().id(2).location(2, 3).build();
67 | ESNode node3 = ESNode.Builder.create().id(3).location(3, 2).build();
68 | index(INDEX_NAME, node1, node2, node3);
69 |
70 | Way way = OsmDataBuilder.buildSampleWay(1, 1, 2, 3, 1);
71 |
72 | // Action
73 | entityDao.save(way);
74 | refresh();
75 |
76 | // Assert
77 | GetResponse response = client().prepareGet(INDEX_NAME, "way", "1").execute().actionGet();
78 | Assert.assertTrue(response.isExists());
79 | String expected = "{\"centroid\":[2.3333333333333335,2.0],\"lengthKm\":536.8973391277414," +
80 | "\"areaKm2\":12364.345757132623,\"shape\":{\"type\":\"polygon\",\"coordinates\":" +
81 | "[[[2.0,1.0],[3.0,2.0],[2.0,3.0],[2.0,1.0]]]},\"tags\":{\"highway\":\"residential\"}}";
82 | String actual = response.getSourceAsString();
83 | Assert.assertEquals(expected, actual);
84 | }
85 |
86 | @Test
87 | public void saveWay_withLineString() {
88 | // Setup
89 | ESNode node1 = ESNode.Builder.create().id(1).location(1.0, 2.0).build();
90 | ESNode node2 = ESNode.Builder.create().id(2).location(2.0, 3.0).build();
91 | ESNode node3 = ESNode.Builder.create().id(3).location(3.0, 2.0).build();
92 | ESNode node4 = ESNode.Builder.create().id(4).location(4.0, 1.0).build();
93 | index(INDEX_NAME, node1, node2, node3, node4);
94 |
95 | Way way = OsmDataBuilder.buildSampleWay(1, 1, 2, 3, 4);
96 |
97 | // Action
98 | entityDao.save(way);
99 | refresh(INDEX_NAME);
100 |
101 | // Assert
102 | GetResponse response = client().prepareGet(INDEX_NAME, "way", "1").execute().actionGet();
103 | Assert.assertTrue(response.isExists());
104 | String expected = "{\"centroid\":[2.1666666666666665,2.5],\"lengthKm\":471.76076948850596," +
105 | "\"areaKm2\":0.0,\"shape\":{\"type\":\"linestring\",\"coordinates\":" +
106 | "[[2.0,1.0],[3.0,2.0],[2.0,3.0],[1.0,4.0]]},\"tags\":{\"highway\":\"residential\"}}";
107 | String actual = response.getSourceAsString();
108 | Assert.assertEquals(expected, actual);
109 | }
110 |
111 | @Test
112 | public void saveAll() throws InterruptedException {
113 | // Setup
114 | Node node1 = OsmDataBuilder.buildSampleNode(1);
115 | Node node2 = OsmDataBuilder.buildSampleNode(2);
116 |
117 | // Action
118 | entityDao.saveAll(Arrays.asList(new Entity[] { node1, node2 }));
119 | refresh(INDEX_NAME);
120 |
121 | // Assert
122 | String expected = "{\"centroid\":[2.0,1.0],\"shape\":{\"type\":\"point\",\"coordinates\":[2.0,1.0]}," +
123 | "\"tags\":{\"highway\":\"traffic_signals\"}}";
124 |
125 | GetResponse response1 = client().prepareGet(INDEX_NAME, "node", "1").execute().actionGet();
126 | Assert.assertTrue(response1.isExists());
127 | String actual1 = response1.getSourceAsString();
128 | Assert.assertEquals(expected, actual1);
129 |
130 | GetResponse response2 = client().prepareGet(INDEX_NAME, "node", "2").execute().actionGet();
131 | Assert.assertTrue(response2.isExists());
132 | String actual2 = response2.getSourceAsString();
133 | Assert.assertEquals(expected, actual2);
134 | }
135 |
136 | /* find */
137 |
138 | @Test
139 | public void findNode() {
140 | // Setup
141 | ESNode node = OsmDataBuilder.buildSampleESNode();
142 | index(INDEX_NAME, node);
143 | refresh(INDEX_NAME);
144 |
145 | // Action
146 | ESNode actual = entityDao.find(ESNode.class, 1);
147 |
148 | // Assert
149 | Assert.assertEquals(node, actual);
150 | }
151 |
152 | @Test(expected = DaoException.class)
153 | public void findNode_thatDoesNotExists() {
154 | // Setup
155 | ESNode node = OsmDataBuilder.buildSampleESNode();
156 | index(INDEX_NAME, node);
157 | refresh(INDEX_NAME);
158 |
159 | // Action
160 | entityDao.find(ESNode.class, 2);
161 | }
162 |
163 | @Test
164 | public void findWay_withLineString() {
165 | // Setup
166 | ESWay way = ESWay.Builder.create().id(1).addLocation(1.0, 2.0).addLocation(2.0, 3.0)
167 | .addLocation(3.0, 2.0).addLocation(4.0, 1.0).build();
168 | index(INDEX_NAME, way);
169 | refresh(INDEX_NAME);
170 |
171 | // Action
172 | ESWay actual = entityDao.find(ESWay.class, 1);
173 |
174 | // Assert
175 | Assert.assertEquals(way, actual);
176 | }
177 |
178 | @Test
179 | public void findWay_withPolygon() {
180 | // Setup
181 | ESWay way = ESWay.Builder.create().id(1).addLocation(1.1, 2.1).addLocation(1.2, 2.2)
182 | .addLocation(1.3, 2.3).addLocation(1.1, 2.1).build();
183 | index(INDEX_NAME, way);
184 | refresh(INDEX_NAME);
185 |
186 | // Action
187 | ESWay actual = entityDao.find(ESWay.class, 1);
188 |
189 | // Assert
190 | Assert.assertEquals(way, actual);
191 | }
192 |
193 | @Test(expected = DaoException.class)
194 | public void findWay_thatDoesNotExists() {
195 | // Setup
196 | ESWay way = ESWay.Builder.create().id(1).addLocation(1.1, 2.1).addLocation(1.2, 2.2)
197 | .addLocation(1.3, 2.3).addLocation(1.4, 2.4).build();
198 | index(INDEX_NAME, way);
199 | refresh(INDEX_NAME);
200 |
201 | // Action
202 | entityDao.find(ESWay.class, 2);
203 | }
204 |
205 | /* findAll */
206 |
207 | @Test
208 | public void findAllNodes_stressTest() {
209 | // Setup
210 | int SIZE = 100;
211 |
212 | long[] ids = new long[SIZE];
213 | List expected = new ArrayList(SIZE);
214 |
215 | for (int i = 0; i < SIZE; i++) {
216 | ESNode node = OsmDataBuilder.buildSampleESNode(i);
217 | expected.add(node);
218 | ids[i] = i;
219 |
220 | }
221 | index(INDEX_NAME, expected.toArray(new ESEntity[0]));
222 | refresh(INDEX_NAME);
223 |
224 | // Action
225 | List actual = entityDao.findAll(ESNode.class, ids);
226 |
227 | // Assert
228 | Assert.assertEquals(expected, actual);
229 | }
230 |
231 | @Test
232 | public void findAllNodes() {
233 | // Setup
234 | ESNode node1 = ESNode.Builder.create().id(1).location(1.0, 2.0).build();
235 | ESNode node2 = ESNode.Builder.create().id(2).location(3.0, 4.0).build();
236 | List expected = Arrays.asList(new ESNode[] { node1, node2 });
237 |
238 | index(INDEX_NAME, node1, node2);
239 | refresh(INDEX_NAME);
240 |
241 | // Action
242 | List actual = entityDao.findAll(ESNode.class, 1l, 2);
243 |
244 | // Assert
245 | Assert.assertEquals(expected, actual);
246 | }
247 |
248 | @Test
249 | public void findAllNodes_withSubset() {
250 | // Setup
251 | ESNode node1 = ESNode.Builder.create().id(1).location(1.0, 2.0).build();
252 | ESNode node2 = ESNode.Builder.create().id(2).location(3.0, 4.0).build();
253 | List expected = Arrays.asList(new ESNode[] { node2 });
254 |
255 | index(INDEX_NAME, node1, node2);
256 | refresh(INDEX_NAME);
257 |
258 | // Action
259 | List actual = entityDao.findAll(ESNode.class, 2);
260 |
261 | // Assert
262 | Assert.assertEquals(expected, actual);
263 | }
264 |
265 | @Test
266 | public void findAllNodes_keepOrder() {
267 | // Setup
268 | ESNode node1 = ESNode.Builder.create().id(1).location(1.0, 2.0).build();
269 | ESNode node2 = ESNode.Builder.create().id(2).location(3.0, 4.0).build();
270 | List expected = Arrays.asList(new ESNode[] { node2, node1 });
271 |
272 | index(INDEX_NAME, node1, node2);
273 | refresh(INDEX_NAME);
274 |
275 | // Action
276 | List actual = entityDao.findAll(ESNode.class, 2l, 1);
277 |
278 | // Assert
279 | Assert.assertEquals(expected, actual);
280 | }
281 |
282 | @Test
283 | public void findAllWays() {
284 | // Setup
285 | // Setup
286 | ESWay way1 = ESWay.Builder.create().id(1).addLocation(1.1, 2.1).addLocation(1.2, 2.2)
287 | .addLocation(1.3, 2.3).addLocation(1.4, 2.4).build();
288 | ESWay way2 = ESWay.Builder.create().id(2).addLocation(1.1, 2.1).addLocation(1.2, 2.2)
289 | .addLocation(1.3, 2.3).addLocation(1.4, 2.4).build();
290 | List expected = Arrays.asList(new ESWay[] { way1, way2 });
291 |
292 | index(INDEX_NAME, way1, way2);
293 | refresh(INDEX_NAME);
294 |
295 | // Action
296 | List actual = entityDao.findAll(ESWay.class, 1l, 2);
297 |
298 | // Assert
299 | Assert.assertEquals(expected, actual);
300 | }
301 |
302 | @Test
303 | public void findAllWays_withSubset() {
304 | // Setup
305 | ESWay way1 = ESWay.Builder.create().id(1).addLocation(1.1, 2.1).addLocation(1.2, 2.2)
306 | .addLocation(1.3, 2.3).addLocation(1.4, 2.4).build();
307 | ESWay way2 = ESWay.Builder.create().id(2).addLocation(1.1, 2.1).addLocation(1.2, 2.2)
308 | .addLocation(1.3, 2.3).addLocation(1.4, 2.4).build();
309 | List expected = Arrays.asList(new ESWay[] { way2 });
310 |
311 | index(INDEX_NAME, way1, way2);
312 | refresh(INDEX_NAME);
313 |
314 | // Action
315 | List actual = entityDao.findAll(ESWay.class, 2);
316 |
317 | // Assert
318 | Assert.assertEquals(expected, actual);
319 | }
320 |
321 | @Test
322 | public void findAllWays_keepOrder() {
323 | // Setup
324 | ESWay way1 = ESWay.Builder.create().id(1).addLocation(1.1, 2.1).addLocation(1.2, 2.2)
325 | .addLocation(1.3, 2.3).addLocation(1.4, 2.4).build();
326 | ESWay way2 = ESWay.Builder.create().id(2).addLocation(1.1, 2.1).addLocation(1.2, 2.2)
327 | .addLocation(1.3, 2.3).addLocation(1.4, 2.4).build();
328 | List expected = Arrays.asList(new ESWay[] { way2, way1 });
329 |
330 | index(INDEX_NAME, way1, way2);
331 | refresh(INDEX_NAME);
332 |
333 | // Action
334 | List actual = entityDao.findAll(ESWay.class, 2l, 1);
335 |
336 | // Assert
337 | Assert.assertEquals(expected, actual);
338 | }
339 |
340 | /* delete */
341 |
342 | @Test
343 | public void deleteNode() {
344 | // Setup
345 | ESNode node = OsmDataBuilder.buildSampleESNode();
346 | index(INDEX_NAME, node);
347 | refresh(INDEX_NAME);
348 |
349 | // Action
350 | boolean actual = entityDao.delete(ESNode.class, 1);
351 |
352 | // Assert
353 | Assert.assertTrue(actual);
354 | }
355 |
356 | @Test
357 | public void deleteNode_thatDoesNotExists() {
358 | // Setup
359 | ESNode node = OsmDataBuilder.buildSampleESNode();
360 | index(INDEX_NAME, node);
361 | refresh(INDEX_NAME);
362 |
363 | // Action
364 | boolean actual = entityDao.delete(ESNode.class, 2);
365 |
366 | // Assert
367 | Assert.assertFalse(actual);
368 | }
369 |
370 | @Test
371 | public void deleteWay() {
372 | // Setup
373 | ESWay way = ESWay.Builder.create().id(1).addLocation(1.1, 2.1).addLocation(1.2, 2.2)
374 | .addLocation(1.3, 2.3).addLocation(1.4, 2.4).build();
375 | index(INDEX_NAME, way);
376 | refresh(INDEX_NAME);
377 |
378 | // Action
379 | boolean actual = entityDao.delete(ESWay.class, 1);
380 |
381 | // Assert
382 | Assert.assertTrue(actual);
383 | }
384 |
385 | @Test
386 | public void deleteWay_thatDoesNotExists() {
387 | // Setup
388 | ESWay way = ESWay.Builder.create().id(1).addLocation(1.1, 2.1).addLocation(1.2, 2.2)
389 | .addLocation(1.3, 2.3).addLocation(1.4, 2.4).build();
390 | index(INDEX_NAME, way);
391 | refresh(INDEX_NAME);
392 |
393 | // Action
394 | boolean actual = entityDao.delete(ESWay.class, 2);
395 |
396 | // Assert
397 | Assert.assertFalse(actual);
398 | }
399 |
400 | }
401 |
--------------------------------------------------------------------------------
/src/test/java/org/openstreetmap/osmosis/plugin/elasticsearch/dao/EntityDaoUTest.java:
--------------------------------------------------------------------------------
1 | package org.openstreetmap.osmosis.plugin.elasticsearch.dao;
2 |
3 | import java.util.*;
4 |
5 | import org.elasticsearch.ElasticsearchException;
6 | import org.elasticsearch.action.ListenableActionFuture;
7 | import org.elasticsearch.action.bulk.BulkItemResponse;
8 | import org.elasticsearch.action.bulk.BulkRequestBuilder;
9 | import org.elasticsearch.action.bulk.BulkResponse;
10 | import org.elasticsearch.action.delete.DeleteRequestBuilder;
11 | import org.elasticsearch.action.delete.DeleteResponse;
12 | import org.elasticsearch.action.get.GetResponse;
13 | import org.elasticsearch.action.get.MultiGetItemResponse;
14 | import org.elasticsearch.action.get.MultiGetRequest.Item;
15 | import org.elasticsearch.action.get.MultiGetRequestBuilder;
16 | import org.elasticsearch.action.get.MultiGetResponse;
17 | import org.elasticsearch.action.index.IndexRequestBuilder;
18 | import org.elasticsearch.client.Client;
19 | import org.hamcrest.BaseMatcher;
20 | import org.hamcrest.Description;
21 | import org.junit.Assert;
22 | import org.junit.Before;
23 | import org.junit.Test;
24 | import org.mockito.Mockito;
25 | import org.openstreetmap.osmosis.core.domain.v0_6.*;
26 | import org.openstreetmap.osmosis.plugin.elasticsearch.model.entity.ESEntity;
27 | import org.openstreetmap.osmosis.plugin.elasticsearch.model.entity.ESEntityType;
28 | import org.openstreetmap.osmosis.plugin.elasticsearch.model.entity.ESNode;
29 | import org.openstreetmap.osmosis.plugin.elasticsearch.model.shape.ESShape;
30 | import org.openstreetmap.osmosis.plugin.elasticsearch.model.shape.ESShape.ESShapeBuilder;
31 | import org.openstreetmap.osmosis.plugin.elasticsearch.testutils.OsmDataBuilder;
32 |
33 | import static org.junit.Assert.assertFalse;
34 | import static org.junit.Assert.assertTrue;
35 | import static org.mockito.Mockito.*;
36 |
37 | @SuppressWarnings("unchecked")
38 | public class EntityDaoUTest {
39 |
40 | private static final String INDEX_NAME = "osm-test";
41 |
42 | private Client clientMocked;
43 |
44 | private EntityDao entityDao;
45 |
46 | @Before
47 | public void setUp() throws Exception {
48 | clientMocked = mock(Client.class);
49 | entityDao = new EntityDao(INDEX_NAME, clientMocked);
50 | entityDao = Mockito.spy(entityDao);
51 | }
52 |
53 | /* SAVE */
54 |
55 | @Test
56 | public void saveEntity() throws Exception {
57 | // Setup
58 | Entity entity = mock(Entity.class);
59 |
60 | doNothing().when(entityDao).saveAll(any(List.class));
61 |
62 | // Action
63 | entityDao.save(entity);
64 |
65 | // Assert
66 | verify(entityDao, times(1)).saveAll(eq(Arrays.asList(entity)));
67 | }
68 |
69 | @Test(expected = IllegalArgumentException.class)
70 | public void saveEntity_withNull_shouldThrowException() {
71 | // Action
72 | entityDao.save(null);
73 | }
74 |
75 | /* SAVE ALL */
76 |
77 | @Test
78 | public void saveAll() {
79 | // Setup
80 | Node node = mock(Node.class);
81 | Way way = mock(Way.class);
82 | Relation relation = mock(Relation.class);
83 | Bound bound = mock(Bound.class);
84 |
85 | when(node.getType()).thenReturn(EntityType.Node);
86 | when(way.getType()).thenReturn(EntityType.Way);
87 | when(relation.getType()).thenReturn(EntityType.Relation);
88 | when(bound.getType()).thenReturn(EntityType.Bound);
89 |
90 | doNothing().when(entityDao).saveAllNodes(any(List.class));
91 | doNothing().when(entityDao).saveAllWays(any(List.class));
92 |
93 | // Action
94 | entityDao.saveAll(Arrays.asList(node, way, relation, bound));
95 |
96 | // Assert
97 | verify(entityDao, times(1)).saveAllNodes(eq(Arrays.asList(node)));
98 | verify(entityDao, times(1)).saveAllWays(eq(Arrays.asList(way)));
99 | }
100 |
101 | @Test
102 | public void saveAll_withNullList() throws Exception {
103 | // Action
104 | entityDao.saveAll(null);
105 |
106 | // Assert
107 | verifyNoMoreInteractions(clientMocked);
108 | }
109 |
110 | @Test
111 | public void saveAll_withEmptyList() throws Exception {
112 | // Action
113 | entityDao.saveAll(new ArrayList());
114 |
115 | // Assert
116 | verifyNoMoreInteractions(clientMocked);
117 | }
118 |
119 | @Test
120 | public void saveAllNodes() {
121 | // Setup
122 | Node node = OsmDataBuilder.buildSampleNode();
123 |
124 | Iterator iteratorMocked = mock(Iterator.class);
125 | doReturn(iteratorMocked).when(entityDao).getNodeItems(any(List.class));
126 |
127 | ESShape builder = new ESShapeBuilder(1).addLocation(1.0, 2.0).build();
128 | doReturn(builder).when(entityDao).getShape(iteratorMocked, 1);
129 |
130 | BulkRequestBuilder bulkRequestBuilderMocked = mock(BulkRequestBuilder.class);
131 | when(clientMocked.prepareBulk()).thenReturn(bulkRequestBuilderMocked);
132 |
133 | IndexRequestBuilder indexRequestBuilderMocked = mock(IndexRequestBuilder.class);
134 | when(indexRequestBuilderMocked.setSource(any(String.class))).thenReturn(indexRequestBuilderMocked);
135 | when(clientMocked.prepareIndex(any(String.class), any(String.class), any(String.class)))
136 | .thenReturn(indexRequestBuilderMocked);
137 |
138 | // Action
139 | entityDao.saveAllNodes(Arrays.asList(node));
140 |
141 | // Assert
142 | String source = "{\"centroid\":[2.0,1.0],\"shape\":{\"type\":\"point\",\"coordinates\":[2.0,1.0]},\"tags\":{\"highway\":\"traffic_signals\"}}";
143 | verify(clientMocked).prepareIndex(INDEX_NAME, ESEntityType.NODE.getIndiceName(), "1");
144 | verify(indexRequestBuilderMocked).setSource(source);
145 | verify(bulkRequestBuilderMocked).add(indexRequestBuilderMocked);
146 | verify(entityDao).executeBulkRequest(bulkRequestBuilderMocked);
147 | }
148 |
149 | @Test
150 | public void saveAllWays() {
151 | // Setup
152 | Way way = OsmDataBuilder.buildSampleWay(1, 1, 2, 3, 4);
153 |
154 | Iterator iteratorMocked = mock(Iterator.class);
155 | doReturn(iteratorMocked).when(entityDao).getNodeItems(any(List.class));
156 |
157 | ESShape builder = new ESShapeBuilder(1).addLocation(1.0, 2.0).addLocation(2.0, 3.0)
158 | .addLocation(3.0, 2.0).addLocation(1.0, 2.0).build();
159 | doReturn(builder).when(entityDao).getShape(iteratorMocked, 4);
160 |
161 | BulkRequestBuilder bulkRequestBuilderMocked = mock(BulkRequestBuilder.class);
162 | when(clientMocked.prepareBulk()).thenReturn(bulkRequestBuilderMocked);
163 |
164 | IndexRequestBuilder indexRequestBuilderMocked = mock(IndexRequestBuilder.class);
165 | when(indexRequestBuilderMocked.setSource(any(String.class))).thenReturn(indexRequestBuilderMocked);
166 | when(clientMocked.prepareIndex(any(String.class), any(String.class), any(String.class)))
167 | .thenReturn(indexRequestBuilderMocked);
168 |
169 | // Action
170 | List ways = Arrays.asList(way);
171 | entityDao.saveAllWays(ways);
172 |
173 | // Assert
174 | verify(entityDao).getNodeItems(ways);
175 | String source = "{\"centroid\":[2.3333333333333335,2.0],\"lengthKm\":536.8973391277414," +
176 | "\"areaKm2\":12364.345757132623,\"shape\":{\"type\":\"polygon\",\"coordinates\":" +
177 | "[[[2.0,1.0],[3.0,2.0],[2.0,3.0],[2.0,1.0]]]},\"tags\":{\"highway\":\"residential\"}}";
178 | verify(clientMocked).prepareIndex(INDEX_NAME, ESEntityType.WAY.getIndiceName(), "1");
179 | verify(indexRequestBuilderMocked).setSource(source);
180 | verify(bulkRequestBuilderMocked).add(indexRequestBuilderMocked);
181 | verify(entityDao).executeBulkRequest(bulkRequestBuilderMocked);
182 | }
183 |
184 | @Test
185 | public void getNodeItems() {
186 | // Setup
187 | Way way = OsmDataBuilder.buildSampleWay();
188 |
189 | MultiGetRequestBuilder multiGetRequestBuilderMocked = mock(MultiGetRequestBuilder.class);
190 | when(clientMocked.prepareMultiGet()).thenReturn(multiGetRequestBuilderMocked);
191 |
192 | ListenableActionFuture listenableActionFutureMocked = mock(ListenableActionFuture.class);
193 | when(multiGetRequestBuilderMocked.execute()).thenReturn(listenableActionFutureMocked);
194 | MultiGetResponse multiGetResponseMocked = mock(MultiGetResponse.class);
195 | when(listenableActionFutureMocked.actionGet()).thenReturn(multiGetResponseMocked);
196 | Iterator iteratorMocked = mock(Iterator.class);
197 | when(multiGetResponseMocked.iterator()).thenReturn(iteratorMocked);
198 |
199 | // Action
200 | Iterator actual = entityDao.getNodeItems(Arrays.asList(way));
201 |
202 | // Assert
203 | Item item = new Item(INDEX_NAME, ESEntityType.NODE.getIndiceName(), "1");
204 | verify(multiGetRequestBuilderMocked).add(argThat(new ItemMatcher(item)));
205 | verify(multiGetRequestBuilderMocked, times(1)).execute();
206 | Assert.assertSame(iteratorMocked, actual);
207 | }
208 |
209 | @Test
210 | public void getLocationArrayBuilder() {
211 | // Setup
212 | GetResponse response1 = mock(GetResponse.class, Mockito.RETURNS_DEEP_STUBS);
213 | when(response1.isExists()).thenReturn(true);
214 | Map map1 = mock(Map.class);
215 | when(response1.getSource().get("shape")).thenReturn(map1);
216 | when(map1.get("coordinates")).thenReturn(Arrays.asList(2.0, 1.0));
217 |
218 | GetResponse response2 = mock(GetResponse.class, Mockito.RETURNS_DEEP_STUBS);
219 | when(response2.isExists()).thenReturn(true);
220 | Map map2 = mock(Map.class);
221 | when(response2.getSource().get("shape")).thenReturn(map2);
222 | when(map2.get("coordinates")).thenReturn(Arrays.asList(4.0, 3.0));
223 |
224 | MultiGetItemResponse multiGetItemResponseMocked = mock(MultiGetItemResponse.class);
225 | when(multiGetItemResponseMocked.getResponse()).thenReturn(response1, response2);
226 |
227 | Iterator iteratorMocked = mock(Iterator.class);
228 | when(iteratorMocked.next()).thenReturn(multiGetItemResponseMocked);
229 |
230 | // Action
231 | ESShape actual = entityDao.getShape(iteratorMocked, 2);
232 |
233 | // Assert
234 | Assert.assertTrue(Arrays.deepEquals(new double[][] {
235 | new double[] { 2.0, 1.0 },
236 | new double[] { 4.0, 3.0 }
237 | }, actual.getGeoJsonArray()));
238 | }
239 |
240 | @Test
241 | public void getLocationArrayBuilder_withNotExistingResponse() {
242 | // Setup
243 | GetResponse response1 = mock(GetResponse.class, Mockito.RETURNS_DEEP_STUBS);
244 | when(response1.isExists()).thenReturn(true);
245 | Map map1 = mock(Map.class);
246 | when(response1.getSource().get("shape")).thenReturn(map1);
247 | when(map1.get("coordinates")).thenReturn(Arrays.asList(2.0, 1.0));
248 |
249 | GetResponse response2 = mock(GetResponse.class, Mockito.RETURNS_DEEP_STUBS);
250 | when(response2.isExists()).thenReturn(false);
251 |
252 | MultiGetItemResponse multiGetItemResponseMocked = mock(MultiGetItemResponse.class);
253 | when(multiGetItemResponseMocked.getResponse()).thenReturn(response1, response2);
254 |
255 | Iterator iteratorMocked = mock(Iterator.class);
256 | when(iteratorMocked.next()).thenReturn(multiGetItemResponseMocked);
257 |
258 | // Action
259 | ESShape actual = entityDao.getShape(iteratorMocked, 2);
260 |
261 | // Assert
262 | Assert.assertTrue(Arrays.deepEquals(new double[][] {
263 | new double[] { 2.0, 1.0 }
264 | }, actual.getGeoJsonArray()));
265 | }
266 |
267 | @Test
268 | public void executeBulkRequest() {
269 | // Setup
270 | BulkRequestBuilder bulkRequestBuilderMocked = mock(BulkRequestBuilder.class);
271 | when(bulkRequestBuilderMocked.numberOfActions()).thenReturn(1);
272 |
273 | ListenableActionFuture listenableActionFutureMocked = mock(ListenableActionFuture.class);
274 | when(bulkRequestBuilderMocked.execute()).thenReturn(listenableActionFutureMocked);
275 | BulkResponse bulkResponseMocked = mock(BulkResponse.class);
276 | when(listenableActionFutureMocked.actionGet()).thenReturn(bulkResponseMocked);
277 | when(bulkResponseMocked.hasFailures()).thenReturn(false);
278 |
279 | // Action
280 | entityDao.executeBulkRequest(bulkRequestBuilderMocked);
281 |
282 | // Assert
283 | verify(bulkRequestBuilderMocked, times(1)).execute();
284 | verify(bulkResponseMocked, times(0)).iterator();
285 | }
286 |
287 | @Test
288 | public void executeBulkRequest_withFailure() {
289 | // Setup
290 | BulkRequestBuilder bulkRequestBuilderMocked = mock(BulkRequestBuilder.class);
291 | when(bulkRequestBuilderMocked.numberOfActions()).thenReturn(1);
292 |
293 | ListenableActionFuture listenableActionFutureMocked = mock(ListenableActionFuture.class);
294 | when(bulkRequestBuilderMocked.execute()).thenReturn(listenableActionFutureMocked);
295 | BulkResponse bulkResponseMocked = mock(BulkResponse.class);
296 | when(listenableActionFutureMocked.actionGet()).thenReturn(bulkResponseMocked);
297 | when(bulkResponseMocked.hasFailures()).thenReturn(true);
298 |
299 | Iterator iteratorMocked = mock(Iterator.class);
300 | when(bulkResponseMocked.iterator()).thenReturn(iteratorMocked);
301 | BulkItemResponse response1 = mock(BulkItemResponse.class);
302 | when(response1.isFailed()).thenReturn(true);
303 | when(iteratorMocked.hasNext()).thenReturn(true, false);
304 | when(iteratorMocked.next()).thenReturn(response1);
305 |
306 | // Action
307 | entityDao.executeBulkRequest(bulkRequestBuilderMocked);
308 |
309 | // Assert
310 | verify(bulkRequestBuilderMocked, times(1)).execute();
311 | verify(bulkResponseMocked, times(1)).iterator();
312 | }
313 |
314 | @Test
315 | public void executeBulkRequest_withNoResult() {
316 | // Setup
317 | BulkRequestBuilder bulkRequestBuilderMocked = mock(BulkRequestBuilder.class);
318 | when(bulkRequestBuilderMocked.numberOfActions()).thenReturn(0);
319 |
320 | // Action
321 | entityDao.executeBulkRequest(bulkRequestBuilderMocked);
322 |
323 | // Assert
324 | verify(bulkRequestBuilderMocked, times(0)).execute();
325 | }
326 |
327 | /* FIND */
328 |
329 | @Test
330 | public void find() throws Exception {
331 | // Setup
332 | ESNode node = mock(ESNode.class);
333 |
334 | doReturn(Arrays.asList(node)).when(entityDao).findAll(ESNode.class, 1);
335 |
336 | // Action
337 | entityDao.find(ESNode.class, 1);
338 |
339 | // Assert
340 | verify(entityDao, times(1)).findAll(ESNode.class, 1);
341 | }
342 |
343 | /* FIND ALL */
344 |
345 | @Test
346 | public void findAll() {
347 | // Setup
348 | Node node1 = OsmDataBuilder.buildSampleNode(1);
349 | Node node2 = OsmDataBuilder.buildSampleNode(2);
350 |
351 | MultiGetRequestBuilder multiGetRequestBuilderMocked = mock(MultiGetRequestBuilder.class);
352 | doReturn(multiGetRequestBuilderMocked).when(entityDao).buildMultiGetRequest(ESNode.class, 1, 2);
353 | doReturn(Arrays.asList(node1, node2)).when(entityDao).executeMultiGetRequest(ESNode.class, multiGetRequestBuilderMocked);
354 |
355 | // Action
356 | List nodes = entityDao.findAll(ESNode.class, 1, 2);
357 |
358 | // Assert
359 | verify(entityDao).buildMultiGetRequest(ESNode.class, 1, 2);
360 | verify(entityDao).executeMultiGetRequest(ESNode.class, multiGetRequestBuilderMocked);
361 | Assert.assertEquals(Arrays.asList(node1, node2), nodes);
362 | }
363 |
364 | @Test
365 | public void findAll_withEmptyArray() {
366 | // Action
367 | entityDao.findAll(ESNode.class);
368 |
369 | // Assert
370 | verify(entityDao, times(0)).buildMultiGetRequest(any(Class.class), any(long[].class));
371 | verify(entityDao, times(0)).executeMultiGetRequest(any(Class.class), any(MultiGetRequestBuilder.class));
372 | }
373 |
374 | @Test
375 | public void findAll_withNullArray() {
376 | // Action
377 | entityDao.findAll(ESNode.class, null);
378 |
379 | // Assert
380 | verify(entityDao, times(0)).buildMultiGetRequest(any(Class.class), any(long[].class));
381 | verify(entityDao, times(0)).executeMultiGetRequest(any(Class.class), any(MultiGetRequestBuilder.class));
382 | }
383 |
384 | @Test(expected = DaoException.class)
385 | public void findAll_withException() {
386 | // Setup
387 | MultiGetRequestBuilder multiGetRequestBuilderMocked = mock(MultiGetRequestBuilder.class);
388 | doReturn(multiGetRequestBuilderMocked).when(entityDao).buildMultiGetRequest(ESNode.class, 1, 2);
389 | doThrow(new RuntimeException("Simulated Exception")).when(entityDao).executeMultiGetRequest(ESNode.class, multiGetRequestBuilderMocked);
390 |
391 | // Action
392 | entityDao.findAll(ESNode.class, 1, 2);
393 | }
394 |
395 | @Test
396 | public void buildMultiGetRequest() {
397 | // Setup
398 | MultiGetRequestBuilder multiGetRequestBuilderMocked = mock(MultiGetRequestBuilder.class);
399 | when(clientMocked.prepareMultiGet()).thenReturn(multiGetRequestBuilderMocked);
400 |
401 | // Action
402 | MultiGetRequestBuilder actual = entityDao.buildMultiGetRequest(ESNode.class, 1, 2);
403 |
404 | // Assert
405 | Item item1 = new Item(INDEX_NAME, ESEntityType.NODE.getIndiceName(), "1");
406 | Item item2 = new Item(INDEX_NAME, ESEntityType.NODE.getIndiceName(), "2");
407 | verify(multiGetRequestBuilderMocked).add(argThat(new ItemMatcher(item1)));
408 | verify(multiGetRequestBuilderMocked).add(argThat(new ItemMatcher(item2)));
409 | Assert.assertSame(multiGetRequestBuilderMocked, actual);
410 | }
411 |
412 | @Test(expected = IllegalArgumentException.class)
413 | public void buildMultiGetRequest_withInvalidClass() {
414 | // Action
415 | entityDao.buildMultiGetRequest(ESEntity.class, 1);
416 | }
417 |
418 | @Test
419 | public void executeMultiGetRequest() {
420 | // Setup
421 | ESNode node1 = OsmDataBuilder.buildSampleESNode(1);
422 | ESNode node2 = OsmDataBuilder.buildSampleESNode(2);
423 |
424 | MultiGetRequestBuilder multiGetRequestBuilderMocked = mock(MultiGetRequestBuilder.class);
425 |
426 | ListenableActionFuture listenableActionFutureMocked = mock(ListenableActionFuture.class);
427 | when(multiGetRequestBuilderMocked.execute()).thenReturn(listenableActionFutureMocked);
428 | MultiGetResponse multiGetResponseMocked = mock(MultiGetResponse.class);
429 | when(listenableActionFutureMocked.actionGet()).thenReturn(multiGetResponseMocked);
430 |
431 | Iterator iterator = mock(Iterator.class);
432 | when(multiGetResponseMocked.iterator()).thenReturn(iterator);
433 | MultiGetItemResponse item1 = mock(MultiGetItemResponse.class);
434 | MultiGetItemResponse item2 = mock(MultiGetItemResponse.class);
435 | when(iterator.hasNext()).thenReturn(true, true, false);
436 | when(iterator.next()).thenReturn(item1, item2);
437 |
438 | doReturn(node1).when(entityDao).buildEntityFromGetResponse(ESNode.class, item1);
439 | doReturn(node2).when(entityDao).buildEntityFromGetResponse(ESNode.class, item2);
440 |
441 | // Action
442 | List actual = entityDao.executeMultiGetRequest(ESNode.class, multiGetRequestBuilderMocked);
443 |
444 | // Assert
445 | Assert.assertEquals(Arrays.asList(node1, node2), actual);
446 | }
447 |
448 | @Test(expected = DaoException.class)
449 | public void buildEntityFromGetResponse_withNotExistingResponse() {
450 | // Setup
451 | MultiGetItemResponse multiGetItemResponseMocked = mock(MultiGetItemResponse.class);
452 | GetResponse getResponseMocked = mock(GetResponse.class);
453 | when(getResponseMocked.isExists()).thenReturn(false);
454 | when(multiGetItemResponseMocked.getResponse()).thenReturn(getResponseMocked);
455 |
456 | // Action
457 | entityDao.buildEntityFromGetResponse(ESNode.class, multiGetItemResponseMocked);
458 | }
459 |
460 | @Test(expected = IllegalArgumentException.class)
461 | public void buildEntityFromGetResponse_withNullType() {
462 | // Setup
463 | MultiGetItemResponse multiGetItemResponseMocked = mock(MultiGetItemResponse.class);
464 | GetResponse getResponseMocked = mock(GetResponse.class);
465 | when(getResponseMocked.isExists()).thenReturn(true);
466 | when(multiGetItemResponseMocked.getResponse()).thenReturn(getResponseMocked);
467 |
468 | // Action
469 | entityDao.buildEntityFromGetResponse(null, multiGetItemResponseMocked);
470 | }
471 |
472 | @Test(expected = IllegalArgumentException.class)
473 | public void buildEntityFromGetResponse_withInvalidType() {
474 | // Setup
475 | MultiGetItemResponse multiGetItemResponseMocked = mock(MultiGetItemResponse.class);
476 | GetResponse getResponseMocked = mock(GetResponse.class);
477 | when(getResponseMocked.isExists()).thenReturn(true);
478 | when(multiGetItemResponseMocked.getResponse()).thenReturn(getResponseMocked);
479 |
480 | // Action
481 | entityDao.buildEntityFromGetResponse(ESEntity.class, multiGetItemResponseMocked);
482 | }
483 |
484 | /* DELETE */
485 |
486 | @Test
487 | public void delete() {
488 | // Setup
489 | DeleteRequestBuilder deleteRequestBuilder = mock(DeleteRequestBuilder.class);
490 | when(clientMocked.prepareDelete(any(String.class), any(String.class), any(String.class))).thenReturn(deleteRequestBuilder);
491 | ListenableActionFuture listenableActionFutureMocked = mock(ListenableActionFuture.class);
492 | when(deleteRequestBuilder.execute()).thenReturn(listenableActionFutureMocked);
493 | DeleteResponse deleteResponseMocked = mock(DeleteResponse.class);
494 | when(listenableActionFutureMocked.actionGet()).thenReturn(deleteResponseMocked);
495 | when(deleteResponseMocked.isFound()).thenReturn(true);
496 |
497 | // Action
498 | boolean actual = entityDao.delete(ESNode.class, 1l);
499 |
500 | // Assert
501 | verify(clientMocked).prepareDelete(INDEX_NAME, "node", "1");
502 | assertTrue(actual);
503 | }
504 |
505 | @Test
506 | public void delete_withNotFoundDocument() {
507 | // Setup
508 | DeleteRequestBuilder deleteRequestBuilder = mock(DeleteRequestBuilder.class);
509 | when(clientMocked.prepareDelete(any(String.class), any(String.class), any(String.class))).thenReturn(deleteRequestBuilder);
510 | ListenableActionFuture listenableActionFutureMocked = mock(ListenableActionFuture.class);
511 | when(deleteRequestBuilder.execute()).thenReturn(listenableActionFutureMocked);
512 | DeleteResponse deleteResponseMocked = mock(DeleteResponse.class);
513 | when(listenableActionFutureMocked.actionGet()).thenReturn(deleteResponseMocked);
514 | when(deleteResponseMocked.isFound()).thenReturn(false);
515 |
516 | // Action
517 | boolean actual = entityDao.delete(ESNode.class, 1l);
518 |
519 | // Assert
520 | assertFalse(actual);
521 | }
522 |
523 | @Test(expected = DaoException.class)
524 | public void delete_withBrokenConnector() {
525 | // Setup
526 | DeleteRequestBuilder deleteRequestBuilder = mock(DeleteRequestBuilder.class);
527 | when(clientMocked.prepareDelete(any(String.class), any(String.class), any(String.class))).thenReturn(deleteRequestBuilder);
528 | ListenableActionFuture listenableActionFutureMocked = mock(ListenableActionFuture.class);
529 | when(deleteRequestBuilder.execute()).thenReturn(listenableActionFutureMocked);
530 | when(listenableActionFutureMocked.actionGet()).thenThrow(new ElasticsearchException("Simulated exception"));
531 |
532 | // Action
533 | entityDao.delete(ESNode.class, 1l);
534 | }
535 |
536 | public class ItemMatcher extends BaseMatcher- {
537 |
538 | private final Item expected;
539 |
540 | public ItemMatcher(Item expected) {
541 | this.expected = expected;
542 | }
543 |
544 | @Override
545 | public boolean matches(Object item) {
546 | if (expected == item) return true;
547 | if (item == null) return false;
548 | if (expected.getClass() != item.getClass()) return false;
549 | Item other = (Item) item;
550 | return expected.index().equals(other.index())
551 | && expected.type().equals(other.type())
552 | && expected.id().equals(other.id())
553 | && Arrays.equals(expected.fields(), other.fields());
554 | }
555 |
556 | @Override
557 | public void describeTo(Description description) {}
558 |
559 | }
560 |
561 | }
562 |
--------------------------------------------------------------------------------
/src/test/java/org/openstreetmap/osmosis/plugin/elasticsearch/integration/PluginIntegrationITest.java:
--------------------------------------------------------------------------------
1 | package org.openstreetmap.osmosis.plugin.elasticsearch.integration;
2 |
3 | import static org.junit.Assert.assertEquals;
4 | import static org.junit.Assert.assertTrue;
5 |
6 | import java.io.File;
7 | import java.net.URISyntaxException;
8 | import java.net.URL;
9 |
10 | import org.elasticsearch.action.admin.indices.exists.indices.IndicesExistsRequest;
11 | import org.elasticsearch.action.count.CountRequest;
12 | import org.junit.Test;
13 | import org.openstreetmap.osmosis.core.Osmosis;
14 | import org.openstreetmap.osmosis.plugin.elasticsearch.model.entity.ESEntityType;
15 | import org.openstreetmap.osmosis.plugin.elasticsearch.testutils.AbstractElasticSearchInMemoryTest;
16 |
17 | public class PluginIntegrationITest extends AbstractElasticSearchInMemoryTest {
18 |
19 | private static final String INDEX_NAME = "osm-test";
20 |
21 | @Test
22 | public void countMainIndexedDocuments() throws Exception {
23 | // Action
24 | Osmosis.run(new String[] {
25 | "--read-xml",
26 | getResourceFile("mondeville-20130123.osm").getPath(),
27 | "--tag-filter",
28 | "accept-relations",
29 | "boundary=administrative",
30 | "--tag-filter",
31 | "accept-ways",
32 | "highway=*",
33 | "--used-node",
34 | "--write-elasticsearch",
35 | "cluster.hosts=" + nodeAddress(),
36 | "cluster.name=" + clusterName(),
37 | "index.name=" + INDEX_NAME,
38 | "index.create=true"
39 | });
40 | refresh(INDEX_NAME);
41 |
42 | // Assert
43 | assertTrue(client().admin().indices().exists(new IndicesExistsRequest(INDEX_NAME)).actionGet().isExists());
44 | assertEquals(777, client().count(new CountRequest(INDEX_NAME).types(ESEntityType.NODE.getIndiceName())).actionGet().getCount());
45 | assertEquals(57, client().count(new CountRequest(INDEX_NAME).types(ESEntityType.WAY.getIndiceName())).actionGet().getCount());
46 | }
47 |
48 | private File getResourceFile(String filename) throws URISyntaxException {
49 | URL url = getClass().getResource("/" + filename);
50 | return new File(url.toURI());
51 | }
52 |
53 | }
54 |
--------------------------------------------------------------------------------
/src/test/java/org/openstreetmap/osmosis/plugin/elasticsearch/model/entity/ESNodeITest.java:
--------------------------------------------------------------------------------
1 | package org.openstreetmap.osmosis.plugin.elasticsearch.model.entity;
2 |
3 | import java.util.HashMap;
4 |
5 | import com.spatial4j.core.shape.Point;
6 | import com.spatial4j.core.shape.Rectangle;
7 | import com.spatial4j.core.shape.impl.PointImpl;
8 |
9 | import org.elasticsearch.action.get.GetResponse;
10 | import org.elasticsearch.action.search.SearchResponse;
11 | import org.elasticsearch.common.geo.builders.ShapeBuilder;
12 | import org.elasticsearch.common.unit.DistanceUnit;
13 | import org.elasticsearch.index.query.GeoDistanceQueryBuilder;
14 | import org.elasticsearch.index.query.GeoShapeQueryBuilder;
15 | import org.elasticsearch.index.query.QueryBuilders;
16 | import org.elasticsearch.search.sort.GeoDistanceSortBuilder;
17 | import org.junit.Before;
18 | import org.junit.Test;
19 | import org.openstreetmap.osmosis.plugin.elasticsearch.service.IndexAdminService;
20 | import org.openstreetmap.osmosis.plugin.elasticsearch.testutils.AbstractElasticSearchInMemoryTest;
21 |
22 | import junit.framework.Assert;
23 | import org.elasticsearch.common.geo.GeoUtils;
24 |
25 | import static org.elasticsearch.common.geo.builders.ShapeBuilder.SPATIAL_CONTEXT;
26 |
27 | public class ESNodeITest extends AbstractElasticSearchInMemoryTest {
28 |
29 | private static final String INDEX_NAME = "shape-test";
30 |
31 | private IndexAdminService indexAdminService;
32 |
33 | @Before
34 | public void setUp() throws Exception {
35 | indexAdminService = new IndexAdminService(client());
36 | HashMap mappings = new HashMap();
37 | mappings.put(ESEntityType.NODE.getIndiceName(), "{\"properties\":{\"centroid\":{\"type\":\"geo_point\"},\"shape\":{\"type\":\"geo_shape\"}}}");
38 | indexAdminService.createIndex(INDEX_NAME, 1, 0, mappings);
39 | }
40 |
41 | @Test
42 | public void getNode() {
43 | // Setup
44 | ESNode node = ESNode.Builder.create().id(1854801716).location(48.675652, 2.384955)
45 | .addTag("highway", "traffic_signals").build();
46 |
47 | // Action
48 | index(INDEX_NAME, node);
49 | refresh();
50 |
51 | // Assert
52 | GetResponse response = client().prepareGet(INDEX_NAME, ESEntityType.NODE.getIndiceName(), "1854801716").execute().actionGet();
53 | Assert.assertTrue(response.isExists());
54 | String expected = "{\"centroid\":[2.384955,48.675652],\"shape\":{\"type\":\"point\",\"coordinates\":" +
55 | "[2.384955,48.675652]},\"tags\":{\"highway\":\"traffic_signals\"}}";
56 | String actual = response.getSourceAsString();
57 | Assert.assertEquals(expected, actual);
58 | }
59 |
60 | @Test
61 | public void searchNode_withGeoShape() {
62 | // Setup
63 | ESNode node = ESNode.Builder.create().id(1854801716).location(48.675652, 2.384955)
64 | .addTag("highway", "traffic_signals").build();
65 | index(INDEX_NAME, node);
66 | refresh();
67 |
68 | // Action
69 | ShapeBuilder shape = buildSquareShape(48.675652, 2.384955, 20);
70 | SearchResponse searchResponse = client().prepareSearch(INDEX_NAME).setTypes(ESEntityType.NODE.getIndiceName())
71 | .setQuery(QueryBuilders.matchAllQuery())
72 | .setPostFilter(new GeoShapeQueryBuilder("shape", shape))
73 | .execute().actionGet();
74 |
75 | // Assert
76 | Assert.assertEquals(1, searchResponse.getHits().hits().length);
77 | }
78 |
79 | @Test
80 | public void searchNode_withGeoShape_shouldNotMatch() {
81 | // Setup
82 | ESNode node = ESNode.Builder.create().id(1854801716).location(48.675652, 2.384955)
83 | .addTag("highway", "traffic_signals").build();
84 | index(INDEX_NAME, node);
85 | refresh();
86 |
87 | // Action
88 | ShapeBuilder shape = buildSquareShape(48.676455, 2.380899, 20);
89 | SearchResponse searchResponse = client().prepareSearch(INDEX_NAME).setTypes(ESEntityType.NODE.getIndiceName())
90 | .setQuery(QueryBuilders.matchAllQuery())
91 | .setPostFilter(new GeoShapeQueryBuilder("shape", shape))
92 | .execute().actionGet();
93 |
94 | // Assert
95 | Assert.assertEquals(0, searchResponse.getHits().hits().length);
96 | }
97 |
98 | @Test
99 | public void searchNode_withGeoShapeAndLargeFilterShape() {
100 | // Setup
101 | ESNode node = ESNode.Builder.create().id(1854801716).location(48.675652, 2.384955)
102 | .addTag("highway", "traffic_signals").build();
103 | index(INDEX_NAME, node);
104 | refresh();
105 |
106 | // Action
107 | ShapeBuilder shape = buildSquareShape(48.675652, 2.384955, 10000);
108 | SearchResponse searchResponse = client().prepareSearch(INDEX_NAME).setTypes(ESEntityType.NODE.getIndiceName())
109 | .setQuery(QueryBuilders.matchAllQuery())
110 | .setPostFilter(new GeoShapeQueryBuilder("shape", shape))
111 | .execute().actionGet();
112 |
113 | // Assert
114 | Assert.assertEquals(1, searchResponse.getHits().hits().length);
115 | }
116 |
117 | @Test
118 | public void searchNode_withGeoShapeAndCloseFilterShape() {
119 | // Setup
120 | ESNode node = ESNode.Builder.create().id(1854801716).location(48.675652, 2.384955)
121 | .addTag("highway", "traffic_signals").build();
122 | index(INDEX_NAME, node);
123 | refresh();
124 |
125 | // Action
126 | // Can't do better than 20m with default shape configuration
127 | ShapeBuilder shape = buildSquareShape(48.675652, 2.384955, 20);
128 | SearchResponse searchResponse = client().prepareSearch(INDEX_NAME).setTypes(ESEntityType.NODE.getIndiceName())
129 | .setQuery(QueryBuilders.matchAllQuery())
130 | .setPostFilter(new GeoShapeQueryBuilder("shape", shape))
131 | .execute().actionGet();
132 |
133 | // Assert
134 | Assert.assertEquals(1, searchResponse.getHits().hits().length);
135 | }
136 |
137 | @Test
138 | public void searchNode_withGeoPoint() {
139 | // Setup
140 | ESNode node = ESNode.Builder.create().id(1854801716).location(48.675652, 2.384955)
141 | .addTag("highway", "traffic_signals").build();
142 | index(INDEX_NAME, node);
143 | refresh();
144 |
145 | // Action
146 | SearchResponse searchResponse = client().prepareSearch(INDEX_NAME).setTypes(ESEntityType.NODE.getIndiceName())
147 | .setQuery(QueryBuilders.matchAllQuery())
148 | .setPostFilter(new GeoDistanceQueryBuilder("centroid").point(48.675652, 2.384955).distance(20, DistanceUnit.METERS))
149 | .execute().actionGet();
150 |
151 | // Assert
152 | Assert.assertEquals(1, searchResponse.getHits().hits().length);
153 | }
154 |
155 | @Test
156 | public void searchNode_withGeoPoint_shouldNotMatch() {
157 | // Setup
158 | ESNode node = ESNode.Builder.create().id(1854801716).location(48.675652, 2.384955)
159 | .addTag("highway", "traffic_signals").build();
160 | index(INDEX_NAME, node);
161 | refresh();
162 |
163 | // Action
164 | SearchResponse searchResponse = client().prepareSearch(INDEX_NAME).setTypes(ESEntityType.NODE.getIndiceName())
165 | .setQuery(QueryBuilders.matchAllQuery())
166 | .setPostFilter(new GeoDistanceQueryBuilder("centroid").point(48.676455, 2.380899).distance(20, DistanceUnit.METERS))
167 | .execute().actionGet();
168 |
169 | // Assert
170 | Assert.assertEquals(0, searchResponse.getHits().hits().length);
171 | }
172 |
173 | @Test
174 | public void searchNode_withGeoPoint_severalPointsPlusSort() {
175 | // Setup
176 | ESNode node1 = ESNode.Builder.create().id(1854801716).location(48.675652, 2.384955)
177 | .addTag("highway", "traffic_signals").build();
178 | ESNode node2 = ESNode.Builder.create().id(1854801717).location(48.676455, 2.380899)
179 | .addTag("highway", "traffic_signals").build();
180 | index(INDEX_NAME, node1, node2);
181 | refresh();
182 |
183 | // Action
184 | SearchResponse searchResponse = client().prepareSearch(INDEX_NAME).setTypes(ESEntityType.NODE.getIndiceName())
185 | .setQuery(QueryBuilders.matchAllQuery())
186 | .setPostFilter(new GeoDistanceQueryBuilder("centroid").point(48.676455, 2.380899).distance(1, DistanceUnit.KILOMETERS))
187 | .addSort(new GeoDistanceSortBuilder("centroid").point(48.676455, 2.380899).unit(DistanceUnit.METERS))
188 | .execute().actionGet();
189 |
190 | // Assert
191 | Assert.assertEquals(2, searchResponse.getHits().hits().length);
192 | Assert.assertEquals("1854801717", searchResponse.getHits().getAt(0).getId());
193 | Assert.assertEquals("1854801716", searchResponse.getHits().getAt(1).getId());
194 | }
195 |
196 | protected ShapeBuilder buildSquareShape(double centerLat, double centerLon, double distanceMeter) {
197 | Point point = new PointImpl(centerLon, centerLat, SPATIAL_CONTEXT);
198 | Rectangle shape = SPATIAL_CONTEXT.makeCircle(point, 360 * distanceMeter / GeoUtils.EARTH_EQUATOR).getBoundingBox();
199 | return ShapeBuilder.newEnvelope().bottomRight(shape.getMaxX(), shape.getMinY()).topLeft(shape.getMinX(), shape.getMaxY());
200 | }
201 |
202 | }
203 |
--------------------------------------------------------------------------------
/src/test/java/org/openstreetmap/osmosis/plugin/elasticsearch/model/entity/ESNodeUTest.java:
--------------------------------------------------------------------------------
1 | package org.openstreetmap.osmosis.plugin.elasticsearch.model.entity;
2 |
3 | import static org.junit.Assert.assertEquals;
4 | import static org.mockito.Mockito.mock;
5 | import static org.mockito.Mockito.when;
6 |
7 | import java.util.ArrayList;
8 | import java.util.Arrays;
9 | import java.util.HashMap;
10 | import java.util.List;
11 | import java.util.Map;
12 |
13 | import org.elasticsearch.action.get.GetResponse;
14 | import org.junit.Test;
15 | import org.mockito.Mockito;
16 | import org.openstreetmap.osmosis.core.domain.v0_6.Node;
17 | import org.openstreetmap.osmosis.core.domain.v0_6.Tag;
18 |
19 | public class ESNodeUTest {
20 |
21 | @Test
22 | public void buildFromNodeEntity() {
23 | // Setup
24 | Node node = mock(Node.class);
25 | when(node.getId()).thenReturn(1l);
26 | List tags = new ArrayList();
27 | tags.add(new Tag("highway", "primary"));
28 | when(node.getTags()).thenReturn(tags);
29 | when(node.getLatitude()).thenReturn(1.0);
30 | when(node.getLongitude()).thenReturn(2.0);
31 |
32 | ESNode expected = ESNode.Builder.create().id(1l).location(1.0, 2.0)
33 | .addTag("highway", "primary").build();
34 |
35 | // Action
36 | ESNode actual = ESNode.Builder.buildFromEntity(node);
37 |
38 | // Assert
39 | assertEquals(expected, actual);
40 | }
41 |
42 | @Test
43 | public void buildFromGetReponse() {
44 | // Setup
45 | GetResponse response = mock(GetResponse.class, Mockito.RETURNS_DEEP_STUBS);
46 | when(response.getType()).thenReturn(ESEntityType.NODE.getIndiceName());
47 | when(response.getId()).thenReturn("1");
48 | Map tags = new HashMap();
49 | tags.put("highway", "primary");
50 | when(response.getSource().get("tags")).thenReturn(tags);
51 | List location = Arrays.asList(new Double[] { 2.0, 1.0 });
52 | @SuppressWarnings("unchecked")
53 | Map shape = mock(Map.class);
54 | when(shape.get("coordinates")).thenReturn(location);
55 | when(response.getSource().get("shape")).thenReturn(shape);
56 |
57 | ESNode expected = ESNode.Builder.create().id(1l).location(1.0, 2.0)
58 | .addTag("highway", "primary").build();
59 |
60 | // Action
61 | ESNode actual = ESNode.Builder.buildFromGetReponse(response);
62 |
63 | // Assert
64 | assertEquals(expected, actual);
65 | }
66 |
67 | @Test(expected = IllegalArgumentException.class)
68 | public void buildFromGetReponse_withInvalidGetResponse() {
69 | // Setup
70 | GetResponse response = mock(GetResponse.class, Mockito.RETURNS_DEEP_STUBS);
71 | when(response.getType()).thenReturn(ESEntityType.WAY.getIndiceName());
72 |
73 | // Action
74 | ESNode.Builder.buildFromGetReponse(response);
75 | }
76 |
77 | @Test
78 | public void getType() {
79 | // Setup
80 | ESNode node = ESNode.Builder.create().id(1l).location(1.0, 2.0)
81 | .addTag("highway", "primary").build();
82 |
83 | // Action
84 | ESEntityType actual = node.getEntityType();
85 |
86 | // Assert
87 | assertEquals(ESEntityType.NODE, actual);
88 | }
89 |
90 | @Test
91 | public void toJson() {
92 | // Setup
93 | ESNode node = ESNode.Builder.create().id(1l).location(1.0, 2.0)
94 | .addTag("highway", "traffic_signals").build();
95 | String expected = "{\"centroid\":[2.0,1.0],\"shape\":{\"type\":\"point\",\"coordinates\":[2.0,1.0]}," +
96 | "\"tags\":{\"highway\":\"traffic_signals\"}}";
97 |
98 | // Action
99 | String actual = node.toJson();
100 |
101 | // Assert
102 | assertEquals(expected, actual);
103 | }
104 |
105 | }
106 |
--------------------------------------------------------------------------------
/src/test/java/org/openstreetmap/osmosis/plugin/elasticsearch/model/entity/ESWayITest.java:
--------------------------------------------------------------------------------
1 | package org.openstreetmap.osmosis.plugin.elasticsearch.model.entity;
2 |
3 | import java.util.HashMap;
4 |
5 | import com.spatial4j.core.shape.Point;
6 | import com.spatial4j.core.shape.Rectangle;
7 | import com.spatial4j.core.shape.impl.PointImpl;
8 |
9 | import org.elasticsearch.action.get.GetResponse;
10 | import org.elasticsearch.action.search.SearchResponse;
11 | import org.elasticsearch.common.geo.builders.ShapeBuilder;
12 | import org.elasticsearch.index.query.GeoShapeQueryBuilder;
13 | import org.elasticsearch.index.query.QueryBuilders;
14 | import org.junit.Before;
15 | import org.junit.Test;
16 | import org.junit.Assert;
17 | import org.openstreetmap.osmosis.plugin.elasticsearch.service.IndexAdminService;
18 | import org.openstreetmap.osmosis.plugin.elasticsearch.testutils.AbstractElasticSearchInMemoryTest;
19 |
20 | import org.elasticsearch.common.geo.GeoUtils;
21 | import static org.elasticsearch.common.geo.builders.ShapeBuilder.SPATIAL_CONTEXT;
22 |
23 | public class ESWayITest extends AbstractElasticSearchInMemoryTest {
24 |
25 | private static final String INDEX_NAME = "shape-test";
26 |
27 | private IndexAdminService indexAdminService;
28 |
29 | @Before
30 | public void setUp() throws Exception {
31 | indexAdminService = new IndexAdminService(client());
32 | HashMap mappings = new HashMap();
33 | mappings.put(ESEntityType.WAY.getIndiceName(), "{\"properties\":{\"centroid\":{\"type\":\"geo_point\"},\"shape\":{\"type\":\"geo_shape\"}}}");
34 | indexAdminService.createIndex(INDEX_NAME, 1, 0, mappings);
35 | }
36 |
37 | @Test
38 | public void getWay() {
39 | // Setup
40 | ESWay way = ESWay.Builder.create().id(40849832l)
41 | .addLocation(48.675763, 2.379358).addLocation(48.675584, 2.379606).addLocation(48.675288, 2.379955)
42 | .addTag("highway", "residential").addTag("name", "Avenue Marc Sangnier").build();
43 |
44 | // Action
45 | index(INDEX_NAME, way);
46 | refresh();
47 |
48 | // Assert
49 | GetResponse response = client().prepareGet(INDEX_NAME, ESEntityType.WAY.getIndiceName(), "40849832").execute().actionGet();
50 | Assert.assertTrue(response.isExists());
51 | String expected = "{\"centroid\":[2.37966091923039,48.67553114382843],\"lengthKm\":0.08489436252741311," +
52 | "\"areaKm2\":0.0,\"shape\":{\"type\":\"linestring\",\"coordinates\":" +
53 | "[[2.379358,48.675763],[2.379606,48.675584],[2.379955,48.675288]]}," +
54 | "\"tags\":{\"highway\":\"residential\",\"name\":\"Avenue Marc Sangnier\"}}";
55 | String actual = response.getSourceAsString();
56 | Assert.assertEquals(expected, actual);
57 | }
58 |
59 | @Test
60 | public void getClosedWay() {
61 | // Setup
62 | ESWay expectedWay = ESWay.Builder.create().id(97583115l)
63 | .addLocation(48.67581, 2.379255).addLocation(48.675874, 2.379358).addLocation(48.675946, 2.379262)
64 | .addLocation(48.675885, 2.379161).addLocation(48.67581, 2.379255)
65 | .addTag("building", "yes").build();
66 |
67 | // Action
68 | indexAdminService.index(INDEX_NAME, ESEntityType.WAY.getIndiceName(), 97583115l, expectedWay.toJson());
69 | refresh();
70 |
71 | // Assert
72 | GetResponse response = client().prepareGet(INDEX_NAME, ESEntityType.WAY.getIndiceName(), "97583115").execute().actionGet();
73 | Assert.assertTrue(response.isExists());
74 |
75 | // Instead of comparing strings, assert a real way object,
76 | // The original assert (equal strings) Fails because of rounding differences for areaKm2:
77 | // expected: areaKm2":1.661088030[79727]3E-4 > but was: areaKm2":1.661088030[80079]3E-4
78 | // Thas why I decided to parse the response to a way object.
79 |
80 | ESWay actualWay = ESWay.Builder.buildFromGetReponse(response);
81 | // Since we set the id on insert, test if it is equal
82 | Assert.assertEquals(expectedWay.getId(), actualWay.getId());
83 | Assert.assertEquals(expectedWay.getShapeType(), actualWay.getShapeType());
84 | Assert.assertArrayEquals(expectedWay.getCoordinates(), actualWay.getCoordinates());
85 | // Centroid should be equal
86 | Assert.assertEquals(expectedWay.getCentroid(), actualWay.getCentroid());
87 | // Are the tags equal?
88 | Assert.assertEquals(expectedWay.getTags(), actualWay.getTags());
89 | // Is the area equal? Might have to set a tolerance
90 | Assert.assertEquals(expectedWay.getArea(), actualWay.getArea(), 0);
91 | Assert.assertEquals(expectedWay.getLenght(), actualWay.getLenght(),0);
92 | //System.out.println(response.getSource());
93 |
94 | }
95 |
96 | @Test
97 | public void searchWay_withGeoShape() {
98 | // Setup
99 | ESWay way = ESWay.Builder.create().id(40849832l)
100 | .addLocation(48.675763, 2.379358).addLocation(48.675584, 2.379606).addLocation(48.675288, 2.379955)
101 | .addTag("highway", "residential").addTag("name", "Avenue Marc Sangnier").build();
102 | indexAdminService.index(INDEX_NAME, ESEntityType.WAY.getIndiceName(), 40849832l, way.toJson());
103 | refresh();
104 |
105 | // Action
106 | ShapeBuilder shape = buildSquareShape(48.675763, 2.379358, 20);
107 | SearchResponse searchResponse = client().prepareSearch(INDEX_NAME).setTypes(ESEntityType.WAY.getIndiceName())
108 | .setQuery(QueryBuilders.matchAllQuery())
109 | .setPostFilter(new GeoShapeQueryBuilder("shape", shape))
110 | .execute().actionGet();
111 |
112 | // Assert
113 | Assert.assertEquals(1, searchResponse.getHits().hits().length);
114 | }
115 |
116 | @Test
117 | public void searchWay_withGeoShape_shouldNotMatch() {
118 | // Setup
119 | ESWay way = ESWay.Builder.create().id(40849832l)
120 | .addLocation(48.675763, 2.379358).addLocation(48.675584, 2.379606).addLocation(48.675288, 2.379955)
121 | .addTag("highway", "residential").addTag("name", "Avenue Marc Sangnier").build();
122 | indexAdminService.index(INDEX_NAME, ESEntityType.WAY.getIndiceName(), 40849832l, way.toJson());
123 | refresh();
124 |
125 | // Action
126 | ShapeBuilder shape = buildSquareShape(48.676455, 2.380899, 20);
127 | SearchResponse searchResponse = client().prepareSearch(INDEX_NAME).setTypes(ESEntityType.WAY.getIndiceName())
128 | .setQuery(QueryBuilders.matchAllQuery())
129 | .setPostFilter(new GeoShapeQueryBuilder("shape", shape))
130 | .execute().actionGet();
131 |
132 | // Assert
133 | Assert.assertEquals(0, searchResponse.getHits().hits().length);
134 | }
135 |
136 | @Test
137 | public void searchWay_withGeoShapeAndLargeFilterShape() {
138 | // Setup
139 | ESWay way = ESWay.Builder.create().id(40849832l)
140 | .addLocation(48.675763, 2.379358).addLocation(48.675584, 2.379606).addLocation(48.675288, 2.379955)
141 | .addTag("highway", "residential").addTag("name", "Avenue Marc Sangnier").build();
142 | indexAdminService.index(INDEX_NAME, ESEntityType.WAY.getIndiceName(), 40849832l, way.toJson());
143 | refresh();
144 |
145 | // Action
146 | ShapeBuilder shape = buildSquareShape(48.675763, 2.379358, 10000);
147 | SearchResponse searchResponse = client().prepareSearch(INDEX_NAME).setTypes(ESEntityType.WAY.getIndiceName())
148 | .setQuery(QueryBuilders.matchAllQuery())
149 | .setPostFilter(new GeoShapeQueryBuilder("shape", shape))
150 | .execute().actionGet();
151 |
152 | // Assert
153 | Assert.assertEquals(1, searchResponse.getHits().hits().length);
154 | }
155 |
156 | @Test
157 | public void searchWay_withGeoShapeAndLargeIndexedShape() {
158 | // Setup
159 | // This way is ~ 550 meters large
160 | ESWay way = ESWay.Builder.create().id(40849832l)
161 | .addLocation(48.675763, 2.379358).addLocation(48.675584, 2.379606).addLocation(48.675087, 2.380314)
162 | .addLocation(48.674958, 2.380947).addLocation(48.675093, 2.381405).addLocation(48.675406, 2.382000)
163 | .addLocation(48.675957, 2.383090).addLocation(48.676137, 2.383404).addLocation(48.676230, 2.384246)
164 | .addLocation(48.675890, 2.384684).addLocation(48.675580, 2.385125)
165 | .addTag("highway", "residential").build();
166 | indexAdminService.index(INDEX_NAME, ESEntityType.WAY.getIndiceName(), 40849832l, way.toJson());
167 | refresh();
168 |
169 | // Action
170 | // ~ 45 meters min shape radius to match
171 | // center between positions index #5 and #6
172 | ShapeBuilder shape = buildSquareShape(48.675689, 2.38259, 45);
173 | SearchResponse searchResponse = client().prepareSearch(INDEX_NAME).setTypes(ESEntityType.WAY.getIndiceName())
174 | .setQuery(QueryBuilders.matchAllQuery())
175 | .setPostFilter(new GeoShapeQueryBuilder("shape", shape))
176 | .execute().actionGet();
177 |
178 | // Assert
179 | Assert.assertEquals(1, searchResponse.getHits().hits().length);
180 | }
181 |
182 | @Test
183 | public void searchClosedWay_withGeoShape() {
184 | // Setup
185 | ESWay way = ESWay.Builder.create().id(97583115l)
186 | .addLocation(48.67581, 2.379255).addLocation(48.675874, 2.379358).addLocation(48.675946, 2.379262)
187 | .addLocation(48.675885, 2.379161).addLocation(48.67581, 2.379255)
188 | .addTag("building", "yes").build();
189 | indexAdminService.index(INDEX_NAME, ESEntityType.WAY.getIndiceName(), 97583115l, way.toJson());
190 | refresh();
191 |
192 | // Action
193 | ShapeBuilder shape = buildSquareShape(48.675763, 2.379358, 100);
194 | SearchResponse searchResponse = client().prepareSearch(INDEX_NAME).setTypes(ESEntityType.WAY.getIndiceName())
195 | .setQuery(QueryBuilders.matchAllQuery())
196 | .setPostFilter(new GeoShapeQueryBuilder("shape", shape))
197 | .execute().actionGet();
198 |
199 | // Assert
200 | Assert.assertEquals(1, searchResponse.getHits().hits().length);
201 | }
202 |
203 | @Test
204 | public void searchClosedWay_withGeoShape_shouldNotMatch() {
205 | // Setup
206 | ESWay way = ESWay.Builder.create().id(97583115l)
207 | .addLocation(48.67581, 2.379255).addLocation(48.675874, 2.379358).addLocation(48.675946, 2.379262)
208 | .addLocation(48.675885, 2.379161).addLocation(48.67581, 2.379255)
209 | .addTag("building", "yes").build();
210 | indexAdminService.index(INDEX_NAME, ESEntityType.WAY.getIndiceName(), 97583115l, way.toJson());
211 | refresh();
212 |
213 | // Action
214 | ShapeBuilder shape = buildSquareShape(48.676455, 2.380899, 20);
215 | SearchResponse searchResponse = client().prepareSearch(INDEX_NAME).setTypes(ESEntityType.WAY.getIndiceName())
216 | .setQuery(QueryBuilders.matchAllQuery())
217 | .setPostFilter(new GeoShapeQueryBuilder("shape", shape))
218 | .execute().actionGet();
219 |
220 | // Assert
221 | Assert.assertEquals(0, searchResponse.getHits().hits().length);
222 | }
223 |
224 | protected ShapeBuilder buildSquareShape(double centerLat, double centerLon, double distanceMeter) {
225 | Point point = new PointImpl(centerLon, centerLat, SPATIAL_CONTEXT);
226 | Rectangle shape = SPATIAL_CONTEXT.makeCircle(point, 360 * distanceMeter / GeoUtils.EARTH_EQUATOR).getBoundingBox();
227 | return ShapeBuilder.newEnvelope().bottomRight(shape.getMaxX(), shape.getMinY()).topLeft(shape.getMinX(), shape.getMaxY());
228 | }
229 |
230 | }
231 |
--------------------------------------------------------------------------------
/src/test/java/org/openstreetmap/osmosis/plugin/elasticsearch/model/entity/ESWayUTest.java:
--------------------------------------------------------------------------------
1 | package org.openstreetmap.osmosis.plugin.elasticsearch.model.entity;
2 |
3 | import static org.junit.Assert.assertEquals;
4 | import static org.mockito.Mockito.mock;
5 | import static org.mockito.Mockito.when;
6 |
7 | import java.util.ArrayList;
8 | import java.util.Arrays;
9 | import java.util.HashMap;
10 | import java.util.List;
11 | import java.util.Map;
12 |
13 | import org.elasticsearch.action.get.GetResponse;
14 | import org.junit.Test;
15 | import org.mockito.Mockito;
16 | import org.openstreetmap.osmosis.core.domain.v0_6.Tag;
17 | import org.openstreetmap.osmosis.core.domain.v0_6.Way;
18 | import org.openstreetmap.osmosis.core.domain.v0_6.WayNode;
19 | import org.openstreetmap.osmosis.plugin.elasticsearch.model.shape.ESShape.ESShapeBuilder;
20 |
21 | public class ESWayUTest {
22 |
23 | @Test
24 | public void buildFromWayEntity() {
25 | // Setup
26 | Way way = mock(Way.class);
27 | when(way.getId()).thenReturn(1l);
28 | List tags = new ArrayList();
29 | tags.add(new Tag("highway", "primary"));
30 | when(way.getTags()).thenReturn(tags);
31 | List wayNodes = new ArrayList();
32 | wayNodes.add(new WayNode(1l));
33 | wayNodes.add(new WayNode(2l));
34 | when(way.getWayNodes()).thenReturn(wayNodes);
35 |
36 | ESShapeBuilder builder = new ESShapeBuilder();
37 | builder.addLocation(1.0, 2.0).addLocation(2.0, 3.0);
38 |
39 | ESWay expected = ESWay.Builder.create().id(1l)
40 | .addLocation(1.0, 2.0).addLocation(2.0, 3.0)
41 | .addTag("highway", "primary").build();
42 |
43 | // Action
44 | ESWay actual = ESWay.Builder.buildFromEntity(way, builder.build());
45 |
46 | // Assert
47 | assertEquals(expected, actual);
48 | }
49 |
50 | @Test(expected = IllegalArgumentException.class)
51 | public void buildFromWayEntity_withIncorrectWayNodeSize() {
52 | // Setup
53 | Way way = mock(Way.class);
54 | when(way.getId()).thenReturn(1l);
55 | List tags = new ArrayList();
56 | tags.add(new Tag("highway", "primary"));
57 | when(way.getTags()).thenReturn(tags);
58 | List wayNodes = new ArrayList();
59 | wayNodes.add(new WayNode(1l));
60 | wayNodes.add(new WayNode(2l));
61 | when(way.getWayNodes()).thenReturn(wayNodes);
62 |
63 | ESShapeBuilder builder = new ESShapeBuilder();
64 | builder.addLocation(1.0, 2.0);
65 |
66 | // Action
67 | ESWay.Builder.buildFromEntity(way, builder.build());
68 | }
69 |
70 | @Test
71 | public void buildFromGetReponse() {
72 | // Setup
73 | GetResponse response = mock(GetResponse.class, Mockito.RETURNS_DEEP_STUBS);
74 | when(response.getType()).thenReturn(ESEntityType.WAY.getIndiceName());
75 | when(response.getId()).thenReturn("1");
76 | Map tags = new HashMap();
77 | tags.put("highway", "primary");
78 | when(response.getSource().get("tags")).thenReturn(tags);
79 | List
>> locations = new ArrayList>>();
80 | ArrayList> subLocations = new ArrayList>();
81 | subLocations.add(Arrays.asList(new Double[] { 2.0, 1.0 }));
82 | subLocations.add(Arrays.asList(new Double[] { 3.0, 2.0 }));
83 | locations.add(subLocations);
84 | @SuppressWarnings("unchecked")
85 | Map shape = mock(Map.class);
86 | when(shape.get("type")).thenReturn("polygon");
87 | when(shape.get("coordinates")).thenReturn(locations);
88 | when(response.getSource().get("shape")).thenReturn(shape);
89 | when(response.getSource().get("centroid")).thenReturn(Arrays.asList(new Double[] { 2.5, 1.5 }));
90 | when(response.getSource().get("lengthKm")).thenReturn(157.25358982950198d);
91 | when(response.getSource().get("areaKm2")).thenReturn(0d);
92 |
93 | ESWay expected = ESWay.Builder.create().id(1l)
94 | .addLocation(1.0, 2.0).addLocation(2.0, 3.0)
95 | .addTag("highway", "primary").build();
96 |
97 | // Action
98 | ESWay actual = ESWay.Builder.buildFromGetReponse(response);
99 |
100 | // Assert
101 | assertEquals(expected, actual);
102 | }
103 |
104 | @Test(expected = IllegalArgumentException.class)
105 | public void buildFromGetReponse_withInvalidGetResponse() {
106 | // Setup
107 | GetResponse response = mock(GetResponse.class, Mockito.RETURNS_DEEP_STUBS);
108 | when(response.getType()).thenReturn(ESEntityType.NODE.getIndiceName());
109 |
110 | // Action
111 | ESNode.Builder.buildFromGetReponse(response);
112 | }
113 |
114 | @Test
115 | public void getType() {
116 | // Setup
117 | ESWay way = ESWay.Builder.create().id(1l)
118 | .addLocation(1.0, 2.0).addLocation(2.0, 3.0)
119 | .addTag("highway", "primary").build();
120 |
121 | // Action
122 | ESEntityType actual = way.getEntityType();
123 |
124 | // Assert
125 | assertEquals(ESEntityType.WAY, actual);
126 | }
127 |
128 | @Test
129 | public void toJson_withLinestring() {
130 | // Setup
131 | ESWay way = ESWay.Builder.create().id(1l)
132 | .addLocation(1.0, 2.0).addLocation(2.0, 3.0)
133 | .addTag("highway", "primary").build();
134 | String expected = "{\"centroid\":[2.5,1.5],\"lengthKm\":157.25358982950198," +
135 | "\"areaKm2\":0.0,\"shape\":{\"type\":\"linestring\",\"coordinates\":" +
136 | "[[2.0,1.0],[3.0,2.0]]},\"tags\":{\"highway\":\"primary\"}}";
137 |
138 | // Action
139 | String actual = way.toJson();
140 |
141 | // Assert
142 | assertEquals(expected, actual);
143 | }
144 |
145 | @Test
146 | public void toJson_withPolygon() {
147 | // Setup
148 | ESWay way = ESWay.Builder.create().id(1l)
149 | .addLocation(1.0, 2.0).addLocation(2.0, 3.0)
150 | .addLocation(3.0, 2.0).addLocation(1.0, 2.0)
151 | .addTag("highway", "primary").build();
152 | String expected = "{\"centroid\":[2.3333333333333335,2.0],\"lengthKm\":536.8973391277414," +
153 | "\"areaKm2\":12364.345757132623,\"shape\":{\"type\":\"polygon\",\"coordinates\":" +
154 | "[[[2.0,1.0],[3.0,2.0],[2.0,3.0],[2.0,1.0]]]},\"tags\":{\"highway\":\"primary\"}}";
155 |
156 | // Action
157 | String actual = way.toJson();
158 |
159 | // Assert
160 | assertEquals(expected, actual);
161 | }
162 |
163 | }
164 |
--------------------------------------------------------------------------------
/src/test/java/org/openstreetmap/osmosis/plugin/elasticsearch/model/shape/ESShapeUTest.java:
--------------------------------------------------------------------------------
1 | package org.openstreetmap.osmosis.plugin.elasticsearch.model.shape;
2 |
3 | import junit.framework.Assert;
4 |
5 | import org.junit.Before;
6 | import org.junit.Test;
7 | import org.openstreetmap.osmosis.plugin.elasticsearch.model.shape.ESShape.ESShapeBuilder;
8 |
9 | public class ESShapeUTest {
10 |
11 | private ESShapeBuilder shapeBuilder;
12 |
13 | @Before
14 | public void setUp() throws Exception {
15 | shapeBuilder = new ESShapeBuilder();
16 | }
17 |
18 | @Test
19 | public void buildPoint() {
20 | // Setup
21 | shapeBuilder.addLocation(48.675881, 2.379247);
22 |
23 | // Action
24 | ESShape shape = shapeBuilder.build();
25 |
26 | // Assert
27 | Assert.assertEquals(ESShapeType.POINT, shape.getShapeType());
28 | Assert.assertTrue(shape.isClosed());
29 | Assert.assertEquals(0, shape.getAreaKm2(), 1E-6);
30 | Assert.assertEquals(0, shape.getLengthKm(), 1E-3);
31 | Assert.assertEquals(new ESLocation(48.675881, 2.379247), shape.getCentroid());
32 | }
33 |
34 | @Test
35 | public void buildLineString() {
36 | // Setup
37 | shapeBuilder.addLocation(48.675763, 2.379358).addLocation(48.675584, 2.379606).addLocation(48.675087, 2.380314)
38 | .addLocation(48.674958, 2.380947).addLocation(48.675093, 2.381405).addLocation(48.675406, 2.382000)
39 | .addLocation(48.675957, 2.383090).addLocation(48.676137, 2.383404).addLocation(48.676230, 2.384246)
40 | .addLocation(48.675890, 2.384684).addLocation(48.675580, 2.385125);
41 |
42 | // Action
43 | ESShape shape = shapeBuilder.build();
44 |
45 | // Assert
46 | Assert.assertEquals(ESShapeType.LINESTRING, shape.getShapeType());
47 | Assert.assertFalse(shape.isClosed());
48 | Assert.assertEquals(0, shape.getAreaKm2(), 1E-6);
49 | Assert.assertEquals(721E-3, shape.getLengthKm(), 1E-3);
50 | Assert.assertEquals(new ESLocation(48.67559909155728, 2.3822438099468224), shape.getCentroid());
51 | }
52 |
53 | @Test
54 | public void buildPolygon() {
55 | // Setup
56 | shapeBuilder.addLocation(48.6759473, 2.3792501).addLocation(48.6758837, 2.379149).addLocation(48.675816, 2.3792444)
57 | .addLocation(48.6758794, 2.3793465).addLocation(48.6759473, 2.3792501);
58 |
59 | // Action
60 | ESShape shape = shapeBuilder.build();
61 |
62 | // Assert
63 | Assert.assertEquals(ESShapeType.POLYGON, shape.getShapeType());
64 | Assert.assertTrue(shape.isClosed());
65 | Assert.assertEquals(160E-6, shape.getAreaKm2(), 1E-6);
66 | Assert.assertEquals(52E-3, shape.getLengthKm(), 1E-3);
67 | Assert.assertEquals(new ESLocation(48.67588161300993, 2.379247584621654), shape.getCentroid());
68 | }
69 |
70 | }
71 |
--------------------------------------------------------------------------------
/src/test/java/org/openstreetmap/osmosis/plugin/elasticsearch/service/IndexAdminServiceITest.java:
--------------------------------------------------------------------------------
1 | package org.openstreetmap.osmosis.plugin.elasticsearch.service;
2 |
3 | import java.io.IOException;
4 | import java.util.HashMap;
5 |
6 | import junit.framework.Assert;
7 |
8 | import org.elasticsearch.cluster.ClusterState;
9 | import org.elasticsearch.common.xcontent.XContentFactory;
10 | import org.junit.Assume;
11 | import org.junit.Before;
12 | import org.junit.Test;
13 | import org.openstreetmap.osmosis.plugin.elasticsearch.testutils.AbstractElasticSearchInMemoryTest;
14 |
15 | public class IndexAdminServiceITest extends AbstractElasticSearchInMemoryTest {
16 |
17 | private static final String INDEX_NAME = "osm-test";
18 |
19 | private IndexAdminService indexAdminService;
20 |
21 | @Before
22 | public void setUp() {
23 | indexAdminService = new IndexAdminService(client());
24 | }
25 |
26 | @Test
27 | public void createIndex() throws IOException {
28 | // Action
29 | indexAdminService.createIndex(INDEX_NAME, 1, 0, null);
30 |
31 | // Assert
32 | Assert.assertTrue(exists(INDEX_NAME));
33 | }
34 |
35 | @Test
36 | public void createIndex_withExistingIndex_shouldDelete() {
37 | // Setup
38 | client().admin().indices().prepareCreate(INDEX_NAME).execute().actionGet();
39 | refresh(INDEX_NAME);
40 | Assume.assumeTrue(exists(INDEX_NAME));
41 |
42 | // Action
43 | indexAdminService.createIndex(INDEX_NAME, 1, 0, null);
44 |
45 | // Assert
46 | Assert.assertTrue(exists(INDEX_NAME));
47 | }
48 |
49 | @Test
50 | public void createIndex_withSettingsAndMappings() throws IOException {
51 | // Setup
52 | String mapping = XContentFactory.jsonBuilder()
53 | .startObject().startObject("properties")
54 | .startObject("my_field").field("type", "string").endObject()
55 | .endObject().endObject().string();
56 | HashMap mappings = new HashMap();
57 | mappings.put("myindex", mapping);
58 |
59 | // Action
60 | indexAdminService.createIndex(INDEX_NAME, 1, 1, mappings);
61 |
62 | // Assert
63 | ClusterState state = client().admin().cluster().prepareState().execute().actionGet().getState();
64 | Assert.assertEquals(1, state.getMetaData().index(INDEX_NAME).getNumberOfShards());
65 | Assert.assertEquals(1, state.getMetaData().index(INDEX_NAME).getNumberOfReplicas());
66 | Assert.assertEquals("{\"myindex\":{\"properties\":{\"my_field\":{\"type\":\"string\"}}}}",
67 | state.getMetaData().index(INDEX_NAME).mapping("myindex").source().string());
68 | }
69 |
70 | }
71 |
--------------------------------------------------------------------------------
/src/test/java/org/openstreetmap/osmosis/plugin/elasticsearch/testutils/AbstractElasticSearchInMemoryTest.java:
--------------------------------------------------------------------------------
1 | package org.openstreetmap.osmosis.plugin.elasticsearch.testutils;
2 |
3 | import static junit.framework.Assert.fail;
4 | import static org.elasticsearch.common.settings.Settings.settingsBuilder;
5 |
6 | import java.io.File;
7 | import java.io.IOException;
8 | import java.util.regex.Matcher;
9 | import java.util.regex.Pattern;
10 |
11 | import org.apache.commons.io.FileUtils;
12 | import org.elasticsearch.action.admin.cluster.node.info.NodesInfoRequest;
13 | import org.elasticsearch.action.admin.cluster.node.info.NodesInfoResponse;
14 | import org.elasticsearch.client.Client;
15 | import org.elasticsearch.common.settings.Settings;
16 | import org.elasticsearch.node.Node;
17 | import org.elasticsearch.node.NodeBuilder;
18 | import org.junit.AfterClass;
19 | import org.junit.Before;
20 | import org.junit.BeforeClass;
21 | import org.openstreetmap.osmosis.plugin.elasticsearch.model.entity.ESEntity;
22 |
23 | /**
24 | * Provides an empty in-memory elasticsearch index
25 | *
26 | * @author Nicolas Colomer
27 | */
28 | public abstract class AbstractElasticSearchInMemoryTest {
29 |
30 | private static final String CLUSTER_NAME = "osm_test_cluster";
31 |
32 | private static File tmpFolder;
33 | private static Node node;
34 |
35 | @BeforeClass
36 | public static void setUpBeforeClass() throws IOException {
37 | tmpFolder = new File("tmp");
38 | String tmpFolderPath = tmpFolder.getCanonicalPath();
39 | FileUtils.deleteQuietly(tmpFolder);
40 | if (!tmpFolder.mkdir()) fail("Could not create a temporary folder [" + tmpFolderPath + "]");
41 | Settings settings = settingsBuilder()
42 | .put("cluster.name", CLUSTER_NAME)
43 | .put("index.number_of_shards", 1)
44 | .put("index.number_of_replicas", 0)
45 | .put("path.home", tmpFolderPath)
46 | .build();
47 | node = NodeBuilder.nodeBuilder()
48 | .settings(settings)
49 | .node();
50 | }
51 |
52 | @AfterClass
53 | public static void tearDownAfterClass() throws IOException {
54 | node.close();
55 | FileUtils.deleteQuietly(tmpFolder);
56 | }
57 |
58 | @Before
59 | public void setUpTest() {
60 | delete();
61 | }
62 |
63 | protected Client client() {
64 | return node.client();
65 | }
66 |
67 | protected void delete(String... indices) {
68 | if (indices == null || indices.length == 0) {
69 | client().admin().indices().prepareDelete("_all").execute().actionGet();
70 | } else {
71 | client().admin().indices().prepareDelete(indices).execute().actionGet();
72 | }
73 | }
74 |
75 | protected void refresh(String... indices) {
76 | client().admin().indices().prepareRefresh(indices).execute().actionGet();
77 | }
78 |
79 | protected boolean exists(String... indices) {
80 | return client().admin().indices().prepareExists(indices).execute().actionGet().isExists();
81 | }
82 |
83 | protected void index(String index, ESEntity... entities) {
84 | for (ESEntity entity : entities) {
85 | index(index, entity.getEntityType().getIndiceName(), entity.getIdString(), entity.toJson());
86 | }
87 | }
88 |
89 | protected void index(String index, String type, String id, String source) {
90 | client().prepareIndex(index, type, id).setSource(source).execute().actionGet();
91 | }
92 |
93 | protected String clusterName() {
94 | return CLUSTER_NAME;
95 | }
96 |
97 | protected String nodeAddress() {
98 | NodesInfoResponse nodesInfo = client().admin().cluster().nodesInfo(new NodesInfoRequest()).actionGet();
99 | String transportAddress = nodesInfo.getNodes()[0].getNode().address().toString();
100 | Matcher matcher = Pattern.compile("\\d{1,3}(?:\\.\\d{1,3}){3}(?::\\d{1,5})?").matcher(transportAddress);
101 | matcher.find();
102 | return matcher.group();
103 | }
104 |
105 | }
106 |
--------------------------------------------------------------------------------
/src/test/java/org/openstreetmap/osmosis/plugin/elasticsearch/testutils/AssertUtils.java:
--------------------------------------------------------------------------------
1 | package org.openstreetmap.osmosis.plugin.elasticsearch.testutils;
2 |
3 | import java.util.Collection;
4 | import java.util.Iterator;
5 |
6 | import junit.framework.Assert;
7 |
8 | import org.openstreetmap.osmosis.core.domain.v0_6.Node;
9 | import org.openstreetmap.osmosis.core.domain.v0_6.Tag;
10 | import org.openstreetmap.osmosis.core.domain.v0_6.Way;
11 | import org.openstreetmap.osmosis.core.domain.v0_6.WayNode;
12 |
13 | public class AssertUtils {
14 |
15 | public static void assertNodesEquals(Collection expected, Collection actual) {
16 | Assert.assertEquals(expected.size(), actual.size());
17 | Iterator expectedNodes = expected.iterator();
18 | Iterator actualNodes = actual.iterator();
19 | while (expectedNodes.hasNext() && actualNodes.hasNext()) {
20 | Node expectedNode = expectedNodes.next();
21 | Node actualNode = actualNodes.next();
22 | assertEquals(expectedNode, actualNode);
23 | }
24 | }
25 |
26 | public static void assertEquals(Node expected, Node actual) {
27 | Assert.assertEquals(expected.getId(), actual.getId());
28 | // Verify Location
29 | Assert.assertEquals(expected.getLatitude(), actual.getLatitude());
30 | Assert.assertEquals(expected.getLongitude(), actual.getLongitude());
31 | // Verify Tags
32 | Iterator expectedTags = expected.getTags().iterator();
33 | Iterator actualTags = actual.getTags().iterator();
34 | while (expectedTags.hasNext() && actualTags.hasNext()) {
35 | Tag expectedTag = expectedTags.next();
36 | Tag actualTag = actualTags.next();
37 | Assert.assertEquals(0, expectedTag.compareTo(actualTag));
38 | }
39 | Assert.assertFalse(expectedTags.hasNext() || actualTags.hasNext());
40 | }
41 |
42 | public static void assertWaysEquals(Collection expected, Collection actual) {
43 | Assert.assertEquals(expected.size(), actual.size());
44 | Iterator expectedWays = expected.iterator();
45 | Iterator actualWays = actual.iterator();
46 | while (expectedWays.hasNext() && actualWays.hasNext()) {
47 | Way expectedWay = expectedWays.next();
48 | Way actualWay = actualWays.next();
49 | assertEquals(expectedWay, actualWay);
50 | }
51 | }
52 |
53 | public static void assertEquals(Way expected, Way actual) {
54 | Assert.assertEquals(expected.getId(), actual.getId());
55 | // Verify Tags
56 | Iterator expectedTags = expected.getTags().iterator();
57 | Iterator actualTags = actual.getTags().iterator();
58 | while (expectedTags.hasNext() && actualTags.hasNext()) {
59 | Tag expectedTag = expectedTags.next();
60 | Tag actualTag = actualTags.next();
61 | Assert.assertEquals(0, expectedTag.compareTo(actualTag));
62 | }
63 | Assert.assertFalse(expectedTags.hasNext() || actualTags.hasNext());
64 | // Verify WayNodes
65 | Iterator expectedWayNodes = expected.getWayNodes().iterator();
66 | Iterator actualWayNodes = actual.getWayNodes().iterator();
67 | while (expectedWayNodes.hasNext() && actualWayNodes.hasNext()) {
68 | WayNode expectedWayNode = expectedWayNodes.next();
69 | WayNode actualWayNode = actualWayNodes.next();
70 | Assert.assertEquals(0, expectedWayNode.compareTo(actualWayNode));
71 | }
72 | Assert.assertFalse(expectedWayNodes.hasNext() || actualWayNodes.hasNext());
73 | }
74 |
75 | }
76 |
--------------------------------------------------------------------------------
/src/test/java/org/openstreetmap/osmosis/plugin/elasticsearch/testutils/OsmDataBuilder.java:
--------------------------------------------------------------------------------
1 | package org.openstreetmap.osmosis.plugin.elasticsearch.testutils;
2 |
3 | import java.util.ArrayList;
4 | import java.util.Arrays;
5 | import java.util.Date;
6 | import java.util.List;
7 |
8 | import org.openstreetmap.osmosis.core.domain.v0_6.CommonEntityData;
9 | import org.openstreetmap.osmosis.core.domain.v0_6.Node;
10 | import org.openstreetmap.osmosis.core.domain.v0_6.OsmUser;
11 | import org.openstreetmap.osmosis.core.domain.v0_6.Tag;
12 | import org.openstreetmap.osmosis.core.domain.v0_6.Way;
13 | import org.openstreetmap.osmosis.core.domain.v0_6.WayNode;
14 | import org.openstreetmap.osmosis.plugin.elasticsearch.model.entity.ESNode;
15 | import org.openstreetmap.osmosis.plugin.elasticsearch.model.entity.ESWay;
16 |
17 | public class OsmDataBuilder {
18 |
19 | public static Node buildSampleNode(long id) {
20 | List tags = Arrays.asList(new Tag[] { new Tag("highway", "traffic_signals") });
21 | CommonEntityData entityData = new CommonEntityData(id, 0, new Date(), new OsmUser(1, "nco"), 1l, tags);
22 | return new Node(entityData, 1.0d, 2.0d);
23 | }
24 |
25 | public static Node buildSampleNode() {
26 | return buildSampleNode(1);
27 | }
28 |
29 | public static Way buildSampleWay(long id, long... nodeIds) {
30 | List tags = Arrays.asList(new Tag[] { new Tag("highway", "residential") });
31 | CommonEntityData entityData = new CommonEntityData(id, 0, new Date(), new OsmUser(1, "nco"), 1l, tags);
32 | List wayNodes = new ArrayList();
33 | for (int i = 0; i < nodeIds.length; i++)
34 | wayNodes.add(new WayNode(nodeIds[i]));
35 | return new Way(entityData, wayNodes);
36 | }
37 |
38 | public static Way buildWay(long id) {
39 | return buildSampleWay(id, 1, 2);
40 | }
41 |
42 | public static Way buildSampleWay() {
43 | return buildSampleWay(1, 1, 2);
44 | }
45 |
46 | // ESEntity
47 |
48 | public static ESNode buildSampleESNode(long id) {
49 | return ESNode.Builder.create().id(id).location(1.0d, 2.0d).addTag("highway", "traffic_signals").build();
50 | }
51 |
52 | public static ESNode buildSampleESNode() {
53 | return buildSampleESNode(1);
54 | }
55 |
56 | public static ESWay buildSampleESWay(long id) {
57 | return ESWay.Builder.create().id(id).addLocation(1.0d, 2.0d).addTag("highway", "residential").build();
58 | }
59 |
60 | public static ESWay buildSampleESWay() {
61 | return buildSampleESWay(1);
62 | }
63 |
64 | }
65 |
--------------------------------------------------------------------------------
/src/test/java/org/openstreetmap/osmosis/plugin/elasticsearch/utils/ParametersUTest.java:
--------------------------------------------------------------------------------
1 | package org.openstreetmap.osmosis.plugin.elasticsearch.utils;
2 |
3 | import junit.framework.Assert;
4 |
5 | import org.junit.Test;
6 |
7 | public class ParametersUTest {
8 |
9 | @Test
10 | public void loadResource() {
11 | // Action
12 | Parameters p = new Parameters.Builder().loadResource("plugin.properties").build();
13 |
14 | // Assert
15 | Assert.assertTrue(p.containsKey(Parameters.CLUSTER_HOSTS));
16 | Assert.assertEquals("localhost", p.getProperty(Parameters.CLUSTER_HOSTS));
17 | Assert.assertEquals("localhost", p.getProperty(Parameters.CLUSTER_HOSTS, "default"));
18 | Assert.assertNull(p.getProperty("DUMMY_PROPERTY"));
19 | Assert.assertEquals("default", p.getProperty("DUMMY_PROPERTY", "default"));
20 | }
21 |
22 | @Test
23 | public void loadFile() {
24 | // Setup
25 | String file = getClass().getClassLoader().getResource("plugin.properties").getPath();
26 |
27 | // Action
28 | Parameters p = new Parameters.Builder().loadFile(file).build();
29 |
30 | // Assert
31 | Assert.assertTrue(p.containsKey(Parameters.CLUSTER_HOSTS));
32 | Assert.assertEquals("localhost", p.getProperty(Parameters.CLUSTER_HOSTS));
33 | Assert.assertEquals("localhost", p.getProperty(Parameters.CLUSTER_HOSTS, "default"));
34 | Assert.assertNull(p.getProperty("DUMMY_PROPERTY"));
35 | Assert.assertEquals("default", p.getProperty("DUMMY_PROPERTY", "default"));
36 | }
37 |
38 | @Test
39 | public void addParameter() {
40 | // Action
41 | Parameters p = new Parameters.Builder().loadResource("plugin.properties")
42 | .addParameter(Parameters.CLUSTER_HOSTS, "192.168.1.1").build();
43 |
44 | // Assert
45 | Assert.assertTrue(p.containsKey(Parameters.CLUSTER_HOSTS));
46 | Assert.assertEquals("192.168.1.1", p.getProperty(Parameters.CLUSTER_HOSTS));
47 | Assert.assertEquals("192.168.1.1", p.getProperty(Parameters.CLUSTER_HOSTS, "default"));
48 | Assert.assertNull(p.getProperty("DUMMY_PROPERTY"));
49 | Assert.assertEquals("default", p.getProperty("DUMMY_PROPERTY", "default"));
50 | }
51 |
52 | }
53 |
--------------------------------------------------------------------------------
/src/test/resources/logback-test.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 | %d{HH:mm:ss.SSS} [%thread] %-5level %logger{36} - %msg%n
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 |
--------------------------------------------------------------------------------
/src/test/resources/osmosis-plugins.conf:
--------------------------------------------------------------------------------
1 | org.openstreetmap.osmosis.plugin.elasticsearch.ElasticSearchWriterPluginLoader
--------------------------------------------------------------------------------
/src/test/resources/plugin.properties:
--------------------------------------------------------------------------------
1 | # Connection configuration
2 | cluster.hosts=localhost
3 | cluster.name=elasticsearch
4 |
5 | # Entity index configuration
6 | index.name=osm-test
7 | index.create=true
8 | index.settings.shards=1
9 | index.settings.replicas=0
10 | index.mapping.node={"_all":{"enabled":false},"dynamic_templates":[{"tags_exceptions":{"path_match":"tags.*","match":"(name.*)","match_pattern":"regex","mapping":{"store":"no","type":"multi_field","fields":{"{name}":{"type":"string","index":"not_analyzed"},"analyzed":{"type":"string","index":"analyzed"}}}}},{"tags_default":{"path_match":"tags.*","mapping":{"index":"not_analyzed","store":"no"}}}],"properties":{"centroid":{"type":"geo_point"},"shape":{"type":"geo_shape"}}}
11 | index.mapping.way={"_all":{"enabled":false},"dynamic_templates":[{"tags_exceptions":{"path_match":"tags.*","match":"(name.*)","match_pattern":"regex","mapping":{"store":"no","type":"multi_field","fields":{"{name}":{"type":"string","index":"not_analyzed"},"analyzed":{"type":"string","index":"analyzed"}}}}},{"tags_default":{"path_match":"tags.*","mapping":{"index":"not_analyzed","store":"no"}}}],"properties":{"centroid":{"type":"geo_point"},"shape":{"type":"geo_shape"}}}
12 | index.builders=
13 |
14 | config.queue.size=5
15 | config.node.bulk.size=100
16 | config.way.bulk.size=10
17 | config.worker.pool.size=2
18 |
19 | # Index builders configuration
20 | highway=org.openstreetmap.osmosis.plugin.elasticsearch.builder.highway.HighwayIndexBuilder
21 | highway.settings.shards=1
22 | highway.settings.replicas=0
23 | highway.mappings={"way":{"_all":{"enabled":false},"dynamic_templates":[{"tags_template_1":{"path_match":"tags.*","match":"name*","mapping":{"store":"no","type":"multi_field","fields":{"{name}":{"type":"string","index":"not_analyzed"},"analyzed":{"type":"string","index":"analyzed"}}}}},{"tags_template_2":{"path_match":"tags.*","mapping":{"index":"not_analyzed","store":"no"}}}],"properties":{"line":{"type":"geo_shape"}}}}
24 | highway.bulk.size=10
--------------------------------------------------------------------------------