May 12, 2024

The more I tinker with technology and build, the more I rely on my home servers & services to be up and accessible. So, I never want them to be unaccessible just because my IP address changed. The typical way to address this is with a Dynamic DNS (DDNS) solution. But if Gandi is your DNS registrar, setting up your own solution is pretty simple.

Gandi’s LiveDNS API And Personal Access Token

Gandi provides a range of APIs for customer use, including the powerful LiveDNS API that enables users to update their DNS records dynamically. To access these APIs, all you need to do is generate a Personal Access Token. You can generate one from your account security page:

You should see a screen similar to the following.

Gandi Personal Access Token

Once you’ve secured your new Personal Access Token, you can use it in your scripts, like the one below.

Implementation Using Ruby

Here’s a Ruby script that serves a specific purpose - it uses Gandi’s LiveDNS API to determine the current IP address and update DNS. This script is a straightforward implementation of the API.

#!/usr/bin/env ruby


# Get external IP address
external_ip = `curl -s`

# Update the A record of the subdomain using a PUT request to Gandi's LiveDNS API
livedns_endpoint = "{gandi_domain}/records/#{gandi_subdomain}/A"
cmd = "curl --silent --fail -X PUT -H 'Content-Type: application/json' -H 'Authorization: Bearer #{gandi_token}' -d '{\"rrset_ttl\": 1200, \"rrset_values\": [\"#{external_ip}\"]}' #{livedns_endpoint}"
output = `#{cmd}`

# Check exit code
if $?.exitstatus != 0
  puts "ERROR: Gandi DNS update failed. Exit code #{$?.exitstatus}."
  exit 1

What is happening here? To start, the script relies on some variable assignments, including the aforementioned Gandi Person Access Token. Then it retrieves the public IP address from, a free service operated by IPinfo. With that, it then attempts to update the ‘A’ DNS record for the subdomain using the LiveDNS API. If the execution goes well, no errors should be reported.

Running The Script

Finally, the script should run periodically since we want to counter unpredictable IP changes. A 30-minute interval makes for a reasonable balance between API consumption and non-commercial service availability. We can declare such a job using the guidance I provided in my Scheduling Commands With Cron On Your Mac post.

— Onyx