使用Spring Boot和Elasticsearch教程
Elasticsearch 是一種實時分散式和開源的全文搜尋和分析引擎。它是基於文件的搜尋平臺,具有快速搜尋功能。它針對大海撈針式的搜尋進行了最佳化,重點不在於一致性或原子性。
在本部落格中,我將介紹如何下載Elasticsearch並進行設定。此外,如何使用 Spring Boot 和 Spring Data ElasticSearch 專案與Elasticsearch 引擎整合 。
首先,安裝和設定elasticsearch引擎。
現在,我們將開發一個Spring Boot應用程式,它將展示 ElasticsearchTemplate 和 ElasticsearchRepository 訪問Elasticsearch引擎的方式並進行CRUD操作。在開發應用程式之前,讓我們首先了解 ElasticsearchTemplate 和 ElasticsearchRepository的 工作原理。
ElasticsearchTemplate - 它是一個實現ElasticsearchOperations的Template類 。 它比ElasticsearchRepository更強大,因為它可以做的不僅僅是CRUD操作。它具有建立,刪除索引,批次上傳的操作。它也可以進行聚合搜尋。
ElasticsearchRepository - 如果我們定義一個擴充套件ElasticsearchRepository的介面 , 它由Spring資料Elasticsearch提供,它將自動為該Document提供CRUD操作。例如,透過擴充套件ElasticsearchRepository,UserRepository介面在下面定義了“ User ”文件。現在可以在使用者文件上完成所有查詢,儲存,刪除,更新預設操作。
@Repository public interface UserRepository extends ElasticsearchRepository<User, String> { } |
它擴充套件了ElasticsearchCrudRepository,最終擴充套件了Repository介面。此儲存庫介面是Spring資料的標準功能。無需提供此介面的實現。您也可以使用@Query 註釋編寫自定義查詢。
Maven配置:
<dependencies> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-data-elasticsearch</artifactId> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-web</artifactId> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-test</artifactId> <scope>test</scope> </dependency> </dependencies> |
配置application.properties ,ElasticsearchTemplate 和 ElasticsearchRepository用這個配置來連線引擎。我使用了諸如叢集節點之類的傳輸客戶端屬性和索引名稱來連線elasticsearch引擎。
application.properties # Local Elasticsearch config spring.data.elasticsearch.repositories.enabled=true spring.data.elasticsearch.cluster-nodes=localhost:9300 spring.data.elasticsearch.cluster-name=elasticsearch elasticsearch.index.name=my_index elasticsearch.user.type=user # App config server.port=8102 spring.application.name=BootElastic |
Mappings
在Elasticsearch中, Index 就像RDBMS中的DB, Mappings / Type 類似於RDBMS中的表。 Document 是屬於某種型別並位於索引中的欄位的集合。Spring資料提供了像@ Document 這樣的註釋來建立文件。在這裡,我們將User定義為索引為“ my_index ”並鍵入“ user ” 的文件。
@Document(indexName = "my_index", type = "user") public class User { @Id private String userId; private String name; private Date creationDate = new Date(); private Map<String, String> userSettings = new HashMap<>(); //getter and setters } |
控制器
第一個控制器是 UserController。它將使用 UserDAOImpl 讓 ElasticserachTemplate 與Elasticsearch Engine 互動 。
@RestController public class UserController { @Autowired private UserDAO userDAO; @RequestMapping("/all") public List<User> getAllUsers() { return userDAO.getAllUsers(); } @RequestMapping(value = "/new", method = RequestMethod.POST) public User addUsers(@RequestBody User user) { userDAO.addNewUser(user); return user; } --- Other methods } |
UserDAOImpl - 此類初始化elasticsearchtemplate並使用queryForList方法檢索資料。
@Repository public class UserDAOImpl implements UserDAO { private final Logger LOG = LoggerFactory.getLogger(getClass()); @Value("${elasticsearch.index.name}") private String indexName; @Value("${elasticsearch.user.type}") private String userTypeName; @Autowired private ElasticsearchTemplate esTemplate; @Override public List<User> getAllUsers() { SearchQuery getAllQuery = new NativeSearchQueryBuilder() .withQuery(matchAllQuery()).build(); return esTemplate.queryForList(getAllQuery, User.class); } // Other methods } |
另一個Controller是UserRepositoryConroller。這是使用UserRepository與elasticsearch引擎進行互動。
@RestController @RequestMapping("/repo") public class UserRepositoryController { @Autowired private UserRepository userRepository; @RequestMapping("/all") public List<User> getAllUsers() { List<User> users = new ArrayList<>(); userRepository.findAll().forEach(users::add); return users; } //Other methods } |
此Repository類擴充套件了ElasticsearchRepository類,該類在內部擴充套件了 ElasticsearchCrudRepository - > PagingAndSortingRepository
@Repository public interface UserRepository extends ElasticsearchRepository<User, String> { } |
你可以在github連結找到完整的程式碼 - https://github.com/RajeshBhojwani/spring-boot-elasticsearch.git
構建應用程式
可以使用Maven命令構建應用程式。
mvn clean install
將構建程式碼並建立 elasticsearch-0.0.1-SNAPSHOT.jar 檔案。
執行該應用程式
java -jar target/elasticsearch-0.0.1-SNAPSHOT.jar
將啟動該應用程式。應用程式將偵聽application.properties 檔案中定義的 埠 8102 。
測試應用程式 -
測試 使用ElasticsearchTemplate的UserController 流程。
第1步 - 新增新使用者。使用此REST API URL新增新使用者 http://localhost:8102/new
在Request正文中新增Json資料。
{ "name": "Sumit", "userSettings": { "gender" : "male", "occupation" : "CA", "hobby" : "chess" } } |
第2步 - 檢查響應。您將看到使用userId生成的新使用者,該文件是此文件的唯一ID。輸出如下:
{ "userId": "AWdj-3KcTJbZRlQtLZfO", "name": "Sumit", "creationDate": 1543570682521, "userSettings": { "gender": "male", "occupation": "CA", "hobby": "chess" } } |
第3步 - 檢索所有使用者。使用 http://localhost:8102/all
{ "userId": "AWdj-3KcTJbZRlQtLZfO", "name": "Sumit", "creationDate": 1543570682521, "userSettings": { "gender": "male", "occupation": "CA", "hobby": "chess" } }, { "userId": "AWdZuKFRgzULDLBu_Y0c", "name": "Suresh", "creationDate": 1543398531296, "userSettings": {} } |
測試 使用ElasticsearchRepository的UserRepositoryController 流。
第1步 - 新增新使用者。使用此REST API URL新增新使用者 http://localhost:8102/repo/new
像我們在之前的測試用例中那樣在Request體中新增Json資料。
第2步 - 檢查響應。您將看到使用userId生成的新使用者,該文件是此文件的唯一ID。
Transport 客戶端庫
如何使用傳輸客戶端庫與最新版本的Elasticsearch引擎進行互動?我們可以直接從程式碼中呼叫Elasticsearch的REST API進行CRUD,也可以使用Elasticsearch提供的傳輸Transport客戶端。
Maven依賴:需要Elasticsearch,一個傳輸客戶端和log4j jar。
<dependencies> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-web</artifactId> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-test</artifactId> <scope>test</scope> </dependency> <dependency> <groupId>org.elasticsearch</groupId> <artifactId>elasticsearch</artifactId> </dependency> <dependency> <groupId>org.elasticsearch.client</groupId> <artifactId>transport</artifactId> <version>5.0.0</version> </dependency> <dependency> <groupId>org.apache.logging.log4j</groupId> <artifactId>log4j-api</artifactId> <version>2.7</version> </dependency> <dependency> <groupId>org.apache.logging.log4j</groupId> <artifactId>log4j-core</artifactId> <version>2.7</version> </dependency> <dependency> <groupId>org.apache.logging.log4j</groupId> <artifactId>log4j-web</artifactId> <version>2.7</version> </dependency> </dependencies> |
配置:
由於我們將使用傳輸客戶端連線到Elasticsearch引擎,因此我們需要為引擎的群集節點提供URL路徑。所以我已將屬性放在application.properties檔案中,用於URL 的主機和埠。
# Local Elasticsearch config elasticsearch.host=localhost elasticsearch.port=9300 # App config server.port=8102 spring.application.name=BootElastic |
建立一個名為的域類User。JSON輸入將對映到此 User 物件。這將用於建立與索引和型別關聯的使用者文件。
public class User { private String userId; private String name; private Date creationDate = new Date(); private Map<String, String> userSettings = new HashMap<>(); -- getter/setter methods } |
建立Java配置檔案以建立連線到Elasticsearch叢集節點的傳輸客戶端。它還從application.properties檔案配置的環境載入主機和埠的值 。
@Configuration public class config{ @Value("${elasticsearch.host:localhost}") public String host; @Value("${elasticsearch.port:9300}") public int port; public String getHost() { return host; } public int getPort() { return port; } @Bean public Client client(){ TransportClient client = null; try{ System.out.println("host:"+ host+"port:"+port); client = new PreBuiltTransportClient(Settings.EMPTY) .addTransportAddress(new InetSocketTransportAddress(InetAddress.getByName(host), port)); } catch (UnknownHostException e) { e.printStackTrace(); } return client; } } |
UserController 建立以展示以下功能:
- 建立一個名為“ users ” 的索引並鍵入“ employee ”。它將建立一個用於儲存使用者資訊的文件。文件的id可以作為JSON輸入傳遞,如果沒有傳遞,Elasticsearch將生成自己的id。客戶端有一個稱為方法 prepareIndex() 構建文件物件和儲存針對索引和型別。這方法是一種 POST 方法呼叫,其中 User 資訊將作為JSON傳遞。
@Autowired Client client; @PostMapping("/create") public String create(@RequestBody User user) throws IOException { IndexResponse response = client.prepareIndex("users", "employee", user.getUserId()) .setSource(jsonBuilder() .startObject() .field("name", user.getName()) .field("userSettings", user.getUserSettings()) .endObject() ) .get(); System.out.println("response id:"+response.getId()); return response.getResult().toString(); } |
2.根據傳遞的“id”檢視使用者資訊。客戶端有一種 prepareGet() 方法可以根據索引,型別和id檢索資訊。它將以JSON格式返回使用者資訊。
@GetMapping("/view/{id}") public Map<String, Object> view(@PathVariable final String id) { GetResponse getResponse = client.prepareGet("users", "employee", id).get(); return getResponse.getSource(); } |
3.根據欄位名稱檢視使用者資訊。我用 matchQuery() 這裡搜尋“ 名稱 ”欄位並返回 User 資訊。但是,班級有許多不同型別的可用 。例如,用於 搜尋特定範圍內的欄位值,例如10到20年之間的年齡。有一種 方法可以使用萬用字元搜尋欄位:
@GetMapping("/view/name/{field}") public Map<String, Object> searchByName(@PathVariable final String field) { Map<String,Object> map = null; SearchResponse response = client.prepareSearch("users") .setTypes("employee") .setSearchType(SearchType.QUERY_AND_FETCH) .setQuery(QueryBuilders..matchQuery("name", field)) .get() ; List<SearchHit> searchHits = Arrays.asList(response.getHits().getHits()); map = searchHits.get(0).getSource(); return map; } |
4.透過使用Id搜尋文件來更新文件並替換欄位值。客戶端有一個名為的方法 update()。它接受 UpdateRequest 更新查詢的輸入。
@GetMapping("/update/{id}") public String update(@PathVariable final String id) throws IOException { UpdateRequest updateRequest = new UpdateRequest(); updateRequest.index("users") .type("employee") .id(id) .doc(jsonBuilder() .startObject() .field("name", "Rajesh") .endObject()); try { UpdateResponse updateResponse = client.update(updateRequest).get(); System.out.println(updateResponse.status()); return updateResponse.status().toString(); } catch (InterruptedException | ExecutionException e) { System.out.println(e); } return "Exception"; } |
5.最後一種方法是展示如何刪除索引和型別的文件。客戶端確實有一個 prepareDelete() 接受索引,型別和id的方法來刪除文件。
@GetMapping("/delete/{id}") public String delete(@PathVariable final String id) { DeleteResponse deleteResponse = client.prepareDelete("users", "employee", id).get(); return deleteResponse.getResult().toString(); } |
程式碼見:GitHub.
測試應用
該應用程式將在http://localhost:8102URL 上執行 。現在讓我們測試一下我們上面討論過的幾個用例。
1.測試建立文件。
透過curl 或Postman 啟動 。http://localhost:8102/rest/users/createPOST
輸入:
{ "userId":"1", "name": "Sumit", "userSettings": { "gender" : "male", "occupation" : "CA", "hobby" : "chess" } } |
您將看到顯示“已建立”的響應。
2.要測試文件是否已建立,讓我們測試檢視功能。
啟動。http://localhost:8102/rest/users/view/1GET
作為響應,您將看到id的使用者資訊,其值為“1”。
{ "userSettings": { "occupation": "CA", "gender": "male", "hobby": "chess" }, "name": "Rajesh" } |
3.您可以透過名稱欄位檢視使用者資訊以及啟動 http://localhost:8102/rest/users/view/name/Rajesh。這是將“Rajesh”作為“名稱”欄位值傳遞。
同樣,可以透過啟動 和 來測試更新和刪除功能 。http://localhost:8102/rest/users/update/1http://localhost:8102/rest/users/delete/1
相關文章
- Spring Boot 教程 - ElasticsearchSpring BootElasticsearch
- Spring Boot 中使用 Java API 呼叫 ElasticsearchSpring BootJavaAPIElasticsearch
- Spring Boot 整合 elasticsearchSpring BootElasticsearch
- 在 Spring Boot 中使用搜尋引擎 ElasticsearchSpring BootElasticsearch
- ElasticSearch與Spring Boot整合ElasticsearchSpring Boot
- Spring Boot 整合 Elasticsearch 實戰Spring BootElasticsearch
- Spring Boot安全保護使用教程Spring Boot
- Spring Boot整合swagger使用教程Spring BootSwagger
- Spring Boot中使用Prometheus監控教程Spring BootPrometheus
- Spring Boot Test 的詳細使用教程Spring Boot
- 使用Spring Boot排程WebSocket推送的教程和原始碼 - BaeldungSpring BootWeb原始碼
- 使用JBang構建Spring Boot Rest API教程Spring BootRESTAPI
- Spring Boot2 系列教程(三)理解 Spring BootSpring Boot
- Nasruddin/elasticsearch-spring-boot-spring-data:使用Spring Data將Elasticsearch儲存庫與Springboot結合使用的入門示例ElasticsearchSpring Boot
- Spring Boot Security配置教程Spring Boot
- Spring Boot-Redis教程Spring BootRedis
- 《Elasticsearch技術解析與實戰》Chapter 1.4 Spring Boot整合ElasticsearchElasticsearchAPTSpring Boot
- Spring Boot基礎教程:EhCache快取的使用Spring Boot快取
- Spring Boot 2.x基礎教程:使用MongoDBSpring BootMongoDB
- elasticsearch教程--中文分詞器作用和使用Elasticsearch中文分詞
- Spring Boot(十八):使用 Spring Boot 整合 FastDFSSpring BootAST
- Spring Boot(五):Spring Boot Jpa 的使用Spring Boot
- 開始使用GraphQL Java和Spring BootJavaSpring Boot
- 在 Spring Boot 中使用 JPA 和 MySQLSpring BootMySql
- ElasticSearch Sharing | ES入門分享(spring-boot-starter-ElasticSearch+ElasticStack/ELK)ElasticsearchSpringboot
- 使用Spring Boot配置JNDI資料來源 -Roy教程Spring Boot
- Spring Boot 2.x基礎教程:使用JdbcTemplate訪Spring BootJDBC
- Spring Boot 教程 - MyBatis-PlusSpring BootMyBatis
- Spring Boot 2.0.1 入門教程Spring Boot
- 使用Elasticsearch實現Spring Boot的自動完成功能 -Milos BiljanovicElasticsearchSpring Boot
- Spring Boot 2.0(四):使用 Docker 部署 Spring BootSpring BootDocker
- Spring Boot(十一):Spring Boot 中 MongoDB 的使用Spring BootMongoDB
- Spring Boot(十六):使用 Jenkins 部署 Spring BootSpring BootJenkins
- Spring Boot(三):Spring Boot 中 Redis 的使用Spring BootRedis
- 使用Spring Boot和Kafka Streams實現CQRSSpring BootKafka
- Spring Boot使用Druid和監控配置Spring BootUI
- Spring Boot 使用1Spring Boot
- Spring Boot(十七):使用 Spring Boot 上傳檔案Spring Boot