依存関係
1 2 | implementation 'org.hibernate.search:hibernate-search-mapper-orm:6.1.4.Final' implementation 'org.hibernate.search:hibernate-search-backend-lucene:6.1.4.Final' |
実装
Entityクラスに@Indexed、メソッドに@FullTextFieldを追加する。
1 2 3 4 5 6 7 8 9 | @Entity @Table (name = "novel" ) @Indexed public class Novel implements Serializable { ... @FullTextField private String title; |
Serviceクラスに検索処理のロジックを追加する。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 | @Service public class NovelService { ... @Transactional public Stream<Novel> searchIndex( final String searchParameters) { SearchSession searchSession = Search.session(entityManager); SearchResult<Novel> result = searchSession.search(Novel. class ) .where(f -> f.bool() .must(f.match() .field( "title" ) .matching( "異世界" ))) .fetchAll(); return result.hits().stream(); } |
実際に動くコードはGitHubに公開予定。公開完了したら、下記に追記する。
※4/22追記
NovelService.java – github
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 | public Stream<Novel> searchIndex( final String searchParameters) { SearchSession searchSession = Search.session(entityManager); String operationSetExper = String.join( "|" , SearchOperation.SIMPLE_OPERATION_SET); Pattern pattern = Pattern.compile( "(\\p{Punct}?)(\\w+?)(" + operationSetExper + ")(\\p{Punct}?)(\\w+?)(\\p{Punct}?)," , Pattern.UNICODE_CHARACTER_CLASS); Matcher matcher = pattern.matcher(searchParameters + "," ); SearchResult<Novel> result = searchSession.search(Novel. class ) .where(f -> f.bool(b -> { b.must(f.matchAll()); while (matcher.find()) { b.must(f.match().field(matcher.group(KEY)) .matching(matcher.group(VALUE))); } })) .fetchAll(); return result.hits().stream(); } |