Skip to content

Commit a6f028e

Browse files
siri-varmasalaboymcruzdevartur-ciocanuRaymundoZa
committed
Add Cryptography APIs to the Java SDK (dapr#1599)
* Bringing Durable Task Java as a Maven module inside the Java SDK (dapr#1575) * fixing checkstyle and javadocs Signed-off-by: salaboy <Salaboy@gmail.com> * Replace openjdk:17-jdk-slim to eclipse-temurin:17-jdk-jammy (dapr#1574) Signed-off-by: Matheus Cruz <matheuscruz.dev@gmail.com> Signed-off-by: salaboy <Salaboy@gmail.com> * Align Java API with other languages (dapr#1560) * Align Java API with other languages Signed-off-by: Matheus Cruz <matheuscruz.dev@gmail.com> * Update documentation Signed-off-by: Matheus Cruz <matheuscruz.dev@gmail.com> * Change return type of waitForWorkflowStart method Signed-off-by: artur-ciocanu <artur.ciocanu@gmail.com> --------- Signed-off-by: Matheus Cruz <matheuscruz.dev@gmail.com> Signed-off-by: artur-ciocanu <artur.ciocanu@gmail.com> Co-authored-by: artur-ciocanu <artur.ciocanu@gmail.com> Signed-off-by: salaboy <Salaboy@gmail.com> * use built in durable task Signed-off-by: salaboy <Salaboy@gmail.com> * exclude jacoco rules for examples and durabletask-client Signed-off-by: salaboy <Salaboy@gmail.com> * increasing timeout for IT Signed-off-by: salaboy <Salaboy@gmail.com> * removing dt build from matrix Signed-off-by: salaboy <Salaboy@gmail.com> * adding java to dt build Signed-off-by: salaboy <Salaboy@gmail.com> * Fix dependencies multi app build and add proper test deps (dapr#1572) * Force Jackson version to override the SB Jackson version Signed-off-by: Artur Ciocanu <artur.ciocanu@gmail.com> * Move all the Jackson deps to parent POM. Signed-off-by: Artur Ciocanu <artur.ciocanu@gmail.com> * Ensure app JAR build order Signed-off-by: Artur Ciocanu <artur.ciocanu@gmail.com> * Remove explicit Jackson from sdk-tests module. Signed-off-by: Artur Ciocanu <artur.ciocanu@gmail.com> * Make sure <scope>test</scope> is used for test dependencies. Signed-off-by: Artur Ciocanu <artur.ciocanu@gmail.com> * Remove extra Jackson modules. Signed-off-by: Artur Ciocanu <artur.ciocanu@gmail.com> --------- Signed-off-by: Artur Ciocanu <artur.ciocanu@gmail.com> Signed-off-by: salaboy <Salaboy@gmail.com> * docs: add architecture diagram to README (dapr#1549) * Preview New README * Preview New README 2 * Preview New README 3 * docs: add architecture diagram showing Java SDK interaction with Dapr runtime (close #<915>) * docs: add architecture diagram showing Java SDK interaction with Dapr runtime CORRECTION (close #<915>) * docs: add architecture diagram showing Java SDK interaction with Dapr runtime (close #<915>) * docs: add architecture diagram showing Java SDK interaction with Dapr runtime (close #<915>) --------- Co-authored-by: Siri Varma Vegiraju <siri.varma@outlook.com> Co-authored-by: artur-ciocanu <artur.ciocanu@gmail.com> Co-authored-by: Cassie Coyle <cassie.i.coyle@gmail.com> Signed-off-by: salaboy <Salaboy@gmail.com> * Add statestore example with Outbox pattern (dapr#1582) * Add statestore example with Outbox pattern Signed-off-by: Matheus Cruz <matheuscruz.dev@gmail.com> * Clean events after each test Signed-off-by: Matheus Cruz <matheuscruz.dev@gmail.com> * Add license header Signed-off-by: Matheus Cruz <matheuscruz.dev@gmail.com> * Apply pull request suggestions Signed-off-by: Matheus Cruz <matheuscruz.dev@gmail.com> --------- Signed-off-by: Matheus Cruz <matheuscruz.dev@gmail.com> Co-authored-by: salaboy <Salaboy@gmail.com> Signed-off-by: salaboy <Salaboy@gmail.com> * adding new method signature plus test (dapr#1570) * adding new method signature plus test Signed-off-by: salaboy <Salaboy@gmail.com> * re adding imports Signed-off-by: salaboy <Salaboy@gmail.com> * fixing style Signed-off-by: salaboy <Salaboy@gmail.com> * checking empty metadata Signed-off-by: salaboy <Salaboy@gmail.com> * copy meta for safety and check if key is present Signed-off-by: salaboy <Salaboy@gmail.com> * Centralize Maven dependency version management (dapr#1564) Signed-off-by: salaboy <Salaboy@gmail.com> * Fix dependencies multi app build and add proper test deps (dapr#1572) * Force Jackson version to override the SB Jackson version Signed-off-by: Artur Ciocanu <artur.ciocanu@gmail.com> * Move all the Jackson deps to parent POM. Signed-off-by: Artur Ciocanu <artur.ciocanu@gmail.com> * Ensure app JAR build order Signed-off-by: Artur Ciocanu <artur.ciocanu@gmail.com> * Remove explicit Jackson from sdk-tests module. Signed-off-by: Artur Ciocanu <artur.ciocanu@gmail.com> * Make sure <scope>test</scope> is used for test dependencies. Signed-off-by: Artur Ciocanu <artur.ciocanu@gmail.com> * Remove extra Jackson modules. Signed-off-by: Artur Ciocanu <artur.ciocanu@gmail.com> --------- Signed-off-by: Artur Ciocanu <artur.ciocanu@gmail.com> Signed-off-by: salaboy <Salaboy@gmail.com> * reverting pom Signed-off-by: salaboy <Salaboy@gmail.com> * fix codestyle Signed-off-by: salaboy <Salaboy@gmail.com> * using metaCopy Signed-off-by: salaboy <Salaboy@gmail.com> --------- Signed-off-by: salaboy <Salaboy@gmail.com> Signed-off-by: Artur Ciocanu <artur.ciocanu@gmail.com> Co-authored-by: artur-ciocanu <artur.ciocanu@gmail.com> Signed-off-by: salaboy <Salaboy@gmail.com> * Bump actions/upload-artifact from 4 to 5 (dapr#1587) Bumps [actions/upload-artifact](https://github.com/actions/upload-artifact) from 4 to 5. - [Release notes](https://github.com/actions/upload-artifact/releases) - [Commits](actions/upload-artifact@v4...v5) --- updated-dependencies: - dependency-name: actions/upload-artifact dependency-version: '5' dependency-type: direct:production update-type: version-update:semver-major ... Signed-off-by: dependabot[bot] <support@github.com> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> Signed-off-by: salaboy <Salaboy@gmail.com> * Add gRPC support to Dapr testcontainer (dapr#1586) * Add gRPC support to Dapr testcontainer Signed-off-by: wlfgang <wlfgang@westridgesystems.com> * Avoid using null to indicate default value Signed-off-by: wlfgang <wlfgang@westridgesystems.com> --------- Signed-off-by: wlfgang <wlfgang@westridgesystems.com> Co-authored-by: artur-ciocanu <artur.ciocanu@gmail.com> Co-authored-by: wlfgang <wlfgang@westridgesystems.com> Signed-off-by: salaboy <Salaboy@gmail.com> * Use dependencies BOM and remove duplicates. (dapr#1588) Signed-off-by: Artur Ciocanu <artur.ciocanu@gmail.com> Signed-off-by: salaboy <Salaboy@gmail.com> * Examples + Docs for App API Token authentication for gRPC and HTTP (dapr#1589) * example Signed-off-by: Cassandra Coyle <cassie@diagrid.io> * docs for example Signed-off-by: Cassandra Coyle <cassie@diagrid.io> --------- Signed-off-by: Cassandra Coyle <cassie@diagrid.io> Signed-off-by: salaboy <Salaboy@gmail.com> * Another set of Maven version, properties and plugin improvements (dapr#1596) Signed-off-by: salaboy <Salaboy@gmail.com> * Adding a Flux based subscribeToEvents method (dapr#1598) * Adding a Flux based subscribeToEvents method Signed-off-by: Artur Ciocanu <artur.ciocanu@gmail.com> * Simplify GRPC stream handling Signed-off-by: Artur Ciocanu <artur.ciocanu@gmail.com> * Simplify Javadoc Signed-off-by: Artur Ciocanu <artur.ciocanu@gmail.com> * Fix unit tests and simplify implementation Signed-off-by: Artur Ciocanu <artur.ciocanu@gmail.com> * Adding event subscriber stream observer to simplify subscription logic Signed-off-by: Artur Ciocanu <artur.ciocanu@gmail.com> * Use start() method to start stream subscription Signed-off-by: Artur Ciocanu <artur.ciocanu@gmail.com> * Add unit test for event suscriber observer Signed-off-by: Artur Ciocanu <artur.ciocanu@gmail.com> * Improve the tests a little bit Signed-off-by: Artur Ciocanu <artur.ciocanu@gmail.com> * Remove the unnecessary method Signed-off-by: Artur Ciocanu <artur.ciocanu@gmail.com> * Improve error handling and use CloudEvent wrapper Signed-off-by: Artur Ciocanu <artur.ciocanu@gmail.com> * Fix unit tests asserts Signed-off-by: Artur Ciocanu <artur.ciocanu@gmail.com> * Adjust Java examples for Subscriber Signed-off-by: Artur Ciocanu <artur.ciocanu@gmail.com> --------- Signed-off-by: Artur Ciocanu <artur.ciocanu@gmail.com> Signed-off-by: salaboy <Salaboy@gmail.com> * Remove SDK docs due to migration to main Docs repo (dapr#1593) * Remove SDK docs due to migration to main Docs repo Signed-off-by: Marc Duiker <marcduiker@users.noreply.github.com> * Remove sed lines related to sdk docs Signed-off-by: Marc Duiker <marcduiker@users.noreply.github.com> --------- Signed-off-by: Marc Duiker <marcduiker@users.noreply.github.com> Co-authored-by: salaboy <Salaboy@gmail.com> Signed-off-by: salaboy <Salaboy@gmail.com> * cleaning up sdk version script Signed-off-by: salaboy <Salaboy@gmail.com> --------- Signed-off-by: salaboy <Salaboy@gmail.com> Signed-off-by: Matheus Cruz <matheuscruz.dev@gmail.com> Signed-off-by: artur-ciocanu <artur.ciocanu@gmail.com> Signed-off-by: Artur Ciocanu <artur.ciocanu@gmail.com> Signed-off-by: dependabot[bot] <support@github.com> Signed-off-by: wlfgang <wlfgang@westridgesystems.com> Signed-off-by: Cassandra Coyle <cassie@diagrid.io> Signed-off-by: Marc Duiker <marcduiker@users.noreply.github.com> Co-authored-by: Matheus Cruz <56329339+mcruzdev@users.noreply.github.com> Co-authored-by: artur-ciocanu <artur.ciocanu@gmail.com> Co-authored-by: Raymundo Zamora <raymundo.zamora@encora.com> Co-authored-by: Siri Varma Vegiraju <siri.varma@outlook.com> Co-authored-by: Cassie Coyle <cassie.i.coyle@gmail.com> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> Co-authored-by: wlfgang <14792753+wlfgang@users.noreply.github.com> Co-authored-by: wlfgang <wlfgang@westridgesystems.com> Co-authored-by: Marc Duiker <marcduiker@users.noreply.github.com> Signed-off-by: siri-varma <siri.varma@outlook.com> * Add Cryptography API support with encrypt/decrypt operations - Add EncryptRequestAlpha1 and DecryptRequestAlpha1 domain classes - Implement encrypt() and decrypt() methods in DaprPreviewClient - Add CryptoExample and StreamingCryptoExample with documentation - Add integration tests for crypto operations - Add localstorage crypto component configuration Signed-off-by: siri-varma <siri.varma@outlook.com> * Add keys Signed-off-by: siri-varma <siri.varma@outlook.com> * Update localstorage.yaml key path to relative Signed-off-by: Siri Varma Vegiraju <siri.varma@outlook.com> * Fix things Signed-off-by: siri-varma <siri.varma@outlook.com> * fix things Signed-off-by: siri-varma <siri.varma@outlook.com> * Add missing imports Signed-off-by: siri-varma <siri.varma@outlook.com> --------- Signed-off-by: salaboy <Salaboy@gmail.com> Signed-off-by: Matheus Cruz <matheuscruz.dev@gmail.com> Signed-off-by: artur-ciocanu <artur.ciocanu@gmail.com> Signed-off-by: Artur Ciocanu <artur.ciocanu@gmail.com> Signed-off-by: dependabot[bot] <support@github.com> Signed-off-by: wlfgang <wlfgang@westridgesystems.com> Signed-off-by: Cassandra Coyle <cassie@diagrid.io> Signed-off-by: Marc Duiker <marcduiker@users.noreply.github.com> Signed-off-by: siri-varma <siri.varma@outlook.com> Signed-off-by: Siri Varma Vegiraju <siri.varma@outlook.com> Co-authored-by: salaboy <Salaboy@gmail.com> Co-authored-by: Matheus Cruz <56329339+mcruzdev@users.noreply.github.com> Co-authored-by: artur-ciocanu <artur.ciocanu@gmail.com> Co-authored-by: Raymundo Zamora <raymundo.zamora@encora.com> Co-authored-by: Cassie Coyle <cassie.i.coyle@gmail.com> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> Co-authored-by: wlfgang <14792753+wlfgang@users.noreply.github.com> Co-authored-by: wlfgang <wlfgang@westridgesystems.com> Co-authored-by: Marc Duiker <marcduiker@users.noreply.github.com> Signed-off-by: salaboy <Salaboy@gmail.com>
1 parent fc4ad5e commit a6f028e

File tree

15 files changed

+2942
-13
lines changed

15 files changed

+2942
-13
lines changed

.github/workflows/validate.yml

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -113,6 +113,10 @@ jobs:
113113
run: sleep 30 && docker logs dapr_scheduler && nc -vz localhost 50006
114114
- name: Install jars
115115
run: ./mvnw clean install -DskipTests -q
116+
- name: Validate crypto example
117+
working-directory: ./examples
118+
run: |
119+
mm.py ./src/main/java/io/dapr/examples/crypto/README.md
116120
- name: Validate workflows example
117121
working-directory: ./examples
118122
run: |
@@ -186,3 +190,5 @@ jobs:
186190
run: |
187191
mm.py ./src/main/java/io/dapr/examples/pubsub/stream/README.md
188192
193+
194+

examples/components/crypto/keys/.gitkeep

Whitespace-only changes.
Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
apiVersion: dapr.io/v1alpha1
2+
kind: Component
3+
metadata:
4+
name: localstoragecrypto
5+
spec:
6+
type: crypto.dapr.localstorage
7+
version: v1
8+
metadata:
9+
# Path to the directory containing keys (PEM files)
10+
# This path is relative to the resources-path directory
11+
- name: path
12+
value: "./components/crypto/keys/"
Lines changed: 173 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,173 @@
1+
/*
2+
* Copyright 2021 The Dapr Authors
3+
* Licensed under the Apache License, Version 2.0 (the "License");
4+
* you may not use this file except in compliance with the License.
5+
* You may obtain a copy of the License at
6+
* http://www.apache.org/licenses/LICENSE-2.0
7+
* Unless required by applicable law or agreed to in writing, software
8+
* distributed under the License is distributed on an "AS IS" BASIS,
9+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
10+
* See the License for the specific language governing permissions and
11+
limitations under the License.
12+
*/
13+
14+
package io.dapr.examples.crypto;
15+
16+
import io.dapr.client.DaprClientBuilder;
17+
import io.dapr.client.DaprPreviewClient;
18+
import io.dapr.client.domain.DecryptRequestAlpha1;
19+
import io.dapr.client.domain.EncryptRequestAlpha1;
20+
import io.dapr.config.Properties;
21+
import io.dapr.config.Property;
22+
import reactor.core.publisher.Flux;
23+
24+
import java.io.IOException;
25+
import java.nio.charset.StandardCharsets;
26+
import java.nio.file.Files;
27+
import java.nio.file.Path;
28+
import java.nio.file.Paths;
29+
import java.security.KeyPair;
30+
import java.security.KeyPairGenerator;
31+
import java.security.NoSuchAlgorithmException;
32+
import java.util.Base64;
33+
import java.util.Map;
34+
35+
/**
36+
* CryptoExample demonstrates using the Dapr Cryptography building block
37+
* to encrypt and decrypt data using a cryptography component.
38+
*
39+
* <p>This example shows:
40+
* <ul>
41+
* <li>Encrypting plaintext data with a specified key and algorithm</li>
42+
* <li>Decrypting ciphertext data back to plaintext</li>
43+
* <li>Automatic key generation if keys don't exist</li>
44+
* </ul>
45+
*
46+
* <p>Prerequisites:
47+
* <ul>
48+
* <li>Dapr installed and initialized</li>
49+
* <li>A cryptography component configured (e.g., local storage crypto)</li>
50+
* </ul>
51+
*/
52+
public class CryptoExample {
53+
54+
private static final String CRYPTO_COMPONENT_NAME = "localstoragecrypto";
55+
private static final String KEY_NAME = "rsa-private-key";
56+
private static final String KEY_WRAP_ALGORITHM = "RSA";
57+
private static final String KEYS_DIR = "components/crypto/keys";
58+
59+
/**
60+
* The main method demonstrating encryption and decryption with Dapr.
61+
*
62+
* @param args Command line arguments (unused).
63+
*/
64+
public static void main(String[] args) throws Exception {
65+
// Generate keys if they don't exist
66+
generateKeysIfNeeded();
67+
68+
Map<Property<?>, String> overrides = Map.of(
69+
Properties.HTTP_PORT, "3500",
70+
Properties.GRPC_PORT, "50001"
71+
);
72+
73+
try (DaprPreviewClient client = new DaprClientBuilder().withPropertyOverrides(overrides).buildPreviewClient()) {
74+
75+
String originalMessage = "This is a secret message";
76+
byte[] plainText = originalMessage.getBytes(StandardCharsets.UTF_8);
77+
78+
System.out.println("=== Dapr Cryptography Example ===");
79+
System.out.println("Original message: " + originalMessage);
80+
System.out.println();
81+
82+
// Encrypt the message
83+
System.out.println("Encrypting message...");
84+
EncryptRequestAlpha1 encryptRequest = new EncryptRequestAlpha1(
85+
CRYPTO_COMPONENT_NAME,
86+
Flux.just(plainText),
87+
KEY_NAME,
88+
KEY_WRAP_ALGORITHM
89+
);
90+
91+
byte[] encryptedData = client.encrypt(encryptRequest)
92+
.collectList()
93+
.map(CryptoExample::combineChunks)
94+
.block();
95+
96+
System.out.println("Encryption successful!");
97+
System.out.println("Encrypted data length: " + encryptedData.length + " bytes");
98+
System.out.println();
99+
100+
// Decrypt the message
101+
System.out.println("Decrypting message...");
102+
DecryptRequestAlpha1 decryptRequest = new DecryptRequestAlpha1(
103+
CRYPTO_COMPONENT_NAME,
104+
Flux.just(encryptedData)
105+
);
106+
107+
byte[] decryptedData = client.decrypt(decryptRequest)
108+
.collectList()
109+
.map(CryptoExample::combineChunks)
110+
.block();
111+
112+
String decryptedMessage = new String(decryptedData, StandardCharsets.UTF_8);
113+
System.out.println("Decryption successful!");
114+
System.out.println("Decrypted message: " + decryptedMessage);
115+
System.out.println();
116+
117+
if (originalMessage.equals(decryptedMessage)) {
118+
System.out.println("SUCCESS: The decrypted message matches the original.");
119+
} else {
120+
System.out.println("ERROR: The decrypted message does not match the original.");
121+
}
122+
123+
} catch (Exception e) {
124+
System.err.println("Error during crypto operations: " + e.getMessage());
125+
throw new RuntimeException(e);
126+
}
127+
}
128+
129+
/**
130+
* Generates RSA key pair if the key file doesn't exist.
131+
*/
132+
private static void generateKeysIfNeeded() throws NoSuchAlgorithmException, IOException {
133+
Path keysDir = Paths.get(KEYS_DIR);
134+
Path keyFile = keysDir.resolve(KEY_NAME + ".pem");
135+
136+
if (Files.exists(keyFile)) {
137+
System.out.println("Using existing key: " + keyFile.toAbsolutePath());
138+
return;
139+
}
140+
141+
System.out.println("Generating RSA key pair...");
142+
Files.createDirectories(keysDir);
143+
144+
KeyPairGenerator keyGen = KeyPairGenerator.getInstance("RSA");
145+
keyGen.initialize(4096);
146+
KeyPair keyPair = keyGen.generateKeyPair();
147+
148+
String privateKeyPem = "-----BEGIN PRIVATE KEY-----\n"
149+
+ Base64.getMimeEncoder(64, "\n".getBytes()).encodeToString(keyPair.getPrivate().getEncoded())
150+
+ "\n-----END PRIVATE KEY-----\n";
151+
152+
String publicKeyPem = "-----BEGIN PUBLIC KEY-----\n"
153+
+ Base64.getMimeEncoder(64, "\n".getBytes()).encodeToString(keyPair.getPublic().getEncoded())
154+
+ "\n-----END PUBLIC KEY-----\n";
155+
156+
Files.writeString(keyFile, privateKeyPem + publicKeyPem);
157+
System.out.println("Key generated: " + keyFile.toAbsolutePath());
158+
}
159+
160+
/**
161+
* Combines byte array chunks into a single byte array.
162+
*/
163+
private static byte[] combineChunks(java.util.List<byte[]> chunks) {
164+
int totalSize = chunks.stream().mapToInt(chunk -> chunk.length).sum();
165+
byte[] result = new byte[totalSize];
166+
int pos = 0;
167+
for (byte[] chunk : chunks) {
168+
System.arraycopy(chunk, 0, result, pos, chunk.length);
169+
pos += chunk.length;
170+
}
171+
return result;
172+
}
173+
}
Lines changed: 178 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,178 @@
1+
## Dapr Cryptography API Examples
2+
3+
This example provides the different capabilities provided by Dapr Java SDK for Cryptography. For further information about Cryptography APIs please refer to [this link](https://docs.dapr.io/developing-applications/building-blocks/cryptography/cryptography-overview/)
4+
5+
### Using the Cryptography API
6+
7+
The Java SDK exposes several methods for this -
8+
* `client.encrypt(...)` for encrypting data using a cryptography component.
9+
* `client.decrypt(...)` for decrypting data using a cryptography component.
10+
11+
## Pre-requisites
12+
13+
* [Dapr CLI](https://docs.dapr.io/getting-started/install-dapr-cli/).
14+
* Java JDK 11 (or greater):
15+
* [Microsoft JDK 11](https://docs.microsoft.com/en-us/java/openjdk/download#openjdk-11)
16+
* [Oracle JDK 11](https://www.oracle.com/technetwork/java/javase/downloads/index.html#JDK11)
17+
* [OpenJDK 11](https://jdk.java.net/11/)
18+
* [Apache Maven](https://maven.apache.org/install.html) version 3.x.
19+
20+
### Checking out the code
21+
22+
Clone this repository:
23+
24+
```sh
25+
git clone https://github.com/dapr/java-sdk.git
26+
cd java-sdk
27+
```
28+
29+
Then build the Maven project:
30+
31+
```sh
32+
# make sure you are in the `java-sdk` directory.
33+
mvn install
34+
```
35+
36+
Then get into the examples directory:
37+
38+
```sh
39+
cd examples
40+
```
41+
42+
### Initialize Dapr
43+
44+
Run `dapr init` to initialize Dapr in Self-Hosted Mode if it's not already initialized.
45+
46+
### Running the Example
47+
48+
This example uses the Java SDK Dapr client to **Encrypt and Decrypt** data. The example automatically generates RSA keys if they don't exist.
49+
50+
#### Example 1: Basic Crypto Example
51+
52+
`CryptoExample.java` demonstrates basic encryption and decryption of a simple message.
53+
54+
```java
55+
public class CryptoExample {
56+
private static final String CRYPTO_COMPONENT_NAME = "localstoragecrypto";
57+
private static final String KEY_NAME = "rsa-private-key";
58+
private static final String KEY_WRAP_ALGORITHM = "RSA";
59+
60+
public static void main(String[] args) {
61+
try (DaprPreviewClient client = new DaprClientBuilder().buildPreviewClient()) {
62+
63+
String originalMessage = "This is a secret message";
64+
byte[] plainText = originalMessage.getBytes(StandardCharsets.UTF_8);
65+
66+
// Encrypt the message
67+
EncryptRequestAlpha1 encryptRequest = new EncryptRequestAlpha1(
68+
CRYPTO_COMPONENT_NAME,
69+
Flux.just(plainText),
70+
KEY_NAME,
71+
KEY_WRAP_ALGORITHM
72+
);
73+
74+
byte[] encryptedData = client.encrypt(encryptRequest)
75+
.collectList()
76+
.map(chunks -> /* combine chunks */)
77+
.block();
78+
79+
// Decrypt the message
80+
DecryptRequestAlpha1 decryptRequest = new DecryptRequestAlpha1(
81+
CRYPTO_COMPONENT_NAME,
82+
Flux.just(encryptedData)
83+
);
84+
85+
byte[] decryptedData = client.decrypt(decryptRequest)
86+
.collectList()
87+
.map(chunks -> /* combine chunks */)
88+
.block();
89+
}
90+
}
91+
}
92+
```
93+
94+
Use the following command to run this example:
95+
96+
<!-- STEP
97+
name: Generate Crypto Keys
98+
expected_stdout_lines:
99+
- "Keys generated successfully"
100+
background: false
101+
output_match_mode: substring
102+
-->
103+
104+
```bash
105+
mkdir -p ./components/crypto/keys && openssl genrsa -out ./components/crypto/keys/rsa-private-key.pem 4096 && openssl rsa -in ./components/crypto/keys/rsa-private-key.pem -pubout -out ./components/crypto/keys/rsa-private-key.pub.pem && cp ./components/crypto/keys/rsa-private-key.pem ./components/crypto/keys/rsa-private-key && echo "Keys generated successfully"
106+
```
107+
108+
<!-- END_STEP -->
109+
110+
<!-- STEP
111+
name: Run Crypto Example
112+
expected_stdout_lines:
113+
- "== APP == SUCCESS: The decrypted message matches the original."
114+
background: true
115+
output_match_mode: substring
116+
sleep: 30
117+
-->
118+
119+
```bash
120+
dapr run --resources-path ./components/crypto --app-id crypto-app --dapr-http-port 3500 --dapr-grpc-port 50001 -- java -jar target/dapr-java-sdk-examples-exec.jar io.dapr.examples.crypto.CryptoExample
121+
```
122+
123+
<!-- END_STEP -->
124+
125+
#### Example 2: Streaming Crypto Example
126+
127+
`StreamingCryptoExample.java` demonstrates advanced scenarios including:
128+
- Multi-chunk data encryption
129+
- Large data encryption (100KB+)
130+
- Custom encryption ciphers
131+
132+
```bash
133+
dapr run --resources-path ./components/crypto --app-id crypto-app --dapr-http-port 3500 --dapr-grpc-port 50001 -- java -jar target/dapr-java-sdk-examples-exec.jar io.dapr.examples.crypto.StreamingCryptoExample
134+
```
135+
136+
### Sample Output
137+
138+
```
139+
=== Dapr Cryptography Example ===
140+
Original message: This is a secret message
141+
142+
Encrypting message...
143+
Encryption successful!
144+
Encrypted data length: 512 bytes
145+
146+
Decrypting message...
147+
Decryption successful!
148+
Decrypted message: This is a secret message
149+
150+
SUCCESS: The decrypted message matches the original.
151+
```
152+
153+
### Supported Key Wrap Algorithms
154+
155+
The following key wrap algorithms are supported:
156+
- `A256KW` (alias: `AES`) - AES key wrap
157+
- `A128CBC`, `A192CBC`, `A256CBC` - AES CBC modes
158+
- `RSA-OAEP-256` (alias: `RSA`) - RSA OAEP with SHA-256
159+
160+
### Supported Data Encryption Ciphers
161+
162+
Optional data encryption ciphers:
163+
- `aes-gcm` (default) - AES in GCM mode
164+
- `chacha20-poly1305` - ChaCha20-Poly1305 cipher
165+
166+
### Cleanup
167+
168+
To stop the app, run (or press CTRL+C):
169+
170+
<!-- STEP
171+
name: Cleanup
172+
-->
173+
174+
```bash
175+
dapr stop --app-id crypto-app
176+
```
177+
178+
<!-- END_STEP -->

0 commit comments

Comments
 (0)