Create some helper functions
In this section, you’ll create helper functions that make requests to the etcd cluster. Add a newclient directory to your etcd-antithesis directory:
client directory, add python-generate-traffic/resources directories:
resources, add a helper.py file. You should now have the following file structure in your etcd-antithesis directory:
Make requests to the cluster
Insidehelper.py, add functions to connect to a randomly chosen etcd node, and to get and put data:
random_choice function from Antithesis’s Python SDK.
Generate random strings
Next, add a helper function that usesrandom_choice to generate some random strings to insert:
get-random function from the Antithesis Python SDK to generate numbers between 1-100:
Add a Test Composer command
Next, we’ll add a Test Composer command that uses these helper functions to add key-value pairs to the etcd cluster and then check for mismatches. The Test Composer relies on an opinionated framework that identifies executable scripts as test commands using a naming convention. There are a few types of test commands, but we’ll only use the parallel driver command in this tutorial. Parallel driver commands make up the core of a typical Antithesis test, and can run in parallel with other parallel driver commands, including other copies of the same one. To make a script a parallel driver command , all we do is name the fileparallel_driver_<name>. In this case, we’ll name it parallel_driver_generate_traffic.py:
python-generate-traffic directory, run:
#!/usr/bin/env -S python3 -u).
Add a simulate_traffic function to parallel_driver_generate_traffic.py that uses your helper functions to connect to an etcd host, then generate a random number of put requests that each add a randomly generated key-value pair:
put_request to be unsuccessful during faults, so we print an “unsuccessful” message rather than stopping execution.
Next, add a validate_puts function that checks for key-value mismatches. This function takes an array of expected key-value pairs. For each key, it makes a get request to a random etcd host, and checks whether the value matches the expected one:
simulate_traffic function to generate random key-value pairs and add them to the datastore, then call validate_puts to get the values back from the datastore and check that they match:
values_stay_consistent will be true and mismatch will be None.
Add some assertions to validate
Assertions express properties your system should have, and Antithesis relies on assertions to understand what you’re testing for. Assertions in Antithesis describes the mechanics in a lot more detail. Antithesis’s SDKs provide many types of assertions, but we’ll only use two here.Add an always assertion
The first is an Always assertion — these assertions are similar to the programming assertions you’re familiar with, but they don’t crash your program. They create a property that Antithesis will test, and list in the triage report as passing or failing. You always want the datastore to be consistent. So, in your parallel driver command,values_stay_consistent must always be true.
Import always assertions from the Python SDK, and add one to your __main__ block to test that values stay consistent:
Add a sometimes assertion
The second assertion we’ll use is a Sometimes assertion (these are so valuable and unusual they get a whole section of documentation to themselves). When inserting key-value pairs into a distributed datastore in the face of network and environmental faults, it’s okay for some requests to fail. But if none of them succeed then your system is never able to insert keys into etcd and that’s either a bug or a test misconfiguration that needs attention. Here’s what a sometimes assertion looks like.sometimes assertions from the Python SDK and add them to your simulate_traffic function to assert that put requests are sometimes successful, and sometimes fail:
sometimes assertions to your validate_puts function to assert that get requests sometimes succeed and sometimes fail:
Build your client
Now you have a test template with one test command to exercise the etcd cluster. To package it, add aDockerfile.client file in the client directory:
Dockerfile.client:
.enumerated}
$TENANT_NAME with your tenant’s name.
To make the simulation more realistic, you should always run multiple client containers using the same container image.
Update the docker-compose.yaml to configure two client containers:
entrypoint attribute.
Rebuild your config image and tag as v2:
Push your images
Now push your updated images to the Antithesis registry. As before, authenticate to your container registry with:You might want to check your test commands and set up locally before running it in Antithesis.
Run your test
Call thebasic_test webhook again endpoint with this updated curl command:
v2 of the config image. Also, remember to replace $USER, $PASSWORD, $TENANT_NAME and the antithesis.report.recipients email addresses.
The test is set up to run for 30 minutes this time. To view the progress and results of your test, go to your Runs page at https://$TENANT_NAME.antithesis.com/runs and click the Triage results button to see your report when it finishes. You’ll also receive an email when the run completes.