Windmillは、スクリプトをWebhook、ワークフロー、cronジョブ、社内向けUIに変えます。RetoolとTemporalのオープンソース代替です。セルフホスト自体は素直ですが、始める前に知っておくべき点が1つあります。Redisは使いません。Web上の少なからぬガイドがそう書いているにもかかわらず、です。
Windmillをセルフホストする理由
クラウド版はユーザー単位と実行回数単位の両方で課金されます。セルフホストすれば両方のメーターが止まります。自動化プラットフォームではこれが効いてきます。定期実行したいジョブこそ、まさに実行課金を積み上げるものだからです。さらに、スクリプト、資格情報、ジョブのログが自分のマシンに残ります。そのスクリプトは、あなたが動かしている他のあらゆるもののAPIキーを日常的に抱えています。
コミュニティ版はAGPL-3.0です。エンタープライズ版はライセンスキーと別のイメージタグの先にありますが、プラットフォームを動かすだけなら必要ありません。
適切なVPSを選ぶ
Windmillはアプリケーション単位ではなくワーカー単位でサイジングします。目安はvCPU1つにつきワーカー1つ、それぞれに1〜2GBのRAM、加えてPostgresとサーバープロセスの分です。
| プロバイダー | プラン | vCPU / RAM / ディスク | 価格 | 補足 | リンク |
|---|---|---|---|---|---|
| Contabo | Cloud VPS 4 | 4 / 8GB / 100GB SSD | 5.50 EUR/月(税別) | 4コアはワーカー4つ分の並列性 | Contabo |
| Hetzner Cloud | CX23 | 2 / 4GB / 40GB NVMe | 5.49 EUR/月(税別) | 標準のワーカー2つ構成に収まる | Hetzner |
| DigitalOcean | Basic 4GB | 2 / 4GB / 80GB SSD | 24 USD/月 | CX23と同スペックで価格は4倍 | DigitalOcean |
| Vultr | Regular 4GB | 2 / 4GB / 80GB SSD | 20 USD/月 | リージョンの選択肢が最も広い | Vultr |
| Linode | Linode 4GB | 2 / 4GB / 80GB SSD | 24 USD/月 | 性能が安定している | Linode |
処理量はワーカー数に比例するため、ここではクロック周波数よりコア数が重要です。詳しい比較はVPS比較の全体版をご覧ください。
前提条件
- 2 vCPUと4GB RAM以上を備え、Ubuntu 24.04 LTSが動くVPS
- Docker EngineとCompose v2
- TLSを使うならサーバーを指すドメイン
手順1:VPSを準備する
接続して更新します。
ssh root@your-vps-ip
apt update && apt upgrade -y
DockerとComposeプラグインをインストールします。
apt install -y docker.io docker-compose-v2
systemctl enable --now docker
docker compose version
Caddyが使うポートを開けます。
ufw allow OpenSSH && ufw allow 80 && ufw allow 443
ufw enable
手順2:公式のcompose構成を取得する
Windmillのcomposeファイルを手書きしないでください。プロジェクトが公開しているものが、ワーカー、インデクサー、言語サーバーを正しく結線してくれます。
mkdir -p ~/windmill && cd ~/windmill
curl -fsSL -o docker-compose.yml https://raw.githubusercontent.com/windmill-labs/windmill/main/docker-compose.yml
curl -fsSL -o .env https://raw.githubusercontent.com/windmill-labs/windmill/main/.env
curl -fsSL -o Caddyfile https://raw.githubusercontent.com/windmill-labs/windmill/main/Caddyfile
いま取得した構成は7つのサービスを動かします。
db-postgres:16、データベース兼ジョブキューwindmill_server- ポート8000のAPIとWeb UIwindmill_worker- ジョブを実行するwindmill_worker_native- 軽量ジョブ、約0.1 CPUと128MBwindmill_indexer- ジョブ履歴の全文検索windmill_extra- ブラウザ内エディタを支える言語サーバーcaddy- ポート80のリバースプロキシ
この一覧にRedisはありませんし、あなたの構成にも入れる必要はありません。
手順3:パスワードとドメインを設定する
配布されている.envには、意図的に弱い既定値が入っています。
DATABASE_URL=postgres://postgres:changeme@db/windmill?sslmode=disable
WM_IMAGE=ghcr.io/windmill-labs/windmill:main
データベースは初回起動時に作成されるため、その前にchangemeを生成した秘密の値へ変更してください。
openssl rand -hex 24
同じファイルでBASE_URLを自分のドメインに設定します。Caddyはこれを読んで証明書を要求します。
手順4:起動する
docker compose up -d
docker compose ps
初回起動では複数のイメージを取得し、データベースのマイグレーションを実行するので、1分ほど待ってください。ドメインを開いて最初のアカウントを作成すると、それがインスタンスのスーパー管理者になります。
手順5:必要に応じてワーカーを増やす
ここがWindmillを多くのセルフホストアプリと分ける部分です。1つのプロセスを大きくするのではなく、ワーカーのコンテナを増やしてスケールします。docker-compose.ymlのwindmill_workerブロックをコピーし、新しいサービス名を付け、DATABASE_URLとMODE=workerはそのままにして適用します。
docker compose up -d
ワーカーはPostgres経由で協調するため、他の設定変更は要りません。1つにつきおよそ1 vCPUと1〜2GBのRAMを見込んでください。
手順6:データベースをバックアップする
重要なものはすべて、つまりスクリプト、フロー、スケジュール、リソース、ジョブ履歴はPostgresに入っています。依存キャッシュのボリュームは派生データで、必要になれば作り直されます。
docker compose exec db pg_dump -U postgres windmill | gzip > windmill-$(date +%F).sql.gz
サーバーの外へコピーしてください。Windmillは他システムの資格情報を保持するので、そのダンプは機密として扱い、保存時に暗号化してください。
つまずきやすい点
ブログからRedis入りのcomposeファイルを写す。 Windmillにそれが必要だったことは一度もありません。コンテナは起動して何もせずに待機し、その横であなたはキューがなぜそれを使わないのかと悩むことになります。
定常状態でサイジングする。 メモリのピークは依存関係のインストールで訪れます。pandasを取り込むPythonジョブは、初回だけ以降の実行よりはるかに多くのRAMを必要とします。アイドル時に問題なく見える構成が、コールドなジョブで落ちるのはこのためです。
changemeをそのままにする。 これは公開されている.envのPostgresパスワードであり、5432番をうっかり外部へ晒したときに、無差別なスキャンが最初に試す値です。
Windmillは速いコアより多いコアを評価します。安価な欧州の多コアプランがこの用途で際立って良い選択肢になるのはそのためです。同時に走らせたいジョブの数に合わせてサイジングし、Postgresのダンプを暗号化した場所に置いておけば、あとは付き合いやすいサービスです。
他のセルフホスト向けプロジェクトやヒントは、awesome-selfhostedのリストやr/selfhostedコミュニティをご覧ください。
Frequently asked questions
WindmillをセルフホストするのにRedisは必要ですか?
必要ありません。そしてこれが多くの人のつまずきどころです。WindmillはPostgreSQLをデータベースとジョブキューの両方として使うため、公式のcomposeファイルにRedisサービスもREDIS_URL変数も存在しません。それでも第三者のガイドのいくつかは追加しています。Redisコンテナ入りのcomposeファイルを写したのなら、Windmillが一度も接続しないサービスを動かしていることになり、安全に削除できます。
稼働中のWindmillにワーカーを追加するには?
同じDATABASE_URLを指しMODE=workerを持つwindmill_workerサービスをcomposeファイルにもう1つ追加し、docker compose up -dを実行します。ワーカーはPostgres経由で協調するため、他に設定を変える必要はありません。実際の上限はコア数です。標準ワーカーは一度に1つのジョブを実行し、およそ1 vCPUと1〜2GBのRAMを求めます。
WindmillをHTTPSの背後に置くには?
この構成にはCaddyが同梱されており、既定ではポート80で平文のHTTPを提供します。自動TLSを有効にするには、BASE_URLを自分のドメインに設定し、配布されている.envのコメントが説明しているとおりCaddyfileとcaddyサービスを443番を公開するよう編集します。初回起動時に証明書を発行できるよう、起動前にDNSをサーバーへ向けておいてください。