From 87c35637d3704b3ab1f4b1808c4aa4f9d0638126 Mon Sep 17 00:00:00 2001 From: Fanis Tharropoulos Date: Fri, 1 Nov 2024 17:14:20 +0200 Subject: [PATCH] feat(presets): add search presets support Implements search presets management to allow storing and reusing common search configurations. Adds complete CRUD operations for search presets with proper error handling and test coverage. Changes include: - New Presets and Preset classes for managing search presets - Full test coverage with realistic search preset scenarios - Helper class updates for testing preset functionality - Documentation updates with usage examples for common scenarios feat(presets): add Presets class for bulk operations feat(presets): add Preset class for individual preset management test(presets): add PresetsTest test coverage refactor(helper): add presets support in test helper docs(presets): add documentation and examples --- README.md | 28 ++++++ src/main/java/org/typesense/api/Client.java | 20 +++++ src/main/java/org/typesense/api/Preset.java | 28 ++++++ src/main/java/org/typesense/api/Presets.java | 29 ++++++ src/test/java/org/typesense/api/Helper.java | 20 +++++ .../java/org/typesense/api/PresetsTest.java | 88 +++++++++++++++++++ 6 files changed, 213 insertions(+) create mode 100644 src/main/java/org/typesense/api/Preset.java create mode 100644 src/main/java/org/typesense/api/Presets.java create mode 100644 src/test/java/org/typesense/api/PresetsTest.java diff --git a/README.md b/README.md index 0fc93bb..ae24df8 100644 --- a/README.md +++ b/README.md @@ -234,6 +234,34 @@ StopwordsSetsRetrieveAllSchema sets = client.stopwords().retrieve(); client.stopwords("common-words").delete(); ``` +### Create or update a search preset +```java +SearchParameters params = new SearchParameters() + .q("bestseller") + .queryBy("title,author") + .sortBy("ratings_count:desc"); + +PresetUpsertSchema preset = new PresetUpsertSchema() + .value(params); + +client.presets().upsert("bestsellers_view", preset); +``` + +### Retrieve a search preset +```java +PresetSchema preset = client.presets("bestsellers_view").retrieve(); +``` + +### Retrieve all search presets +```java +PresetsRetrieveSchema presets = client.presets().retrieve(); +``` + +### Delete a search preset +```java +client.presets("bestsellers_view").delete(); +``` + ### Create an API key ```java ApiKeySchema apiKeySchema = new ApiKeySchema(); diff --git a/src/main/java/org/typesense/api/Client.java b/src/main/java/org/typesense/api/Client.java index 84e94f0..f638522 100644 --- a/src/main/java/org/typesense/api/Client.java +++ b/src/main/java/org/typesense/api/Client.java @@ -24,6 +24,9 @@ public class Client { private Stopwords stopwords; private Map individualStopwordsSets; + private Presets presets; + private Map individualPresets; + public Health health; public Operations operations; public Metrics metrics; @@ -47,6 +50,8 @@ public Client(Configuration configuration){ this.analytics = new Analytics(this.apiCall); this.stopwords = new Stopwords(this.apiCall); this.individualStopwordsSets = new HashMap<>(); + this.presets = new Presets(this.apiCall); + this.individualPresets = new HashMap<>(); } public Collection collections(String name){ @@ -114,4 +119,19 @@ public StopwordsSet stopwords(String stopwordsSetId) { retVal = this.individualStopwordsSets.get(stopwordsSetId); return retVal; } + + public Presets presets() { + return this.presets; + } + + public Preset presets(String presetId) { + Preset retVal; + + if (!this.individualPresets.containsKey(presetId)) { + this.individualPresets.put(presetId, new Preset(presetId, this.apiCall)); + } + + retVal = this.individualPresets.get(presetId); + return retVal; + } } diff --git a/src/main/java/org/typesense/api/Preset.java b/src/main/java/org/typesense/api/Preset.java new file mode 100644 index 0000000..29454c8 --- /dev/null +++ b/src/main/java/org/typesense/api/Preset.java @@ -0,0 +1,28 @@ +package org.typesense.api; + +import org.typesense.api.utils.URLEncoding; +import org.typesense.model.PresetDeleteSchema; +import org.typesense.model.PresetSchema; + +public class Preset { + private final ApiCall apiCall; + private final String name; + + public Preset(String name, ApiCall apiCall) { + this.name = name; + this.apiCall = apiCall; + } + + public PresetSchema retrieve() throws Exception { + return this.apiCall.get(this.getEndpoint(), null, PresetSchema.class); + } + + public PresetDeleteSchema delete() throws Exception { + return this.apiCall.delete(this.getEndpoint(), null, PresetDeleteSchema.class); + } + + private String getEndpoint() { + return Presets.RESOURCEPATH + "/" + URLEncoding.encodeURIComponent(this.name); + } + +} diff --git a/src/main/java/org/typesense/api/Presets.java b/src/main/java/org/typesense/api/Presets.java new file mode 100644 index 0000000..84edc06 --- /dev/null +++ b/src/main/java/org/typesense/api/Presets.java @@ -0,0 +1,29 @@ +package org.typesense.api; + +import org.typesense.api.utils.URLEncoding; +import org.typesense.model.PresetSchema; +import org.typesense.model.PresetUpsertSchema; +import org.typesense.model.PresetsRetrieveSchema; + +public class Presets { + public final static String RESOURCEPATH = "/presets"; + + private final ApiCall apiCall; + + public Presets(ApiCall apiCall) { + this.apiCall = apiCall; + } + + public PresetSchema upsert(String name, PresetUpsertSchema preset) throws Exception { + return this.apiCall.put(getEndpoint(name), preset, null, PresetSchema.class); + } + + public PresetsRetrieveSchema retrieve() throws Exception { + return this.apiCall.get(Presets.RESOURCEPATH, null, PresetsRetrieveSchema.class); + } + + private String getEndpoint(String name) { + return RESOURCEPATH + "/" + URLEncoding.encodeURIComponent(name); + } + +} diff --git a/src/test/java/org/typesense/api/Helper.java b/src/test/java/org/typesense/api/Helper.java index de910e3..dc2cff4 100644 --- a/src/test/java/org/typesense/api/Helper.java +++ b/src/test/java/org/typesense/api/Helper.java @@ -21,9 +21,13 @@ import org.typesense.model.CollectionResponse; import org.typesense.model.CollectionSchema; import org.typesense.model.Field; +import org.typesense.model.PresetSchema; +import org.typesense.model.PresetUpsertSchema; +import org.typesense.model.PresetsRetrieveSchema; import org.typesense.model.SearchOverrideInclude; import org.typesense.model.SearchOverrideRule; import org.typesense.model.SearchOverrideSchema; +import org.typesense.model.SearchParameters; import org.typesense.model.SearchSynonymSchema; import org.typesense.model.StopwordsSetSchema; import org.typesense.model.StopwordsSetUpsertSchema; @@ -140,6 +144,17 @@ public void createTestStopwordsSet() throws Exception { client.stopwords().upsert("common-words", stopwordsSetSchema); } + public void createTestPreset() throws Exception { + SearchParameters params = new SearchParameters() + .q("Romeo") + .queryBy("title"); + + PresetUpsertSchema preset = new PresetUpsertSchema() + .value(params); + + client.presets().upsert("listing_view", preset); + } + public void teardown() throws Exception { CollectionResponse[] collectionResponses = client.collections().retrieve(); for (CollectionResponse c : collectionResponses) { @@ -165,5 +180,10 @@ public void teardown() throws Exception { for (StopwordsSetSchema s : stopwords.getStopwords()) { client.stopwords(s.getId()).delete(); } + + PresetsRetrieveSchema presets = client.presets().retrieve(); + for (PresetSchema p : presets.getPresets()) { + client.presets(p.getName()).delete(); + } } } diff --git a/src/test/java/org/typesense/api/PresetsTest.java b/src/test/java/org/typesense/api/PresetsTest.java new file mode 100644 index 0000000..6aba96b --- /dev/null +++ b/src/test/java/org/typesense/api/PresetsTest.java @@ -0,0 +1,88 @@ +package org.typesense.api; + +import org.junit.jupiter.api.AfterEach; +import static org.junit.jupiter.api.Assertions.assertEquals; +import static org.junit.jupiter.api.Assertions.assertNotNull; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; +import org.typesense.model.OneOfPresetUpsertSchemaValue; +import org.typesense.model.PresetDeleteSchema; +import org.typesense.model.PresetSchema; +import org.typesense.model.PresetUpsertSchema; +import org.typesense.model.PresetsRetrieveSchema; +import org.typesense.model.SearchParameters; + +public class PresetsTest { + + private Client client; + private Helper helper; + + @BeforeEach + void setUp() throws Exception { + helper = new Helper(); + client = helper.getClient(); + helper.teardown(); + helper.createTestCollection(); + } + + @AfterEach + void tearDown() throws Exception { + helper.teardown(); + } + + @Test + void testUpsert() throws Exception { + SearchParameters params = new SearchParameters() + .q("Romeo") + .queryBy("title"); + + PresetUpsertSchema preset = new PresetUpsertSchema() + .value(params); + + PresetSchema result = client.presets().upsert("listing_view", preset); + + assertNotNull(result); + assertEquals("listing_view", result.getName()); + + OneOfPresetUpsertSchemaValue value = result.getValue(); + assertNotNull(value); + } + + @Test + void testRetrieve() throws Exception { + helper.createTestPreset(); + + PresetSchema result = this.client.presets("listing_view").retrieve(); + + assertNotNull(result); + assertEquals("listing_view", result.getName()); + assertNotNull(result.getValue()); + } + + @Test + void testRetrieveAll() throws Exception { + helper.createTestPreset(); + + PresetsRetrieveSchema result = this.client.presets().retrieve(); + + assertNotNull(result); + + assertEquals(1, result.getPresets().size()); + + PresetSchema preset = result.getPresets().get(0); + assertEquals("listing_view", preset.getName()); + assertNotNull(preset.getValue()); + } + + @Test + void testDelete() throws Exception { + helper.createTestPreset(); + + PresetDeleteSchema result = this.client.presets("listing_view").delete(); + + assertNotNull(result); + + assertEquals("listing_view", result.getName()); + + } +}