Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Sample and command line refactor #394

Merged
merged 34 commits into from
Apr 10, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
34 commits
Select commit Hold shift + click to select a range
d3ce316
Refactor BasicConnect to not rely on cmdUtils
TwistedTwigleg Apr 4, 2023
502513c
Refactor pubsub to not rely on cmdUtils to create the connection
TwistedTwigleg Apr 4, 2023
e0a9fc7
Refactor cognito connect to not rely on cmdUtils to create the connec…
TwistedTwigleg Apr 4, 2023
bf15252
Refactor custom auth connect to not rely on cmdUtils to create the co…
TwistedTwigleg Apr 4, 2023
c3be714
Refactor CustomKeyOps to not rely on cmdUtils, refactor sample to be …
TwistedTwigleg Apr 4, 2023
908a247
Refactor BasicDiscovery sample to fit same format as other samples
TwistedTwigleg Apr 4, 2023
ea88ad7
Refactor Fleet Provisioning sample to not rely on cmdUtils
TwistedTwigleg Apr 4, 2023
27f7d8d
Refactor java keystore sample not to rely on cmdUtils
TwistedTwigleg Apr 4, 2023
528f480
Refactor jobs sample to not rely on cmdUtils for connection
TwistedTwigleg Apr 4, 2023
a7da97a
Refactor PubSub sample to not rely on cmdUtils to make the connection
TwistedTwigleg Apr 4, 2023
45d95ef
Refactor PKCS11 connect sample to not rely on cmdUtils for connection
TwistedTwigleg Apr 4, 2023
4475409
Remove PubSubStress sample
TwistedTwigleg Apr 4, 2023
e35e5fa
Refactor raw connect sample to not rely on cmdUtils for sample functi…
TwistedTwigleg Apr 4, 2023
0529ddf
Refactor shadow sample not to rely on cmdUtils for creating the MQTT …
TwistedTwigleg Apr 4, 2023
74e97e2
Refactor websocket connect to avoid relying on cmdUtils to make the c…
TwistedTwigleg Apr 4, 2023
8d0774c
Refactor WindowsCertConnect not to rely on cmdUtils, make it more lik…
TwistedTwigleg Apr 4, 2023
63dcfb3
Refactor the X509 sample to not rely on cmdUtils to make the MQTT con…
TwistedTwigleg Apr 4, 2023
f72108f
Fix compile issues
TwistedTwigleg Apr 4, 2023
27951c8
Rename Identity to Fleet Provisioning for the purpose of the sample. …
TwistedTwigleg Apr 4, 2023
3ee10db
Update the custom key ops package name
TwistedTwigleg Apr 4, 2023
fe4b27a
Remove trying to get arguments that are not required in samples
TwistedTwigleg Apr 4, 2023
6a15fc0
Typo fix
TwistedTwigleg Apr 4, 2023
ee383ab
Another typo fix
TwistedTwigleg Apr 4, 2023
3ef753b
More fixes
TwistedTwigleg Apr 4, 2023
57dcc92
Merge branch 'main' of https://github.com/aws/aws-iot-device-sdk-java…
TwistedTwigleg Apr 4, 2023
dc91d85
Parse command line input into a single struct to simplify samples. St…
TwistedTwigleg Apr 5, 2023
5fe859b
Finish simplifying command line argumets in samples
TwistedTwigleg Apr 5, 2023
9097b87
Merge branch 'main' of https://github.com/aws/aws-iot-device-sdk-java…
TwistedTwigleg Apr 5, 2023
2e998bc
Send the arguments in the custom key ops sample
TwistedTwigleg Apr 5, 2023
568858c
Keep optional arguments optional
TwistedTwigleg Apr 5, 2023
2786b30
Condense setting up and getting the sample arguments from the command…
TwistedTwigleg Apr 5, 2023
2422bf6
Fix CI
TwistedTwigleg Apr 5, 2023
0672a27
CR - append UUID as part of populating cmdData, remove unused imports
TwistedTwigleg Apr 7, 2023
e7fbac5
Remove Raw Connect sample
TwistedTwigleg Apr 7, 2023
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions .github/workflows/ci_run_custom_key_ops_cfg.json
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
{
"language": "Java",
"sample_file": "samples/CustomKeyOpsPubSub",
"sample_file": "samples/CustomKeyOpsConnect",
"sample_region": "us-east-1",
"sample_main_class": "customkeyopspubsub.CustomKeyOpsPubSub",
"sample_main_class": "customkeyopsconnect.CustomKeyOpsConnect",
"arguments": [
{
"name": "--endpoint",
Expand Down
4 changes: 2 additions & 2 deletions .github/workflows/ci_run_fleet_provisioning_cfg.json
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
{
"language": "Java",
"sample_file": "samples/Identity",
"sample_file": "samples/FleetProvisioning",
"sample_region": "us-east-1",
"sample_main_class": "identity.FleetProvisioningSample",
"sample_main_class": "fleetprovisioning.FleetProvisioningSample",
"arguments": [
{
"name": "--endpoint",
Expand Down
1 change: 0 additions & 1 deletion android/app/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,6 @@ android {
main {
java.srcDir '../../samples/BasicPubSub/src/main/java'
java.srcDir '../../samples/Jobs/src/main/java'
java.srcDir '../../samples/PubSubStress/src/main/java'
java.srcDir '../../samples/Shadow/src/main/java'
java.srcDir 'src/main/java'
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -17,8 +17,7 @@ import kotlin.concurrent.thread
val SAMPLES = mapOf(
"Publish/Subscribe Sample" to "pubsub.PubSub",
"Jobs Client Sample" to "jobs.JobsSample",
"Shadow Client Sample" to "shadow.ShadowSample",
"Publish/Subscribe Load Test" to "pubsubstress.PubSubStress"
"Shadow Client Sample" to "shadow.ShadowSample"
)

class MainActivity : AppCompatActivity(), AdapterView.OnItemSelectedListener {
Expand Down
4 changes: 2 additions & 2 deletions codebuild/samples/custom-key-ops-linux.sh
Original file line number Diff line number Diff line change
Expand Up @@ -4,13 +4,13 @@ set -e
set -o pipefail
env

pushd $CODEBUILD_SRC_DIR/samples/CustomKeyOpsPubSub
pushd $CODEBUILD_SRC_DIR/samples/CustomKeyOpsConnect

ENDPOINT=$(aws secretsmanager get-secret-value --secret-id "ci/endpoint" --query "SecretString" | cut -f2 -d":" | sed -e 's/[\\\"\}]//g')

mvn compile

echo "Custom Key Ops test"
mvn exec:java -Dexec.mainClass="customkeyopspubsub.CustomKeyOpsPubSub" -Daws.crt.ci="True" -Dexec.arguments="--endpoint,$ENDPOINT,--key,/tmp/privatekey_p8.pem,--cert,/tmp/certificate.pem"
mvn exec:java -Dexec.mainClass="customkeyopsconnect.CustomKeyOpsConnect" -Daws.crt.ci="True" -Dexec.arguments="--endpoint,$ENDPOINT,--key,/tmp/privatekey_p8.pem,--cert,/tmp/certificate.pem"

popd
4 changes: 2 additions & 2 deletions codebuild/samples/customkeyops-linux.sh
Original file line number Diff line number Diff line change
Expand Up @@ -4,13 +4,13 @@ set -e

env

pushd $CODEBUILD_SRC_DIR/samples/CustomKeyOpsPubSub
pushd $CODEBUILD_SRC_DIR/samples/CustomKeyOpsConnect

ENDPOINT=$(aws secretsmanager get-secret-value --secret-id "unit-test/endpoint" --query "SecretString" | cut -f2 -d":" | sed -e 's/[\\\"\}]//g')

mvn compile

echo "Custom Key Ops test"
mvn exec:java -Dexec.mainClass="customkeyopspubsub.CustomKeyOpsPubSub" -Daws.crt.ci="True" -Dexec.arguments="--endpoint,$ENDPOINT,--key,/tmp/privatekey_p8.pem,--cert,/tmp/certificate.pem"
mvn exec:java -Dexec.mainClass="customkeyopsconnect.CustomKeyOpsConnect" -Daws.crt.ci="True" -Dexec.arguments="--endpoint,$ENDPOINT,--key,/tmp/privatekey_p8.pem,--cert,/tmp/certificate.pem"

popd
4 changes: 2 additions & 2 deletions documents/MQTT5_Userguide.md
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,7 @@

MQTT5 support is currently in **developer preview**. We encourage feedback at all times, but feedback during the preview window is especially valuable in shaping the final product. During the preview period we may make backwards-incompatible changes to the public API, but in general, this is something we will try our best to avoid.

The MQTT5 client cannot yet be used with the AWS IoT MQTT services (Shadow, Jobs, Identity). We plan to address this in the near future.
The MQTT5 client cannot yet be used with the AWS IoT MQTT services (Shadow, Jobs, Fleet-Provisioning/Identity). We plan to address this in the near future.

# Introduction

Expand Down Expand Up @@ -221,7 +221,7 @@ A MQTT5 direct connection can be made with a set of custom private key operation
~~~ java
class MyKeyOperationHandler implements TlsKeyOperationHandler {

// Implement based on the operation. See CustomKeyOpsPubSub sample for example
// Implement based on the operation. See CustomKeyOpsConnect sample for example
public void performOperation(TlsKeyOperation operation) {
try {
throw new RuntimeException("This is just an example!");
Expand Down
6 changes: 2 additions & 4 deletions pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -12,19 +12,17 @@
<module>samples/BasicConnect</module>
<module>samples/WebsocketConnect</module>
<module>samples/X509CredentialsProviderConnect</module>
<module>samples/RawConnect</module>
<module>samples/Pkcs11Connect</module>
<module>samples/CustomAuthorizerConnect</module>
<module>samples/JavaKeystoreConnect</module>
<module>samples/CognitoConnect</module>
<module>samples/Greengrass</module>
<module>samples/GreengrassIPC</module>
<module>samples/Jobs</module>
<module>samples/PubSubStress</module>
<module>samples/CustomKeyOpsPubSub</module>
<module>samples/CustomKeyOpsConnect</module>
<module>samples/WindowsCertConnect</module>
<module>samples/Shadow</module>
<module>samples/Identity</module>
<module>samples/FleetProvisioning</module>
<module>samples/Mqtt5/PubSub</module>
<module>samples/Mqtt5/SharedSubscription</module>
</modules>
Expand Down
80 changes: 54 additions & 26 deletions samples/BasicConnect/src/main/java/basicconnect/BasicConnect.java
Original file line number Diff line number Diff line change
Expand Up @@ -8,29 +8,26 @@
import software.amazon.awssdk.crt.CRT;
import software.amazon.awssdk.crt.CrtResource;
import software.amazon.awssdk.crt.CrtRuntimeException;
import software.amazon.awssdk.crt.io.ClientBootstrap;
import software.amazon.awssdk.crt.mqtt.MqttClientConnection;
import software.amazon.awssdk.crt.mqtt.MqttClientConnectionEvents;
import software.amazon.awssdk.iot.iotjobs.model.RejectedError;
import software.amazon.awssdk.crt.http.HttpProxyOptions;
import software.amazon.awssdk.iot.AwsIotMqttConnectionBuilder;

import java.util.concurrent.ExecutionException;
import java.util.concurrent.CompletableFuture;

import utils.commandlineutils.CommandLineUtils;

public class BasicConnect {

// When run normally, we want to exit nicely even if something goes wrong
// When run normally, we want to exit nicely even if something goes wrong.
// When run from CI, we want to let an exception escape which in turn causes the
// exec:java task to return a non-zero exit code
// exec:java task to return a non-zero exit code.
static String ciPropValue = System.getProperty("aws.crt.ci");
static boolean isCI = ciPropValue != null && Boolean.valueOf(ciPropValue);

static CommandLineUtils cmdUtils;

static void onRejectedError(RejectedError error) {
System.out.println("Request rejected: " + error.code.toString() + ": " + error.message);
}

/*
* When called during a CI run, throw an exception that will escape and fail the exec:java task
* When called otherwise, print what went wrong (if anything) and just continue (return from main)
Expand All @@ -45,15 +42,12 @@ static void onApplicationFailure(Throwable cause) {

public static void main(String[] args) {

cmdUtils = new CommandLineUtils();
cmdUtils.registerProgramName("BasicConnect");
cmdUtils.addCommonMQTTCommands();
cmdUtils.addCommonProxyCommands();
cmdUtils.registerCommand("key", "<path>", "Path to your key in PEM format.");
cmdUtils.registerCommand("cert", "<path>", "Path to your client certificate in PEM format.");
cmdUtils.registerCommand("client_id", "<int>", "Client id to use (optional, default='test-*').");
cmdUtils.registerCommand("port", "<int>", "Port to connect to on the endpoint (optional, default='8883').");
cmdUtils.sendArguments(args);
/**
* cmdData is the arguments/input from the command line placed into a single struct for
* use in this sample. This handles all of the command line parsing, validating, etc.
* See the Utils/CommandLineUtils for more information.
*/
CommandLineUtils.SampleCommandLineData cmdData = CommandLineUtils.getInputForIoTSample("BasicConnect", args);

MqttClientConnectionEvents callbacks = new MqttClientConnectionEvents() {
@Override
Expand All @@ -71,20 +65,54 @@ public void onConnectionResumed(boolean sessionPresent) {

try {

// Create a connection using a certificate and key
// Note: The data for the connection is gotten from cmdUtils.
// (see buildDirectMQTTConnection for implementation)
MqttClientConnection connection = cmdUtils.buildDirectMQTTConnection(callbacks);
/**
* Create the MQTT connection from the builder
*/
AwsIotMqttConnectionBuilder builder = AwsIotMqttConnectionBuilder.newMtlsBuilderFromPath(cmdData.input_cert, cmdData.input_key);
if (cmdData.input_ca != "") {
builder.withCertificateAuthorityFromPath(null, cmdData.input_ca);
}
builder.withConnectionEventCallbacks(callbacks)
.withClientId(cmdData.input_clientId)
.withEndpoint(cmdData.input_endpoint)
.withPort((short)cmdData.input_port)
.withCleanSession(true)
.withProtocolOperationTimeoutMs(60000);
if (cmdData.input_proxyHost != "" && cmdData.input_proxyPort > 0) {
HttpProxyOptions proxyOptions = new HttpProxyOptions();
proxyOptions.setHost(cmdData.input_proxyHost);
proxyOptions.setPort(cmdData.input_proxyPort);
builder.withHttpProxyOptions(proxyOptions);
}
MqttClientConnection connection = builder.build();
builder.close();

/**
* Verify the connection was created
*/
if (connection == null)
{
onApplicationFailure(new RuntimeException("MQTT connection creation failed!"));
}

// Connect and disconnect using the connection we created
// (see sampleConnectAndDisconnect for implementation)
cmdUtils.sampleConnectAndDisconnect(connection);

// Close the connection now that we are completely done with it.
/**
* Connect and disconnect
*/
CompletableFuture<Boolean> connected = connection.connect();
try {
boolean sessionPresent = connected.get();
System.out.println("Connected to " + (!sessionPresent ? "new" : "existing") + " session!");
} catch (Exception ex) {
throw new RuntimeException("Exception occurred during connect", ex);
}
System.out.println("Disconnecting...");
CompletableFuture<Void> disconnected = connection.disconnect();
disconnected.get();
System.out.println("Disconnected.");

/**
* Close the connection now that it is complete
*/
connection.close();

} catch (CrtRuntimeException | InterruptedException | ExecutionException ex) {
Expand Down
74 changes: 34 additions & 40 deletions samples/BasicPubSub/src/main/java/pubsub/PubSub.java
Original file line number Diff line number Diff line change
Expand Up @@ -8,21 +8,14 @@
import software.amazon.awssdk.crt.CRT;
import software.amazon.awssdk.crt.CrtResource;
import software.amazon.awssdk.crt.CrtRuntimeException;
import software.amazon.awssdk.crt.Log;
import software.amazon.awssdk.crt.auth.credentials.X509CredentialsProvider;
import software.amazon.awssdk.crt.http.HttpProxyOptions;
import software.amazon.awssdk.crt.io.ClientBootstrap;
import software.amazon.awssdk.crt.io.ClientTlsContext;
import software.amazon.awssdk.crt.io.TlsContextOptions;
import software.amazon.awssdk.crt.mqtt.MqttClientConnection;
import software.amazon.awssdk.crt.mqtt.MqttClientConnectionEvents;
import software.amazon.awssdk.crt.mqtt.MqttMessage;
import software.amazon.awssdk.crt.mqtt.QualityOfService;
import software.amazon.awssdk.iot.AwsIotMqttConnectionBuilder;
import software.amazon.awssdk.iot.iotjobs.model.RejectedError;

import java.nio.charset.StandardCharsets;
import java.util.UUID;
import java.util.concurrent.CompletableFuture;
import java.util.concurrent.CountDownLatch;
import java.util.concurrent.ExecutionException;
Expand All @@ -37,16 +30,8 @@ public class PubSub {
static String ciPropValue = System.getProperty("aws.crt.ci");
static boolean isCI = ciPropValue != null && Boolean.valueOf(ciPropValue);

static String topic = "test/topic";
static String message = "Hello World!";
static int messagesToPublish = 10;

static CommandLineUtils cmdUtils;

static void onRejectedError(RejectedError error) {
System.out.println("Request rejected: " + error.code.toString() + ": " + error.message);
}

/*
* When called during a CI run, throw an exception that will escape and fail the exec:java task
* When called otherwise, print what went wrong (if anything) and just continue (return from main)
Expand All @@ -61,20 +46,12 @@ static void onApplicationFailure(Throwable cause) {

public static void main(String[] args) {

cmdUtils = new CommandLineUtils();
cmdUtils.registerProgramName("PubSub");
cmdUtils.addCommonMQTTCommands();
cmdUtils.addCommonTopicMessageCommands();
cmdUtils.registerCommand("key", "<path>", "Path to your key in PEM format.");
cmdUtils.registerCommand("cert", "<path>", "Path to your client certificate in PEM format.");
cmdUtils.registerCommand("client_id", "<int>", "Client id to use (optional, default='test-*').");
cmdUtils.registerCommand("port", "<int>", "Port to connect to on the endpoint (optional, default='8883').");
cmdUtils.registerCommand("count", "<int>", "Number of messages to publish (optional, default='10').");
cmdUtils.sendArguments(args);

topic = cmdUtils.getCommandOrDefault("topic", topic);
message = cmdUtils.getCommandOrDefault("message", message);
messagesToPublish = Integer.parseInt(cmdUtils.getCommandOrDefault("count", String.valueOf(messagesToPublish)));
/**
* cmdData is the arguments/input from the command line placed into a single struct for
* use in this sample. This handles all of the command line parsing, validating, etc.
* See the Utils/CommandLineUtils for more information.
*/
CommandLineUtils.SampleCommandLineData cmdData = CommandLineUtils.getInputForIoTSample("PubSub", args);

MqttClientConnectionEvents callbacks = new MqttClientConnectionEvents() {
@Override
Expand All @@ -92,12 +69,29 @@ public void onConnectionResumed(boolean sessionPresent) {

try {

MqttClientConnection connection = cmdUtils.buildMQTTConnection(callbacks);
if (connection == null)
{
onApplicationFailure(new RuntimeException("MQTT connection creation failed!"));
/**
* Create the MQTT connection from the builder
*/
AwsIotMqttConnectionBuilder builder = AwsIotMqttConnectionBuilder.newMtlsBuilderFromPath(cmdData.input_cert, cmdData.input_key);
if (cmdData.input_ca != "") {
builder.withCertificateAuthorityFromPath(null, cmdData.input_ca);
}
builder.withConnectionEventCallbacks(callbacks)
.withClientId(cmdData.input_clientId)
.withEndpoint(cmdData.input_endpoint)
.withPort((short)cmdData.input_port)
.withCleanSession(true)
.withProtocolOperationTimeoutMs(60000);
if (cmdData.input_proxyHost != "" && cmdData.input_proxyPort > 0) {
HttpProxyOptions proxyOptions = new HttpProxyOptions();
proxyOptions.setHost(cmdData.input_proxyHost);
proxyOptions.setPort(cmdData.input_proxyPort);
builder.withHttpProxyOptions(proxyOptions);
}
MqttClientConnection connection = builder.build();
builder.close();

// Connect the MQTT client
CompletableFuture<Boolean> connected = connection.connect();
try {
boolean sessionPresent = connected.get();
Expand All @@ -106,25 +100,25 @@ public void onConnectionResumed(boolean sessionPresent) {
throw new RuntimeException("Exception occurred during connect", ex);
}

CountDownLatch countDownLatch = new CountDownLatch(messagesToPublish);

CompletableFuture<Integer> subscribed = connection.subscribe(topic, QualityOfService.AT_LEAST_ONCE, (message) -> {
// Subscribe to the topic
CountDownLatch countDownLatch = new CountDownLatch(cmdData.input_count);
CompletableFuture<Integer> subscribed = connection.subscribe(cmdData.input_topic, QualityOfService.AT_LEAST_ONCE, (message) -> {
String payload = new String(message.getPayload(), StandardCharsets.UTF_8);
System.out.println("MESSAGE: " + payload);
countDownLatch.countDown();
});

subscribed.get();

// Publish to the topic
int count = 0;
while (count++ < messagesToPublish) {
CompletableFuture<Integer> published = connection.publish(new MqttMessage(topic, message.getBytes(), QualityOfService.AT_LEAST_ONCE, false));
while (count++ < cmdData.input_count) {
CompletableFuture<Integer> published = connection.publish(new MqttMessage(cmdData.input_topic, cmdData.input_message.getBytes(), QualityOfService.AT_LEAST_ONCE, false));
published.get();
Thread.sleep(1000);
}

countDownLatch.await();

// Disconnect
CompletableFuture<Void> disconnected = connection.disconnect();
disconnected.get();

Expand Down
Loading