# Update Hetzner Cloud Firewall Rules with Current Cloudflare IP Ranges <!-- omit in toc -->
[![codecov](https://codecov.io/gh/jkreileder/cf-ips-to-hcloud-fw/graph/badge.svg?token=PCP1F2XWAT)](https://codecov.io/gh/jkreileder/cf-ips-to-hcloud-fw)
[![OpenSSF Best Practices](https://www.bestpractices.dev/projects/8275/badge)](https://www.bestpractices.dev/projects/8275)
[![OpenSSF Scorecard](https://api.scorecard.dev/projects/github.com/jkreileder/cf-ips-to-hcloud-fw/badge)](https://scorecard.dev/viewer/?uri=github.com/jkreileder/cf-ips-to-hcloud-fw)
[![CodeQL](https://github.com/jkreileder/cf-ips-to-hcloud-fw/actions/workflows/codeql.yaml/badge.svg)](https://github.com/jkreileder/cf-ips-to-hcloud-fw/actions/workflows/codeql.yaml)
[![Python package](https://github.com/jkreileder/cf-ips-to-hcloud-fw/actions/workflows/python-package.yaml/badge.svg)](https://github.com/jkreileder/cf-ips-to-hcloud-fw/actions/workflows/python-package.yaml)
[![Docker build](https://github.com/jkreileder/cf-ips-to-hcloud-fw/actions/workflows/docker.yaml/badge.svg)](https://github.com/jkreileder/cf-ips-to-hcloud-fw/actions/workflows/docker.yaml)
[![PyPI - Version](https://img.shields.io/pypi/v/cf-ips-to-hcloud-fw)](https://pypi.org/project/cf-ips-to-hcloud-fw/)
[![PyPI - Python Version](https://img.shields.io/pypi/pyversions/cf-ips-to-hcloud-fw?logo=python)](https://pypi.org/project/cf-ips-to-hcloud-fw/)
This tool, `cf-ips-to-hcloud-fw`, helps you keep your Hetzner Cloud firewall
rules up-to-date with the current Cloudflare IP ranges.
## Table of Contents <!-- omit in toc -->
- [Overview](#overview)
- [Installation](#installation)
- [Using Python](#using-python)
- [Using pipx (Recommended)](#using-pipx-recommended)
- [Using pip](#using-pip)
- [Docker and Kubernetes](#docker-and-kubernetes)
- [Configuration](#configuration)
- [Preparing the Hetzner Cloud Firewall](#preparing-the-hetzner-cloud-firewall)
- [Configuring the Application](#configuring-the-application)
## Overview
`cf-ips-to-hcloud-fw` fetches the current [Cloudflare IP
ranges](https://www.cloudflare.com/ips/) and updates your Hetzner Cloud firewall
rules using the [hcloud
API](https://docs.hetzner.cloud/#firewall-actions-set-rules).
The tool specifically targets **incoming** firewall rules and **replaces** the
networks with Cloudflare networks if their description contains
`__CLOUDFLARE_IPS_V4__`, `__CLOUDFLARE_IPS_V6__` or `__CLOUDFLARE_IPS__`.
| Text in rule description | Cloudflare IP ranges |
| ------------------------ | -------------------- |
| `__CLOUDFLARE_IPS_V4__` | IPv4 only |
| `__CLOUDFLARE_IPS_V6__` | IPv6 only |
| `__CLOUDFLARE_IPS__` | IPv4 + IPv6 |
Note: Having both `__CLOUDFLARE_IPS_V4__` and `__CLOUDFLARE_IPS_V6__` in a rule
description is equivalent to having `__CLOUDFLARE_IPS__` there.
## Installation
### Using Python
To install `cf-ips-to-hcloud-fw` using Python, we recommend using
[`pipx`](https://pipx.pypa.io/). `pipx` is a tool for installing and running
Python applications in isolated environments.
#### Using pipx (Recommended)
1. Install `cf-ips-to-hcloud-fw` using pipx:
```shell
pipx install cf-ips-to-hcloud-fw
```
2. Verify the installation:
```shell
cf-ips-to-hcloud-fw -h
```
You should see the usage information for `cf-ips-to-hcloud-fw`.
To upgrade `cf-ips-to-hcloud-fw`, run:
> [!TIP]
> To upgrade `cf-ips-to-hcloud-fw`, run `pipx upgrade cf-ips-to-hcloud-fw`.
#### Using pip
We strongly recommend using a virtual environment when installing Python
packages with pip. This helps to avoid conflicts between packages and allows you
to manage packages on a per-project basis.
1. Create a virtual environment:
```shell
python3 -m venv cf-ips-to-hcloud-fw-venv
```
2. Install `cf-ips-to-hcloud-fw` into the virtual environment:
```shell
./cf-ips-to-hcloud-fw-venv/bin/pip3 install cf-ips-to-hcloud-fw
```
3. Verify the installation:
```shell
./cf-ips-to-hcloud-fw-venv/bin/cf-ips-to-hcloud-fw -h
```
You should see the usage information for `cf-ips-to-hcloud-fw`.
> [!TIP]
> To upgrade `cf-ips-to-hcloud-fw` in your virtual environment, run
> `./cf-ips-to-hcloud-fw-venv/bin/pip3 install --upgrade cf-ips-to-hcloud-fw`.
### Docker and Kubernetes
As an alternative, `cf-ips-to-hcloud-fw` can be run using Docker or a Kubernetes
CronJob. Simply mount your configuration file as `/usr/src/app/config.yaml`.
Here's an example using Docker:
```shell
docker run --rm \
--mount type=bind,source=$(pwd)/config.yaml,target=/usr/src/app/config.yaml,readonly \
jkreileder/cf-ips-to-hcloud-fw:1.0.14
```
(Add `--pull=always` if you use a rolling image tag.)
Docker images for `cf-ips-to-hcloud-fw` are available for both `linux/amd64` and
`linux/arm64` architectures. The Docker images support the following tags:
- `1`: This tag always points to the latest `1.x.x` release.
- `1.0`: This tag always points to the latest `1.0.x` release.
- `1.0.14`: This tag points to the specific `1.0.14` release.
- `main`: This tag points to the most recent development version of
`cf-ips-to-hcloud-fw`. Use this at your own risk as it may contain unstable
changes.
You can find the Docker images at:
- [Docker Hub](https://hub.docker.com/r/jkreileder/cf-ips-to-hcloud-fw)
- [Quay.io](https://quay.io/repository/jkreileder/cf-ips-to-hcloud-fw)
- [GitHub Packages](https://github.com/jkreileder/cf-ips-to-hcloud-fw/pkgs/container/cf-ips-to-hcloud-fw)
Here's an example of how to create a Kubernetes Secret for your
[configuration](#configuration):
```yaml
apiVersion: v1
kind: Secret
metadata:
name: cf-ips-to-hcloud-fw-config
type: Opaque
stringData:
config.yaml: |
- token: API_TOKEN_FOR_PROJECT_1
firewalls:
- firewall-1
- firewall-2
- token: API_TOKEN_FOR_PROJECT_2
firewalls:
- default
```
And here's an example of a Kubernetes CronJob that uses the Secret:
```yaml
apiVersion: batch/v1
kind: CronJob
metadata:
name: cf-ips-to-hcloud-fw
spec:
schedule: "0 * * * *" # Run every hour
jobTemplate:
spec:
template:
spec:
securityContext:
runAsNonRoot: true
runAsUser: 65534
containers:
- name: cf-ips-to-hcloud-fw
image: jkreileder/cf-ips-to-hcloud-fw:1.0.14
# imagePullPolicy: Always # Uncomment this if you use a rolling image tag
securityContext:
allowPrivilegeEscalation: false
readOnlyRootFilesystem: true
capabilities:
drop:
- ALL
volumeMounts:
- name: config-volume
mountPath: /usr/src/app/config.yaml
subPath: config.yaml
volumes:
- name: config-volume
secret:
secretName: cf-ips-to-hcloud-fw-config
restartPolicy: OnFailure
```
## Configuration
### Preparing the Hetzner Cloud Firewall
To prepare your Hetzner Cloud Firewall:
1. **Set the rule descriptions**: Include `__CLOUDFLARE_IPS_V4__`,
`__CLOUDFLARE_IPS_V6__`, or `__CLOUDFLARE_IPS__` in the description of any
incoming firewall rule where you want to insert Cloudflare networks. This
will be used as a marker to identify which rules should be updated with the
Cloudflare IP ranges.
2. **Generate an API token**: You'll need an API token with write permissions
for the project that contains the firewall. This token will be used to
authenticate your requests to the Hetzner Cloud API. You can generate a token
in the Hetzner Cloud Console by going to "Security" > "API Tokens" >
"Generate API Token".
### Configuring the Application
To configure the application, you'll need to create a `config.yaml` file with
your API tokens and the names of the firewalls you want to update:
```yaml
- token: API_TOKEN_FOR_PROJECT_1 # Token with read-write permissions for a Hetzner Cloud project
firewalls:
- firewall-1
- firewall-2
- token: API_TOKEN_FOR_PROJECT_2 # Token with read-write permissions for another Hetzner Cloud project
firewalls:
- default
```
Raw data
{
"_id": null,
"home_page": null,
"name": "cf-ips-to-hcloud-fw",
"maintainer": null,
"docs_url": null,
"requires_python": ">=3.9",
"maintainer_email": null,
"keywords": "cloudflare, hcloud, hetzner, firewall, cli",
"author": "J\u00fcrgen Kreileder",
"author_email": "jk@blackdown.de",
"download_url": "https://files.pythonhosted.org/packages/65/99/45d2a0dec0d4c150c08f5b9d2e92878482d0980fc69847b0644ee547f9ec/cf_ips_to_hcloud_fw-1.0.14.tar.gz",
"platform": null,
"description": "# Update Hetzner Cloud Firewall Rules with Current Cloudflare IP Ranges <!-- omit in toc -->\n\n[![codecov](https://codecov.io/gh/jkreileder/cf-ips-to-hcloud-fw/graph/badge.svg?token=PCP1F2XWAT)](https://codecov.io/gh/jkreileder/cf-ips-to-hcloud-fw)\n[![OpenSSF Best Practices](https://www.bestpractices.dev/projects/8275/badge)](https://www.bestpractices.dev/projects/8275)\n[![OpenSSF Scorecard](https://api.scorecard.dev/projects/github.com/jkreileder/cf-ips-to-hcloud-fw/badge)](https://scorecard.dev/viewer/?uri=github.com/jkreileder/cf-ips-to-hcloud-fw)\n[![CodeQL](https://github.com/jkreileder/cf-ips-to-hcloud-fw/actions/workflows/codeql.yaml/badge.svg)](https://github.com/jkreileder/cf-ips-to-hcloud-fw/actions/workflows/codeql.yaml)\n[![Python package](https://github.com/jkreileder/cf-ips-to-hcloud-fw/actions/workflows/python-package.yaml/badge.svg)](https://github.com/jkreileder/cf-ips-to-hcloud-fw/actions/workflows/python-package.yaml)\n[![Docker build](https://github.com/jkreileder/cf-ips-to-hcloud-fw/actions/workflows/docker.yaml/badge.svg)](https://github.com/jkreileder/cf-ips-to-hcloud-fw/actions/workflows/docker.yaml)\n[![PyPI - Version](https://img.shields.io/pypi/v/cf-ips-to-hcloud-fw)](https://pypi.org/project/cf-ips-to-hcloud-fw/)\n[![PyPI - Python Version](https://img.shields.io/pypi/pyversions/cf-ips-to-hcloud-fw?logo=python)](https://pypi.org/project/cf-ips-to-hcloud-fw/)\n\nThis tool, `cf-ips-to-hcloud-fw`, helps you keep your Hetzner Cloud firewall\nrules up-to-date with the current Cloudflare IP ranges.\n\n## Table of Contents <!-- omit in toc -->\n\n- [Overview](#overview)\n- [Installation](#installation)\n - [Using Python](#using-python)\n - [Using pipx (Recommended)](#using-pipx-recommended)\n - [Using pip](#using-pip)\n - [Docker and Kubernetes](#docker-and-kubernetes)\n- [Configuration](#configuration)\n - [Preparing the Hetzner Cloud Firewall](#preparing-the-hetzner-cloud-firewall)\n - [Configuring the Application](#configuring-the-application)\n\n## Overview\n\n`cf-ips-to-hcloud-fw` fetches the current [Cloudflare IP\nranges](https://www.cloudflare.com/ips/) and updates your Hetzner Cloud firewall\nrules using the [hcloud\nAPI](https://docs.hetzner.cloud/#firewall-actions-set-rules).\n\nThe tool specifically targets **incoming** firewall rules and **replaces** the\nnetworks with Cloudflare networks if their description contains\n`__CLOUDFLARE_IPS_V4__`, `__CLOUDFLARE_IPS_V6__` or `__CLOUDFLARE_IPS__`.\n\n| Text in rule description | Cloudflare IP ranges |\n| ------------------------ | -------------------- |\n| `__CLOUDFLARE_IPS_V4__` | IPv4 only |\n| `__CLOUDFLARE_IPS_V6__` | IPv6 only |\n| `__CLOUDFLARE_IPS__` | IPv4 + IPv6 |\n\nNote: Having both `__CLOUDFLARE_IPS_V4__` and `__CLOUDFLARE_IPS_V6__` in a rule\ndescription is equivalent to having `__CLOUDFLARE_IPS__` there.\n\n## Installation\n\n### Using Python\n\nTo install `cf-ips-to-hcloud-fw` using Python, we recommend using\n[`pipx`](https://pipx.pypa.io/). `pipx` is a tool for installing and running\nPython applications in isolated environments.\n\n#### Using pipx (Recommended)\n\n1. Install `cf-ips-to-hcloud-fw` using pipx:\n\n ```shell\n pipx install cf-ips-to-hcloud-fw\n ```\n\n2. Verify the installation:\n\n ```shell\n cf-ips-to-hcloud-fw -h\n ```\n\nYou should see the usage information for `cf-ips-to-hcloud-fw`.\n\nTo upgrade `cf-ips-to-hcloud-fw`, run:\n\n> [!TIP]\n> To upgrade `cf-ips-to-hcloud-fw`, run `pipx upgrade cf-ips-to-hcloud-fw`.\n\n#### Using pip\n\nWe strongly recommend using a virtual environment when installing Python\npackages with pip. This helps to avoid conflicts between packages and allows you\nto manage packages on a per-project basis.\n\n1. Create a virtual environment:\n\n ```shell\n python3 -m venv cf-ips-to-hcloud-fw-venv\n ```\n\n2. Install `cf-ips-to-hcloud-fw` into the virtual environment:\n\n ```shell\n ./cf-ips-to-hcloud-fw-venv/bin/pip3 install cf-ips-to-hcloud-fw\n ```\n\n3. Verify the installation:\n\n ```shell\n ./cf-ips-to-hcloud-fw-venv/bin/cf-ips-to-hcloud-fw -h\n ```\n\nYou should see the usage information for `cf-ips-to-hcloud-fw`.\n\n> [!TIP]\n> To upgrade `cf-ips-to-hcloud-fw` in your virtual environment, run\n> `./cf-ips-to-hcloud-fw-venv/bin/pip3 install --upgrade cf-ips-to-hcloud-fw`.\n\n### Docker and Kubernetes\n\nAs an alternative, `cf-ips-to-hcloud-fw` can be run using Docker or a Kubernetes\nCronJob. Simply mount your configuration file as `/usr/src/app/config.yaml`.\n\nHere's an example using Docker:\n\n```shell\ndocker run --rm \\\n --mount type=bind,source=$(pwd)/config.yaml,target=/usr/src/app/config.yaml,readonly \\\n jkreileder/cf-ips-to-hcloud-fw:1.0.14\n```\n\n(Add `--pull=always` if you use a rolling image tag.)\n\nDocker images for `cf-ips-to-hcloud-fw` are available for both `linux/amd64` and\n`linux/arm64` architectures. The Docker images support the following tags:\n\n- `1`: This tag always points to the latest `1.x.x` release.\n- `1.0`: This tag always points to the latest `1.0.x` release.\n- `1.0.14`: This tag points to the specific `1.0.14` release.\n- `main`: This tag points to the most recent development version of\n `cf-ips-to-hcloud-fw`. Use this at your own risk as it may contain unstable\n changes.\n\nYou can find the Docker images at:\n\n- [Docker Hub](https://hub.docker.com/r/jkreileder/cf-ips-to-hcloud-fw)\n- [Quay.io](https://quay.io/repository/jkreileder/cf-ips-to-hcloud-fw)\n- [GitHub Packages](https://github.com/jkreileder/cf-ips-to-hcloud-fw/pkgs/container/cf-ips-to-hcloud-fw)\n\nHere's an example of how to create a Kubernetes Secret for your\n[configuration](#configuration):\n\n```yaml\napiVersion: v1\nkind: Secret\nmetadata:\n name: cf-ips-to-hcloud-fw-config\ntype: Opaque\nstringData:\n config.yaml: |\n - token: API_TOKEN_FOR_PROJECT_1\n firewalls:\n - firewall-1\n - firewall-2\n - token: API_TOKEN_FOR_PROJECT_2\n firewalls:\n - default\n```\n\nAnd here's an example of a Kubernetes CronJob that uses the Secret:\n\n```yaml\napiVersion: batch/v1\nkind: CronJob\nmetadata:\n name: cf-ips-to-hcloud-fw\nspec:\n schedule: \"0 * * * *\" # Run every hour\n jobTemplate:\n spec:\n template:\n spec:\n securityContext:\n runAsNonRoot: true\n runAsUser: 65534\n containers:\n - name: cf-ips-to-hcloud-fw\n image: jkreileder/cf-ips-to-hcloud-fw:1.0.14\n # imagePullPolicy: Always # Uncomment this if you use a rolling image tag\n securityContext:\n allowPrivilegeEscalation: false\n readOnlyRootFilesystem: true\n capabilities:\n drop:\n - ALL\n volumeMounts:\n - name: config-volume\n mountPath: /usr/src/app/config.yaml\n subPath: config.yaml\n volumes:\n - name: config-volume\n secret:\n secretName: cf-ips-to-hcloud-fw-config\n restartPolicy: OnFailure\n```\n\n## Configuration\n\n### Preparing the Hetzner Cloud Firewall\n\nTo prepare your Hetzner Cloud Firewall:\n\n1. **Set the rule descriptions**: Include `__CLOUDFLARE_IPS_V4__`,\n `__CLOUDFLARE_IPS_V6__`, or `__CLOUDFLARE_IPS__` in the description of any\n incoming firewall rule where you want to insert Cloudflare networks. This\n will be used as a marker to identify which rules should be updated with the\n Cloudflare IP ranges.\n\n2. **Generate an API token**: You'll need an API token with write permissions\n for the project that contains the firewall. This token will be used to\n authenticate your requests to the Hetzner Cloud API. You can generate a token\n in the Hetzner Cloud Console by going to \"Security\" > \"API Tokens\" >\n \"Generate API Token\".\n\n### Configuring the Application\n\nTo configure the application, you'll need to create a `config.yaml` file with\nyour API tokens and the names of the firewalls you want to update:\n\n```yaml\n- token: API_TOKEN_FOR_PROJECT_1 # Token with read-write permissions for a Hetzner Cloud project\n firewalls:\n - firewall-1\n - firewall-2\n- token: API_TOKEN_FOR_PROJECT_2 # Token with read-write permissions for another Hetzner Cloud project\n firewalls:\n - default\n```\n",
"bugtrack_url": null,
"license": "MIT",
"summary": "Update Hetzner Cloud firewall rules with Cloudflare IP ranges",
"version": "1.0.14",
"project_urls": {
"Bluesky": "https://bsky.app/profile/jk.blackdown.de",
"Changelog": "https://github.com/jkreileder/cf-ips-to-hcloud-fw/blob/main/CHANGELOG.md",
"Documentation": "https://github.com/jkreileder/cf-ips-to-hcloud-fw",
"Homepage": "https://github.com/jkreileder/cf-ips-to-hcloud-fw",
"Issues": "https://github.com/jkreileder/cf-ips-to-hcloud-fw/issues",
"PyPI": "https://pypi.org/project/cf-ips-to-hcloud-fw/",
"Source": "https://github.com/jkreileder/cf-ips-to-hcloud-fw",
"Twitter": "https://twitter/jkreileder"
},
"split_keywords": [
"cloudflare",
" hcloud",
" hetzner",
" firewall",
" cli"
],
"urls": [
{
"comment_text": "",
"digests": {
"blake2b_256": "fa69e95572f966344525cb6578ef10b7fba2bf6f059782523047673bbb987c3e",
"md5": "8d0c835e0595f0a9811afb783a0725b3",
"sha256": "62c31228f587904618791d90db24ec7beeaccff87d55cc1aa8f96322900edc24"
},
"downloads": -1,
"filename": "cf_ips_to_hcloud_fw-1.0.14-py3-none-any.whl",
"has_sig": false,
"md5_digest": "8d0c835e0595f0a9811afb783a0725b3",
"packagetype": "bdist_wheel",
"python_version": "py3",
"requires_python": ">=3.9",
"size": 10433,
"upload_time": "2024-11-07T18:04:14",
"upload_time_iso_8601": "2024-11-07T18:04:14.084055Z",
"url": "https://files.pythonhosted.org/packages/fa/69/e95572f966344525cb6578ef10b7fba2bf6f059782523047673bbb987c3e/cf_ips_to_hcloud_fw-1.0.14-py3-none-any.whl",
"yanked": false,
"yanked_reason": null
},
{
"comment_text": "",
"digests": {
"blake2b_256": "659945d2a0dec0d4c150c08f5b9d2e92878482d0980fc69847b0644ee547f9ec",
"md5": "0623df80285a4b3ac1d9ff4a3c467009",
"sha256": "69a1ead5aa6f593302dec7333881dbe3e679bc0ee71c8bc1025b5f06f21e090d"
},
"downloads": -1,
"filename": "cf_ips_to_hcloud_fw-1.0.14.tar.gz",
"has_sig": false,
"md5_digest": "0623df80285a4b3ac1d9ff4a3c467009",
"packagetype": "sdist",
"python_version": "source",
"requires_python": ">=3.9",
"size": 16355,
"upload_time": "2024-11-07T18:04:16",
"upload_time_iso_8601": "2024-11-07T18:04:16.231384Z",
"url": "https://files.pythonhosted.org/packages/65/99/45d2a0dec0d4c150c08f5b9d2e92878482d0980fc69847b0644ee547f9ec/cf_ips_to_hcloud_fw-1.0.14.tar.gz",
"yanked": false,
"yanked_reason": null
}
],
"upload_time": "2024-11-07 18:04:16",
"github": true,
"gitlab": false,
"bitbucket": false,
"codeberg": false,
"github_user": "jkreileder",
"github_project": "cf-ips-to-hcloud-fw",
"travis_ci": false,
"coveralls": false,
"github_actions": true,
"requirements": [],
"lcname": "cf-ips-to-hcloud-fw"
}