انتقل إلى المحتوى الرئيسي
العودة إلى الفئة

إعداد خادم ويب Caddy: HTTPS تلقائي وبروكسي عكسي

تثبيت خادم ويب Caddy، تكوين Caddyfile، SSL تلقائي من Let's Encrypt، بروكسي عكسي، استضافة المواقع الثابتة، تكامل PHP-FPM وإعدادات الأداء.

وقت القراءة: 14 دقيقة DevOps والأتمتة
caddyخادم ويبhttpssslبروكسي عكسيlet's encryptdevops

جدول المحتويات

إعداد خادم ويب Caddy: HTTPS تلقائي وبروكسي عكسي

Caddy خادم ويب حديث يتميز بإدارة شهادات HTTPS التلقائية. بفضل تكامله مع Let's Encrypt، يحصل على شهادات SSL ويجددها ويكوّنها تلقائياً.

ما هو Caddy؟

الميزات البارزة لـ Caddy:

  • HTTPS تلقائي: إدارة الشهادات مع Let's Encrypt تلقائية بالكامل
  • تكوين بسيط: صيغة Caddyfile سهلة القراءة
  • HTTP/2 وHTTP/3: مفعّلان افتراضياً
  • بروكسي عكسي: موازنة تحميل مدمجة وفحوصات صحة
  • إعادة تحميل بدون توقف: لا انقطاع عند تغيير التكوين

يتطلب Caddy صلاحيات root لاستخدام المنفذين 80 و443. يُدار هذا تلقائياً عند التشغيل كخدمة systemd.

تثبيت Caddy

التثبيت عبر apt (Ubuntu/Debian)

hljs bash
# إضافة مفتاح GPG ومستودع Caddy
sudo apt install -y debian-keyring debian-archive-keyring apt-transport-https curl
curl -1sLf 'https://dl.cloudsmith.io/public/caddy/stable/gpg.key' | sudo gpg --dearmor -o /usr/share/keyrings/caddy-stable-archive-keyring.gpg
curl -1sLf 'https://dl.cloudsmith.io/public/caddy/stable/debian.deb.txt' | sudo tee /etc/apt/sources.list.d/caddy-stable.list

# تثبيت Caddy
sudo apt update
sudo apt install caddy -y

# التحقق من حالة الخدمة
sudo systemctl status caddy

تثبيت الملف الثنائي

hljs bash
# تنزيل أحدث إصدار
VERSION=$(curl -s https://api.github.com/repos/caddyserver/caddy/releases/latest | grep tag_name | cut -d '"' -f 4)
curl -L "https://github.com/caddyserver/caddy/releases/download/${VERSION}/caddy_${VERSION#v}_linux_amd64.tar.gz" -o caddy.tar.gz

# فك الضغط والتثبيت
tar -xzf caddy.tar.gz
sudo mv caddy /usr/local/bin/
sudo chmod +x /usr/local/bin/caddy

# التحقق من الإصدار
caddy version

بناء مخصص مع xcaddy

hljs bash
# تثبيت xcaddy
go install github.com/caddyserver/xcaddy/cmd/xcaddy@latest

# البناء مع وحدات إضافية
xcaddy build \
  --with github.com/caddy-dns/cloudflare \
  --with github.com/greenpau/caddy-security

صيغة Caddyfile

الهيكل الأساسي

hljs caddyfile
# موقع واحد
example.com {
    root * /var/www/html
    file_server
}

# مواقع متعددة
example.com {
    respond "مرحباً example.com!"
}

api.example.com {
    reverse_proxy localhost:3000
}

الخيارات العامة

hljs caddyfile
# الإعدادات العامة في بداية Caddyfile
{
    # منفذ Admin API
    admin localhost:2019

    # البريد الإلكتروني (لـ Let's Encrypt)
    email admin@example.com

    # خادم ACME (staging للاختبار)
    # acme_ca https://acme-staging-v02.api.letsencrypt.org/directory

    # منفذ HTTP
    http_port 80

    # منفذ HTTPS
    https_port 443

    # تنسيق السجل
    log {
        output file /var/log/caddy/access.log
        format json
    }
}

HTTPS التلقائي

يحصل Caddy تلقائياً على شهادة Let's Encrypt لنطاقك:

hljs caddyfile
# فقط اكتب اسم النطاق - HTTPS تلقائي!
example.com {
    root * /var/www/html
    file_server
    encode gzip
}

# إعادة توجيه www
www.example.com {
    redir https://example.com{uri} permanent
}

# شهادة Wildcard (تتطلب DNS challenge)
*.example.com {
    tls {
        dns cloudflare {env.CLOUDFLARE_API_TOKEN}
    }
    @api host api.example.com
    handle @api {
        reverse_proxy localhost:3000
    }
}

يجدد Caddy الشهادات تلقائياً. لا يلزم تدخل يدوي. تُخزَّن الشهادات في ~/.local/share/caddy/ أو /var/lib/caddy/.

تكوين البروكسي العكسي

بروكسي عكسي أساسي

hljs caddyfile
app.example.com {
    reverse_proxy localhost:3000
}

# عدة upstreams (موازنة التحميل)
api.example.com {
    reverse_proxy {
        to localhost:3001 localhost:3002 localhost:3003
        lb_policy round_robin
        health_uri /health
        health_interval 30s
        health_timeout 5s
    }
}

بروكسي عكسي متقدم

hljs caddyfile
app.example.com {
    reverse_proxy localhost:3000 {
        # إعادة توجيه الترويسات
        header_up Host {upstream_hostport}
        header_up X-Real-IP {remote_host}
        header_up X-Forwarded-For {remote_host}
        header_up X-Forwarded-Proto {scheme}

        # المهل الزمنية
        transport http {
            dial_timeout 5s
            response_header_timeout 30s
        }

        # إعادة المحاولة
        lb_retries 3
        lb_try_duration 5s
    }

    # ترويسات الأمان
    header {
        Strict-Transport-Security "max-age=31536000; includeSubDomains; preload"
        X-Content-Type-Options nosniff
        X-Frame-Options DENY
        Referrer-Policy strict-origin-when-cross-origin
        -Server
    }
}

تقديم الملفات الثابتة

hljs caddyfile
static.example.com {
    root * /var/www/static
    file_server {
        # قائمة المجلدات
        browse
        # إخفاء الملفات المخفية
        hide .git .env
    }
    encode gzip zstd

    # ترويسات التخزين المؤقت
    header /assets/* Cache-Control "public, max-age=31536000, immutable"
    header /*.html Cache-Control "no-cache"

    # صفحات الخطأ
    handle_errors {
        rewrite * /errors/{err.status_code}.html
        file_server
    }
}

# SPA (تطبيق صفحة واحدة)
app.example.com {
    root * /var/www/app
    encode gzip
    try_files {path} /index.html
    file_server
}

تكامل PHP-FPM

hljs caddyfile
php.example.com {
    root * /var/www/php
    encode gzip

    # توجيه ملفات PHP إلى PHP-FPM
    php_fastcgi unix//run/php/php8.2-fpm.sock

    # أو عبر TCP
    # php_fastcgi localhost:9000

    file_server

    # لـ WordPress
    @notStatic {
        not path /wp-content/* /wp-includes/*
        not file
    }
    rewrite @notStatic /index.php
}

Caddy مع Docker

hljs yaml
# docker-compose.yml
services:
  caddy:
    image: caddy:2-alpine
    restart: unless-stopped
    ports:
      - "80:80"
      - "443:443"
      - "443:443/udp"  # HTTP/3
    volumes:
      - ./Caddyfile:/etc/caddy/Caddyfile:ro
      - caddy_data:/data
      - caddy_config:/config
      - ./html:/var/www/html:ro
    environment:
      - CLOUDFLARE_API_TOKEN=${CLOUDFLARE_API_TOKEN}

  app:
    build: ./app
    expose:
      - "3000"

volumes:
  caddy_data:
  caddy_config:
hljs caddyfile
# Docker Caddyfile
example.com {
    reverse_proxy app:3000
}

الإدارة عبر API

يدعم Caddy التكوين الديناميكي عبر REST API:

hljs bash
# عرض التكوين الحالي
curl http://localhost:2019/config/

# تحديث التكوين
curl -X POST http://localhost:2019/load \
  -H "Content-Type: application/json" \
  -d @caddy.json

# إعادة تحميل Caddy (بدون توقف)
caddy reload --config /etc/caddy/Caddyfile

# التحقق من التكوين
caddy validate --config /etc/caddy/Caddyfile

# تنسيق Caddyfile
caddy fmt --overwrite /etc/caddy/Caddyfile

إعدادات الأداء

hljs caddyfile
{
    servers {
        max_header_size 1MB
        timeouts {
            read_body 10s
            read_header 10s
            write 30s
            idle 2m
        }
    }
}

example.com {
    # الضغط
    encode {
        gzip 6
        zstd
        minimum_length 1024
    }

    reverse_proxy localhost:3000
}

الخلاصة

يلبي Caddy متطلبات خادم الويب الحديث بإدارة HTTPS التلقائية والتكوين البسيط. يتطلب تكويناً أقل بكثير مقارنة بـ Nginx أو Apache مع تقديم جميع الميزات اللازمة لبيئات الإنتاج. إنه الخيار المثالي خاصة لمن يريد أتمتة إدارة شهادات Let's Encrypt.