MeanStreet
MeanStreet

Reputation: 1287

How to check that a Cassandra node is ready?

I have a Cassandra node running in a Docker container and I want to launch a CQL script when the database is ready. I tried checking the port to detect when it's ready :

while ! nc -z localhost 7199; do
    sleep 1
done
echo "Cassandra is ready"
cqlsh -f ./createTables.cql

But the port is opened before the database is really ready, and the cqlsh therefore fails. How to properly check the Cassandra status and launch the script ?

Upvotes: 12

Views: 7177

Answers (2)

Gino Mempin
Gino Mempin

Reputation: 29598

You can use a shell command to poll nodetool status on your Docker container, and wait until the node/s are marked as UN.

For example, let's say you only have 1 Cassandra node in a Docker container and it's named cassandra-node-1 (set with docker run --name), the output of nodetool status if cassandra-node-1 is already available is:

$ docker exec cassandra-node-1 nodetool status
Datacenter: my-datacenter-1
=======================================
Status=Up/Down
|/ State=Normal/Leaving/Joining/Moving
--  Address     Load      Tokens  Owns (effective)  Host ID                               Rack 
UN  172.21.0.2  7.91 MiB  16      100.0%            c74fb450-fe49-4a73-9a0b-f25fbc4ad096  rack1

where UN means the node is Up and Normal.

Then an until bash loop can be:

until $(docker exec cassandra-node-1 nodetool status | grep "UN" > /dev/null); do 
  echo "Waiting for cassandra-node-1..."; 
  sleep 1; 
done

where we grep for a UN string. grep will return a non-zero exit code if there is no matching string and until will keep looping while the condition is false-y. (If you have multiple nodes, you'll need to do a better check that all the nodes are UN. This is just an example for the case of 1 node.)

The sample output would be:

$ until $(docker exec cassandra-node-1 nodetool status | grep "UN" > /dev/null); do echo "Waiting for cassandra-node-1"; sleep 1; done;
Error response from daemon: Container 42103912deea0329e5a2e73eda7a7a157f757598a58dc79e9ec9972ae95ec7a8 is not running
Error response from daemon: Container 42103912deea0329e5a2e73eda7a7a157f757598a58dc79e9ec9972ae95ec7a8 is not running
Error response from daemon: Container 42103912deea0329e5a2e73eda7a7a157f757598a58dc79e9ec9972ae95ec7a8 is not running
Waiting for cassandra-node-1
Waiting for cassandra-node-1
$

where the until loop exits once the node is UN.

You can also try to use other nodetool commands like info and describecluster:
https://cassandra.apache.org/doc/latest/cassandra/tools/nodetool/nodetool.html

Upvotes: 0

Alex Ott
Alex Ott

Reputation: 87164

First, you need to wait on another port: 9042. This is the port that is used by CQLSH.

Another approach could be also waiting for execution of cqlsh instead of nc (or as a second step, because nc is much faster to execute). For example, you can use something like these commands:

while ! cqlsh -e 'describe cluster' ; do
    sleep 1
done

to wait until Cassandra is ready...

Upvotes: 15

Related Questions