DDClient is a Linux command-line utility written in Perl, that can update your dynamic IP entries in supported DNS providers to ensure that your domain is always pointing to the right IP.
It uses an internet service to get your public IP, but also supports reading your home router's status page instead.
For more information, see the DDClient official documentation page with supported protocols and additional configuration values.
CronJob
Kubernetes supports a native CronJob
workload, that allows you to schedule container runs that run at a certain CRON schedule. These pods can also support PVCs, making them ideal to configure DDClient with a cache PVC to ensure that DDClient only pushes updates when your public IP changes.
To create the PVC in Terraform, use the following configuration:
resource "kubernetes_persistent_volume_claim" "ddclient_cache" {
metadata {
name = "ddclient-cache"
namespace = kubernetes_namespace.ddclient.metadata.0.name
}
spec {
access_modes = ["ReadWriteOnce"]
resources {
requests = {
storage = "1Gi"
}
}
storage_class_name = "local-path"
}
}
This PVC will be mounted to the DDClient CronJob
resource at /tmp/ddclient/ddclient.cache
which we can configure as DDClient's cache using the command-line flags.
resource "kubernetes_cron_job_v1" "ddclient" {
metadata {
name = "ddclient"
namespace = kubernetes_namespace.ddclient.metadata.0.name
}
spec {
schedule = "*/5 * * * *"
job_template {
metadata {
annotations = {
"ravianand.me/config-hash" = sha1(jsonencode(merge(
kubernetes_secret.ddclient.data
)))
}
}
spec {
template {
metadata {
}
spec {
container {
image = "linuxserver/ddclient:3.10.0"
name = "ddclient"
command = ["ddclient"]
args = ["-daemon=0", "-debug", "-verbose", "-noquiet", "-cache", "/tmp/ddclient/ddclient.cache"]
volume_mount {
name = "config"
mount_path = "/etc/ddclient/ddclient.conf"
sub_path = "ddclient.conf"
}
volume_mount {
name = "cache"
mount_path = "/tmp/ddclient"
}
}
volume {
name = "config"
secret {
secret_name = kubernetes_secret.ddclient.metadata.0.name
}
}
volume {
name = "cache"
persistent_volume_claim {
claim_name = "ddclient-cache"
}
}
}
}
}
}
}
}
In addition to mounting the PVC, we specify a couple of command-line flags, to ensure DDClient only runs once, and use the -debug
and -verbose
flags to see a detailed output of the job in the pod's logs.
The pod will also mount a ConfigMap
containing the ddclient.conf
configuration file. For more information about configuration, see the section below.
DDClient is configured with a ddclient.conf
file which configures settings such as the router page to use for the public IP, your DNS provider and authentication settings.
For Namecheap dynamic DNS your settings might look something like this:
daemon=0
debug=yes
verbose=yes
fw=<your-router-ip-address>
use=web, web=dynamicdns.park-your-domain.com/getip
protocol=namecheap
server=dynamicdns.park-your-domain.com
login=<your-root-domain>
password='<your-dynamic-dns-password>'
<comma-separated-list-of-fqdns>
You can deploy the ConfigMap
with Terraform using this configuration:
resource "kubernetes_secret" "ddclient" {
metadata {
name = "ddclient"
namespace = kubernetes_namespace.ddclient.metadata.0.name
}
data = {
"ddclient.conf" = <<EOT
daemon=0
debug=yes
verbose=yes
fw=${var.router_ip}
use=web, web=dynamicdns.park-your-domain.com/getip
protocol=namecheap
server=dynamicdns.park-your-domain.com
login=${var.namecheap_domain}
password='${var.namecheap_dynamic_dns_password}'
${join(", ", var.hosts)}
EOT
}
}
Using a variable
for hosts
makes it easier to generate the config, since you can use Terraform's join()
function to join the values with commas.
To declare the value, add a variable
block like this:
variable "hosts" {
description = "List of hosts to update"
type = list(string)
}
For more information about DDClient's configuration values, see the configuration section in their docs.