Curl and jq to Manage ZeroTier networks

tldr; Snippets of code for using the ZeroTier API to manage and monitor the devices on my networks. This is just curl and jq command-line-fu.

I use ZeroTier as my VPN. It is effortless and works well. However, there is a bit of management overhead when you start connecting multiple networks and devices.

And, like many of you, I try to get as much done on the command line as possible.

There are only a few commands here, but they solve my immediate pain points. However, they should certaily show how easy it is to extend to your needs.

My use cases

  • Simple hostname management - I use these scripts to help me keep my /etc/hosts file updated with the other machines on my networks. I use these commands to list the machines, and then I merge any updates into my hosts file. This obviates the need for additional DNS entries, and it works all the time.
  • Prune old entries / network housecleaning - I can keep the network clean and updated easily when moving VMs, machines, etc.

References

Requirements

Before you get started you will need the following:

  • ZeroTier account (free to get, up to 100 connected devices I think)
  • API Key (generated in the ZeroTier management admin)
  • curl, jq, and colum commands installed on your system.

List my Networks

Show the network names and ids to which I have access

note - api keys and network names have been changed

$ curl -s -H "Authorization: Bearer <my_api_key>" \¬
	 -H "Content-Type: application/json" \¬
     https://my.zerotier.com/api/network \¬
     | jq -r '.[]| "\(.config.name)***\(.id)"' | column -t -s "***"¬
     
MyNet Production  c700000000000000
MyNet Staging     e411111111111111
MyNet Ops         e422222222222222
test              e433333333333333
eval pcs          1d44444444444444     

Let's unpack this a little bit:

  1. We use curl with some headers to talk to the ZeroTier API
  2. Using the API key as the token we make a request to a static endpoint.
  3. That enpoint returns a mess of JSON, which we neatly parse with the jq command. I recomment you read up the docs and the hunt for specific uses on Stackoverflow. I am not an expert.
  4. Now that we have cherry-picked our data with jq we pass it into the column command to get the pretty able output. The three asterisks *** is simply a custom delimitere we use to denote columns.

List members (eg - devices) in a single network

Given the ID (collected from the command above), show the network members (names, ids, and ip addresses).

$ curl -s -H "Authorization: Bearer <my_api_key>" \¬
	 -H "Content-Type: application/json" \¬
	  https://my.zerotier.com/api/network/c700000000000000/member \¬
 	  | jq -r '.[]| "\(.name)***\(.config.id)***\(.config.ipAssignments[0])"' | column -t -s "***" |sort
 
coffee-pot          1fffffffff  10.181.22.73
firewall-1           e222222222  10.181.22.152
macbook air         7000000000  10.181.22.98
streaming1          6aaaaaaaaa  10.181.22.81
vm-server1          6111111111  10.181.22.183

Now that we have the network id, we can see what devices are in it.

  1. Curl GET with API key in header to ZeroTier API endpoint
  2. Parse the JSON result
  3. pull out the device name, networkid, and IP address
  4. Pipe that into the column command
  5. Pip that into sort to see it alphabetically

Limitations

  • A device can have more than one IP per network. These scripts only take the first IP address in the list.
  • There are not checks on the kind of access your API key has.
  • These scripts are only for reading. None of them write to the API