Bash script to update IPv4 and IPv6 records in Cloudflare. Update with WAN or LAN IP.
- Bash Script for most Linux, Unix distributions and MacOS.
- Choose any source IP address to update external or internal (WAN/LAN) for ech domain.
- For multiply lan interfaces like Wifi, Docker Networks and Bridges the script will automatically detects the primary Interface by priority.
- Cloudflare's options proxy and TTL configurable via the config file for each domain.
- Optional Telegram Notifications
- curl
- Cloudflare api-token with ZONE-DNS-EDIT Permissions
- DNS Record must be pre created in web interface (WIP: Create record if no exist)
To create a CloudFlare API token for your DNS zone go to cloudflare-api-token-url and follow these steps:
- Click Create Token
- Select Create Custom Token
- Provide the token a name, for example,
example.com-dns-zone-readonly
- Grant the token the following permissions:
- Zone - DNS - Edit
- Set the zone resources to:
- Include - Specific Zone -
example.com
- Include - Specific Zone -
- Complete the wizard and use the generated token at the
CLOUDFLARE_API_TOKEN
variable for the container
You can place the script at any location manually.
MacOS: Don't use the /usr/local/bin/ for the script location. Create a separate folder under your user path /Users/${USER}
The automatic install examples below will place the script at /usr/local/bin/
wget https://raw.githubusercontent.com/jmrplens/DyDNS_Cloudflare_IPv4-6/main/cloudflare-dns.sh
sudo chmod +x cloudflare-dns.sh
sudo mv cloudflare-dns.sh /usr/local/bin/cloudflare-dns
You can use default config file cloudflare-dns.yaml or pass your own config file as parameter to script.
wget https://raw.githubusercontent.com/jmrplens/DyDNS_Cloudflare_IPv4-6/main/cloudflare-dns.yaml
Place the config file in the directory as the update-cloudflare-dns for above example at /usr/local/bin/
sudo mv cloudflare-dns.yaml /usr/local/bin/cloudflare-dns.yaml
Edit it with your favorite editor and set the necessary parameters.
domains:
- name: example.com
ip_type: external
ipv4: true
ipv6: true
proxied: true
ttl: auto
settings:
cloudflare:
- zone_id: #########
- zone_api_token: ########
misc:
- create_if_no_exist: false
notifications:
telegram:
enabled: false
bot_token: token
chat_id: id
Multiple domains is supported:
domains:
- name: example.com
ip_type: external
ipv4: true
ipv6: true
proxied: true
ttl: auto
- name: example2.com # Only name = using default settings
- name: example3.com
ip_type: external
ipv4: true
ipv6: true
proxied: false
ttl: auto
- name: ..........
.........
Option | Example | Description |
---|---|---|
name | example.com | Domain name. Required |
ip_type | external | Which IP should be used for the record: internal/external. Optional (default: external) |
ipv4 | true | Update IPv4 DNS Record: true/false. Optional (default: true) |
ipv6 | true | Update IPv6 DNS Record: true/false. Optional (default: true) |
proxied | true | Use Cloudflare proxy on dns record: true/false. Optional (default: true) |
ttl | 3600 | 120-7200 in seconds or auto. Optional (default: auto) |
Option | Example | Description |
---|---|---|
zone_api_token | token | Cloudflare API Token KEEP IT PRIVATE!!!! |
zone_id | id | Cloudflare's Zone ID |
Option | Example | Description |
---|---|---|
create_if_no_exist | false | Not yet implemented |
Option | Example | Description |
---|---|---|
enabled | true | Use Telegram notifications: true/false. |
bot_token | token | Telegram's Bot API Token |
chat_id | id | Chat ID of the bot |
When placed in /usr/local/bin/
cloudflare-dns dyndns-update
With your config file (need to be placed in same folder)
cloudflare-dns dyndns-update your_config.yaml
You can run the script via crontab
crontab -e
Example | Code |
Run every minute |
* * * * * /usr/local/bin/cloudflare-dns dyndns-update |
Run every minute with your specific config file |
* * * * * /usr/local/bin/cloudflare-dns dyndns-update myconfig.yaml |
Run every every 2 minutes |
*/2 * * * * /usr/local/bin/cloudflare-dns dyndns-update |
Run at boot |
@reboot /usr/local/bin/cloudflare-dns dyndns-update |
Run 1 minute after boot |
@reboot sleep 60 && /usr/local/bin/cloudflare-dns dyndns-update |
This Script will create a log file with only the last run information Log file will be located at the script's location.
Example:
/usr/local/bin/cloudflare-dns.log
The bats framework is used to perform the unit tests. In addition, if you want to obtain the Code Coverage you use bashcov.
To run them locally:
-
Clone this repository and update the submodules:
git clone https://github.com/jmrplens/DynDNS_Cloudflare_IPv4-6.git cd DynDNS_Cloudflare_IPv4-6 git submodule update --init --recursive
-
Execute the tests:
-
Without code coverage:
# Path: ../DynDNS_Cloudflare_IPv4-6/ ./unit_test.sh
-
With code coverage:
-
With Ruby 3 or higher, install the dependencies:
# Path: ../DynDNS_Cloudflare_IPv4-6/ gem install bundler export BUNDLE_GEMFILE=test/Gemfile bundle install
-
Execute tests with code coverage:
# Path: ../DynDNS_Cloudflare_IPv4-6/ bashcov ./unit_test.sh
-
-
Here we describe how the Github CI workflows for unit testing and code coverage work.
%%{
init: {
"fontFamily": "monospace",
"flowchart": {
"htmlLabels": true
},
"sequence": {}
}
}%%
flowchart LR
subgraph WC[Main Workflow]
A(<b>Unit Test and Coverage</b>\n <i><small><a href='https://github.com/jmrplens/DynDNS_Cloudflare_IPv4-6/blob/main/.github/workflows/test_cov_main.yaml'>test_cov_main.yaml</a></small></i>)
A --> B[Matrix strategy\n\n<table><tr><td align='left'><b>OS           RUBY</b></td><td> 3.0 </td><td style='background-color:'> 3.1 </td><td> 3.2 </td><td> 3.3 </td></tr><tr style='color:brown'><td>Ubuntu 22.04     </td><td>•</td><td>•</td><td>•</td><td>•</td></tr><tr style='color:darkviolet'><td align='left'>Debian 11        </td><td>•</td><td>•</td><td>•</td><td>•</td></tr><tr style='color:forestgreen'><td align='left'>CentOS 9         </td><td>•</td><td>•</td><td>•</td><td>•</td></tr><tr style='color:darkorange'><td align='left'>Mac OS 13        </td><td>•</td><td>•</td><td>•</td><td>•</td></tr></table>\n]
B ==>C[Call a worker for each combination]
linkStyle 1 stroke-width:2px,stroke:red;
end
C -->WU
C -->WU
C -->WU
C -->WU
C -->WU
C -->WU
C -->WU
C -->WU
C -->WU
C -->WU
C -->WU
C -->WU
C -->WU
C -->WU
C -->WU
C -->WU
subgraph WU[Reusable Workflow]
D[<b>Worker to run the tests and coverage</b>\n<i><small><a href='https://github.com/jmrplens/DynDNS_Cloudflare_IPv4-6/blob/main/.github/workflows/test_cov_worker.yaml'>test_cov_worker.yaml</a></small></i>]
D --> E[Checkout repository with submodules]
E --> F[Build/Install Ruby and the needed Gems\n<i><small><a href='https://github.com/jmrplens/DynDNS_Cloudflare_IPv4-6/blob/main/test/Gemfile'>test/Gemfile</a></small></i>]
F --> G[Run unit test with coverage\n<small><code>bashcov ./unit-test.sh</code></small>]
G --> H[Upload coverage reports to:\n<a href='https://app.codecov.io/github/jmrplens/DynDNS_Cloudflare_IPv4-6'>Codecov</a> and <a href='https://app.codacy.com/gh/jmrplens/DynDNS_Cloudflare_IPv4-6/dashboard'>Codacy</a>]
end
To run the Github CI on MacOS, Debian and CentOS, self-hosted runners are used.
For Debian and CentOS operating systems it is necessary to manually install the Ruby versions that will run the tests. This is required:
-
Install self-hosted runner.
-
Install ruby-build. Follow the instructions in Install manually as a standalone program.
-
Assuming you have used the default work folder name
_work
, you must install the Ruby versions to be run in the runner into that folder:ruby-build X.Y.Z ACTION_RUNNER_PATH/_work/_tool/Ruby/X.Y.Z/x64
Where X.Y.Z is the Ruby version you want to install (3.0.6, 3.1.4, ...).
And mark it as completed with:
touch /root/actions-runner/_work/_tool/Ruby/X.Y.Z/x64.complete
Where X.Y.Z is the Ruby version you have installed (3.0.6, 3.1.4, ...).