Search service configurable index settings
[aai/search-data-service.git] / src / test / java / org / onap / aai / sa / searchdbabstraction / elasticsearch / dao / ElasticSearchHttpControllerTest.java
1 /**
2  * ============LICENSE_START=======================================================
3  * org.onap.aai
4  * ================================================================================
5  * Copyright © 2017-2018 AT&T Intellectual Property. All rights reserved.
6  * Copyright © 2017-2018 Amdocs
7  * ================================================================================
8  * Licensed under the Apache License, Version 2.0 (the "License");
9  * you may not use this file except in compliance with the License.
10  * You may obtain a copy of the License at
11  *
12  *       http://www.apache.org/licenses/LICENSE-2.0
13  *
14  * Unless required by applicable law or agreed to in writing, software
15  * distributed under the License is distributed on an "AS IS" BASIS,
16  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
17  * See the License for the specific language governing permissions and
18  * limitations under the License.
19  * ============LICENSE_END=========================================================
20  */
21 package org.onap.aai.sa.searchdbabstraction.elasticsearch.dao;
22
23 import static org.hamcrest.CoreMatchers.anyOf;
24 import static org.hamcrest.CoreMatchers.containsString;
25 import static org.hamcrest.CoreMatchers.either;
26 import static org.hamcrest.CoreMatchers.equalTo;
27 import static org.hamcrest.CoreMatchers.is;
28 import static org.hamcrest.CoreMatchers.not;
29 import static org.junit.Assert.assertThat;
30
31 import java.util.Properties;
32 import org.eclipse.jetty.util.security.Password;
33 import org.json.JSONObject;
34 import org.junit.Before;
35 import org.junit.Ignore;
36 import org.junit.Test;
37 import org.onap.aai.sa.rest.AnalysisConfiguration;
38 import org.onap.aai.sa.rest.DocumentSchema;
39 import org.onap.aai.sa.rest.SettingConfiguration;
40 import org.onap.aai.sa.searchdbabstraction.elasticsearch.config.ElasticSearchConfig;
41 import org.onap.aai.sa.searchdbabstraction.entity.OperationResult;
42
43 @Ignore("All tests in this classes require an Elasticsearch instance to run locally")
44 public class ElasticSearchHttpControllerTest {
45
46     static {
47         // Set the location of the payload translation JSON file.
48         System.setProperty("CONFIG_HOME", "src/test/resources/json");
49     }
50
51     private static ElasticSearchHttpController elasticSearch;
52     private static AAIEntityTestObject testDocument;
53
54     private static final String TEST_INDEX_NAME = "test";
55
56     private static final String indexMappings =
57             "{\r\n    \"properties\": {\r\n        \"entityType\": {\r\n            \"type\": \"text\"\r\n        },\r\n"
58                     + "        \"edgeTagQueryEntityFieldName\": {\r\n            \"type\": \"text\",\r\n            \"index\": \"false\"\r\n        },\r\n"
59                     + "        \"edgeTagQueryEntityFieldValue\": {\r\n            \"type\": \"text\",\r\n            \"index\": \"false\"\r\n        },\r\n        \"searchTagIDs\" : {\r\n            \"type\" : \"text\"\r\n          },\r\n        \"searchTags\": {\r\n            \"type\": \"text\",\r\n            \"analyzer\": \"nGram_analyzer\",\r\n            \"search_analyzer\": \"whitespace_analyzer\"\r\n        }\r\n    }\r\n}";
60     private static final String indexSettings =
61             "{\r\n    \"analysis\": {\r\n        \"filter\": {\r\n            \"nGram_filter\": {\r\n                \"type\": \"nGram\",\r\n                \"min_gram\": 1,\r\n                \"max_gram\": 50,\r\n                \"token_chars\": [\r\n                    \"letter\",\r\n                    \"digit\",\r\n                    \"punctuation\",\r\n                    \"symbol\"\r\n                ]\r\n            }\r\n        },\r\n        \"analyzer\": {\r\n            \"nGram_analyzer\": {\r\n                \"type\": \"custom\",\r\n                \"tokenizer\": \"whitespace\",\r\n                \"filter\": [\r\n                    \"lowercase\",\r\n                    \"asciifolding\",\r\n                    \"nGram_filter\"\r\n                ]\r\n            },\r\n            \"whitespace_analyzer\": {\r\n                \"type\": \"custom\",\r\n                \"tokenizer\": \"whitespace\",\r\n                \"filter\": [\r\n                    \"lowercase\",\r\n                    \"asciifolding\"\r\n                ]\r\n            }\r\n        }\r\n    }\r\n}";
62
63     @Before
64     public void setUp() throws Exception {
65         Properties properties = new Properties();
66         properties.put(ElasticSearchConfig.ES_IP_ADDRESS, "127.0.0.1");
67         properties.put(ElasticSearchConfig.ES_HTTP_PORT, "9200");
68         properties.put(ElasticSearchConfig.ES_URI_SCHEME, "http");
69         properties.put(ElasticSearchConfig.ES_AUTH_USER, "your_user_here");
70         properties.put(ElasticSearchConfig.ES_AUTH_ENC, Password.obfuscate("your_password_here"));
71         elasticSearch = new ElasticSearchHttpController(new ElasticSearchConfig(properties));
72
73         testDocument = new AAIEntityTestObject();
74         testDocument.setId("test123");
75         testDocument.setEntityType("service-instance");
76         testDocument.setEdgeTagQueryEntityFieldName("service-instance.service-instance-id");
77         testDocument.setEdgeTagQueryEntityFieldValue("123456");
78         testDocument.setSearchTagIDs("0");
79         testDocument.setSearchTags("service-instance-id");
80     }
81
82     @Test
83     public void testGetInstance() throws Exception {
84         ElasticSearchHttpController.getInstance();
85     }
86
87     @Test
88     public void testCreateIndex() throws Exception {
89         testDeleteIndex();
90         OperationResult result = elasticSearch.createIndex(TEST_INDEX_NAME, new DocumentSchema());
91         assertThat(result.getResult(), containsString("/search/indexes/test"));
92         assertThat(result.getResultCode(), is(201));
93
94         result = elasticSearch.createIndex(TEST_INDEX_NAME, new DocumentSchema());
95         assertThat(result.getResult(), containsString("already exists"));
96         assertThat(result.getResultCode(), is(400));
97     }
98
99     @Test(expected = IllegalArgumentException.class)
100     public void testCreateDynamicIndexEmptySchema() throws Exception {
101         elasticSearch.createDynamicIndex(TEST_INDEX_NAME, "");
102     }
103
104     @Test
105     public void testCreateDynamicIndex() throws Exception {
106         String indexName = "test_dynamic";
107         elasticSearch.deleteIndex(indexName);
108
109         OperationResult result = elasticSearch.createDynamicIndex(indexName,
110                 "{\"mappings\":{\"_doc\":{\"dynamic_templates\":[{\"strings_as_text\":{\"match_mapping_type\":\"string\",\"mapping\":{\"type\":\"text\"}}}]}}}");
111         assertThat(result.getResult(), containsString("/search/indexes/test"));
112         assertThat(result.getResultCode(), is(201));
113
114         elasticSearch.deleteIndex(indexName);
115     }
116
117     @Test
118     public void testCreateTable() throws Exception {
119         AnalysisConfiguration ac = new AnalysisConfiguration();
120         ac.init("src/test/resources/json/filter-config.json", "src/test/resources/json/analysis-config.json");
121         SettingConfiguration sc = new SettingConfiguration();
122         sc.init("src/test/resources/json/settings-config.json");
123         
124         OperationResult result =
125                 elasticSearch.createTable(TEST_INDEX_NAME, "aai-entities", ac, indexMappings, sc);
126         assertThat(result.getResult(), containsString("\"index\":\"test\"}"));
127         assertThat(result.getResultCode(), either(is(200)).or(is(400)));
128     }
129
130     @Test
131     public void testCreateDocument() throws Exception {
132         OperationResult result = elasticSearch.createDocument(TEST_INDEX_NAME, testDocument, false);
133         assertThat(result.getResult(), not(equalTo("")));
134
135         DocumentStoreDataEntityImpl ds = new DocumentStoreDataEntityImpl();
136         ds.setId(testDocument.getId());
137
138         result = elasticSearch.getDocument(TEST_INDEX_NAME, ds);
139         assertThat(result.getResult(), not(equalTo("")));
140     }
141
142     @Test
143     public void testCreateDocumentInvalidIndex() throws Exception {
144         OperationResult result = elasticSearch.createDocument("index_does_not_exist", testDocument, false);
145         assertThat(result.getResultCode(), is(404));
146         assertThat(result.getResult(), not(equalTo("")));
147     }
148
149     @Test
150     public void testUpdateDocument() throws Exception {
151         testDocument.setEdgeTagQueryEntityFieldValue("567890");
152
153         OperationResult result = elasticSearch.getDocument(TEST_INDEX_NAME, testDocument);
154         if (result.getResultCode() == 404) {
155             testCreateDocument();
156         }
157         // assertThat(result.getResultCode(), anyOf(equalTo(200), equalTo(412)));
158         // assertThat(result.getResult(), containsString("\"found\":true"));
159
160         result = elasticSearch.updateDocument(TEST_INDEX_NAME, testDocument, false);
161         assertThat(result.getResultCode(), anyOf(equalTo(200), equalTo(412)));
162
163         result = elasticSearch.getDocument(TEST_INDEX_NAME, testDocument);
164         assertThat(result.getResult(), containsString("test123"));
165     }
166
167     @Test
168     public void testDeleteDocument() throws Exception {
169         OperationResult result = elasticSearch.getDocument(TEST_INDEX_NAME, testDocument);
170         if (result.getResultCode() == 404) {
171             testCreateDocument();
172         }
173
174         result = elasticSearch.deleteDocument(TEST_INDEX_NAME, testDocument);
175         assertThat(result.getResult(), containsString(TEST_INDEX_NAME));
176
177         result = elasticSearch.getDocument(TEST_INDEX_NAME, testDocument);
178         assertThat(result.getResult(), containsString("test123"));
179     }
180
181     @Test
182     public void testBulkCreateDocuments() throws Exception {
183         for (int i = 0; i < 10; i++) {
184             AAIEntityTestObject doc = new AAIEntityTestObject();
185             doc.setId("test-" + i);
186             doc.setEntityType("service-instance");
187             doc.setEdgeTagQueryEntityFieldName("service-instance.service-instance-id");
188             doc.setEdgeTagQueryEntityFieldValue("123456" + i);
189             doc.setSearchTagIDs("" + i);
190             doc.setSearchTags("service-instance-id");
191
192             OperationResult result = elasticSearch.createDocument(TEST_INDEX_NAME, doc, false);
193             assertThat(result.getResultCode(), anyOf(equalTo(201), equalTo(400)));
194         }
195     }
196
197     @Test
198     public void serchByEntityType() throws Exception {
199         OperationResult result = elasticSearch.search(TEST_INDEX_NAME, "q=instance");
200         assertThat(result.getResult(), not(equalTo("")));
201     }
202
203     @Test
204     public void serchByTagIDs() throws Exception {
205         OperationResult result = elasticSearch.search(TEST_INDEX_NAME, "q=9");
206         assertThat(result.getResult(), not(equalTo("")));
207     }
208
209     @Test
210     public void serchByTags() throws Exception {
211         OperationResult result = elasticSearch.search(TEST_INDEX_NAME, "q=service");
212         assertThat(result.getResult(), not(equalTo("")));
213     }
214
215     @Test
216     public void searchWithPayload() throws Exception {
217         testCreateIndex();
218         OperationResult result =
219                 elasticSearch.searchWithPayload(TEST_INDEX_NAME, "{\"query\":{\"term\":{\"user\":\"fred\"}}}");
220         assertThat(result.getResult(), containsString("successful"));
221         assertThat(result.getResultCode(), is(equalTo(200)));
222     }
223
224     /**
225      * The _suggest endpoint appears to be deprecated in ES 5.x and above.
226      */
227     @Test
228     public void suggestionQueryWithPayload() throws Exception {
229         testCreateIndex();
230         OperationResult result = elasticSearch.suggestionQueryWithPayload(TEST_INDEX_NAME,
231                 "{\"my-suggestion\":{\"text\":\"fred\",\"term\":{\"field\":\"body\"}}}");
232         assertThat(result.getResult(), containsString("error"));
233         assertThat(result.getResultCode(), is(equalTo(400)));
234     }
235
236     @Test
237     public void testCreateDocumentWithoutId() throws Exception {
238         AAIEntityTestObject doc = new AAIEntityTestObject();
239         doc.setEntityType("service-instance");
240         doc.setEdgeTagQueryEntityFieldName("service-instance.service-instance-id");
241         doc.setEdgeTagQueryEntityFieldValue("1111111");
242         doc.setSearchTagIDs("321");
243         doc.setSearchTags("service-instance-id");
244
245         OperationResult result = elasticSearch.createDocument(TEST_INDEX_NAME, doc, false);
246         assertThat(result.getResult(), not(equalTo("")));
247     }
248
249     @Test
250     public void testDeleteIndex() throws Exception {
251         OperationResult result = elasticSearch.deleteIndex(TEST_INDEX_NAME);
252         assertThat(result.getResultCode(), anyOf(equalTo(200), equalTo(404)));
253         assertThat(result.getResult(), not(equalTo("")));
254     }
255
256     class AAIEntityTestObject implements DocumentStoreDataEntity {
257         private String id;
258         private String entityType;
259         private String edgeTagQueryEntityFieldName;
260         private String edgeTagQueryEntityFieldValue;
261         private String searchTagIDs;
262         private String searchTags;
263
264         public void setId(String id) {
265             this.id = id;
266         }
267
268         @Override
269         public String getId() {
270             return this.id;
271         }
272
273         public String getEntityType() {
274             return entityType;
275         }
276
277         public void setEntityType(String entityType) {
278             this.entityType = entityType;
279         }
280
281         public String getEdgeTagQueryEntityFieldName() {
282             return edgeTagQueryEntityFieldName;
283         }
284
285         public void setEdgeTagQueryEntityFieldName(String edgeTagQueryEntityFieldName) {
286             this.edgeTagQueryEntityFieldName = edgeTagQueryEntityFieldName;
287         }
288
289         public String getEdgeTagQueryEntityFieldValue() {
290             return edgeTagQueryEntityFieldValue;
291         }
292
293         public void setEdgeTagQueryEntityFieldValue(String edgeTagQueryEntityFieldValue) {
294             this.edgeTagQueryEntityFieldValue = edgeTagQueryEntityFieldValue;
295         }
296
297         public String getSearchTagIDs() {
298             return searchTagIDs;
299         }
300
301         public void setSearchTagIDs(String searchTagIDs) {
302             this.searchTagIDs = searchTagIDs;
303         }
304
305         public String getSearchTags() {
306             return searchTags;
307         }
308
309         public void setSearchTags(String searchTags) {
310             this.searchTags = searchTags;
311         }
312
313         @Override
314         public String getVersion() {
315             return "1";
316         }
317
318         @Override
319         public String getContentInJson() {
320             return new JSONObject(). //
321                     put("entityType", entityType) //
322                     .put("edgeTagQueryEntityFieldName", edgeTagQueryEntityFieldName)
323                     .put("edgeTagQueryEntityFieldValue", edgeTagQueryEntityFieldValue) //
324                     .put("searchTagIDs", searchTagIDs) //
325                     .put("searchTags", searchTags) //
326                     .toString();
327         }
328     }
329
330 }