diff --git a/sdk/src/main/java/io/dapr/client/AbstractDaprClient.java b/sdk/src/main/java/io/dapr/client/AbstractDaprClient.java index 203f3f00a2..d13c463cb6 100644 --- a/sdk/src/main/java/io/dapr/client/AbstractDaprClient.java +++ b/sdk/src/main/java/io/dapr/client/AbstractDaprClient.java @@ -51,6 +51,7 @@ import java.util.ArrayList; import java.util.Arrays; import java.util.Collections; +import java.util.HashMap; import java.util.List; import java.util.Map; import java.util.stream.Collectors; @@ -509,6 +510,24 @@ public Mono saveState(String storeName, String key, String etag, Object va return this.saveBulkState(storeName, Collections.singletonList(state)); } + /** + * {@inheritDoc} + */ + @Override + public Mono saveState(String storeName, String key, String etag, Object value, Map meta, + StateOptions options) { + if (meta == null) { + meta = new HashMap<>(); + } + + if (value != null) { + meta.put("contentType", stateSerializer.getContentType()); + } + + State state = new State<>(key, value, etag, meta, options); + return this.saveBulkState(storeName, Collections.singletonList(state)); + } + /** * {@inheritDoc} */ diff --git a/sdk/src/main/java/io/dapr/client/DaprClient.java b/sdk/src/main/java/io/dapr/client/DaprClient.java index f51a6d0ffb..6ac6086e76 100644 --- a/sdk/src/main/java/io/dapr/client/DaprClient.java +++ b/sdk/src/main/java/io/dapr/client/DaprClient.java @@ -498,6 +498,21 @@ Mono executeStateTransaction(String storeName, */ Mono saveState(String storeName, String key, String etag, Object value, StateOptions options); + + /** + * Save/Update a state. + * + * @param storeName The name of the state store. + * @param key The key of the state. + * @param etag The etag to be used. + * @param value The value of the state. + * @param meta The metadata to be set to the state. + * @param options The Options to use for each state. + * @return a Mono plan of type Void. + */ + Mono saveState(String storeName, String key, String etag, Object value, Map meta, + StateOptions options); + /** * Delete a state. * diff --git a/sdk/src/test/java/io/dapr/client/DaprClientGrpcTest.java b/sdk/src/test/java/io/dapr/client/DaprClientGrpcTest.java index 54240d70ca..7ac6ab3cf5 100644 --- a/sdk/src/test/java/io/dapr/client/DaprClientGrpcTest.java +++ b/sdk/src/test/java/io/dapr/client/DaprClientGrpcTest.java @@ -1241,6 +1241,64 @@ public void saveStateNoOptionsTest() { result.block(); } + @Test + public void saveStateWithMetaTest() { + String key = "key1"; + String etag = "ETag1"; + String value = "State value"; + Map metadata = new HashMap<>(); + metadata.put("custom", "customValue"); + ArgumentCaptor argument = ArgumentCaptor.forClass(DaprProtos.SaveStateRequest.class); + doAnswer((Answer) invocation -> { + StreamObserver observer = (StreamObserver) invocation.getArguments()[1]; + observer.onNext(Empty.getDefaultInstance()); + observer.onCompleted(); + return null; + }).when(daprStub).saveState(argument.capture(), any()); + + + Mono result = client.saveState(STATE_STORE_NAME, key, etag, value, metadata,null); + result.block(); + assertEquals("customValue", argument.getValue().getStates(0).getMetadata().get("custom")); + } + + @Test + public void saveStateWithMetaContentTypeTest() { + String key = "key1"; + String etag = "ETag1"; + String value = "State value"; + Map metadata = new HashMap<>(); + ArgumentCaptor argument = ArgumentCaptor.forClass(DaprProtos.SaveStateRequest.class); + doAnswer((Answer) invocation -> { + StreamObserver observer = (StreamObserver) invocation.getArguments()[1]; + observer.onNext(Empty.getDefaultInstance()); + observer.onCompleted(); + return null; + }).when(daprStub).saveState(argument.capture(), any()); + + + Mono result = client.saveState(STATE_STORE_NAME, key, etag, value, metadata,null); + result.block(); + assertEquals("application/json", argument.getValue().getStates(0).getMetadata().get("contentType")); + } + + @Test + public void saveStateWithMetaEmptyTest() { + String key = "key1"; + String etag = "ETag1"; + ArgumentCaptor argument = ArgumentCaptor.forClass(DaprProtos.SaveStateRequest.class); + doAnswer((Answer) invocation -> { + StreamObserver observer = (StreamObserver) invocation.getArguments()[1]; + observer.onNext(Empty.getDefaultInstance()); + observer.onCompleted(); + return null; + }).when(daprStub).saveState(argument.capture(), any()); + + Mono result = client.saveState(STATE_STORE_NAME, key, etag, null, null,null); + result.block(); + assertTrue(argument.getValue().getStates(0).getMetadata().keySet().isEmpty()); + } + @Test public void saveStateTest() { String key = "key1";