Nginx config translation help

Hi,

I would like help on translating the Nginx config for Pterodactyl into a Caddy config.

I am trying to translate it the Nginx config for Pterodactyl into a Caddyfile by learning from the docs, but it turns out that there are certain elements in the Nginx config that can only be done in the JSON format of Caddy configs instead of a Caddyfile, which is where it got too complex for my level. The Nginx adapter for Caddy also doesn’t support some of the elements from the Nginx config.

Therefore, could anyone help me translate this Nginx config below into a Caddy config? I am using the latest release of Caddy on Debian 10 as TaaS.

server_tokens off;

server {
    listen 80;
    server_name <domain>;
    return 301 https://$server_name$request_uri;
}

server {
    listen 443 ssl http2;
    server_name <domain>;

    root /var/www/pterodactyl/public;
    index index.php;

    access_log /var/log/nginx/pterodactyl.app-access.log;
    error_log  /var/log/nginx/pterodactyl.app-error.log error;

    # allow larger file uploads and longer script runtimes
    client_max_body_size 100m;
    client_body_timeout 120s;

    sendfile off;

    # SSL Configuration
    ssl_certificate /etc/letsencrypt/live/<domain>/fullchain.pem;
    ssl_certificate_key /etc/letsencrypt/live/<domain>/privkey.pem;
    ssl_session_cache shared:SSL:10m;
    ssl_protocols TLSv1.2;
    ssl_ciphers 'ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-CHACHA20-POLY1305:ECDHE-RSA-CHACHA20-POLY1305:ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES256-SHA384:ECDHE-RSA-AES256-SHA384:ECDHE-ECDSA-AES128-SHA256:ECDHE-RSA-AES128-SHA256';
    ssl_prefer_server_ciphers on;

    # See https://hstspreload.org/ before uncommenting the line below.
    # add_header Strict-Transport-Security "max-age=15768000; preload;";
    add_header X-Content-Type-Options nosniff;
    add_header X-XSS-Protection "1; mode=block";
    add_header X-Robots-Tag none;
    add_header Content-Security-Policy "frame-ancestors 'self'";
    add_header X-Frame-Options DENY;
    add_header Referrer-Policy same-origin;

    location / {
        try_files $uri $uri/ /index.php?$query_string;
    }

    location ~ \.php$ {
        fastcgi_split_path_info ^(.+\.php)(/.+)$;
        fastcgi_pass unix:/run/php/php7.2-fpm.sock;
        fastcgi_index index.php;
        include fastcgi_params;
        fastcgi_param PHP_VALUE "upload_max_filesize = 100M \n post_max_size=100M";
        fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
        fastcgi_param HTTP_PROXY "";
        fastcgi_intercept_errors off;
        fastcgi_buffer_size 16k;
        fastcgi_buffers 4 16k;
        fastcgi_connect_timeout 300;
        fastcgi_send_timeout 300;
        fastcgi_read_timeout 300;
        include /etc/nginx/fastcgi_params;
    }

    location ~ /\.ht {
        deny all;
    }
}

Edit: I would also like to try out CertMagic in the config, instead of seperately generating one from acme.sh.

I would highly appreciate any help. Thanks.

What was your Caddyfile so far? We can help you go from there.

Which ones?

I’m also not seeing, at a quick glance, anything that Caddy won’t be able to achieve quite simply.

Here’s my Caddyfile so far:

{
	email {env.ACME_EMAIL}
}

tls {
	protocols tls1.2 tls1.2
	dns cloudflare {env.CLOUDFLARE_API_TOKEN}
}

{env.FQDN} {
	root * /var/www/pterodactyl/public;
	php_fastcgi unix//run/php/php-7.3-fpm.sock
}

As you can see, it’s still very limited compared to the Nginx one. There are also a lot of things I couldn’t find in the docs.

The Nginx adapter only supports the commonly used directives.

I know, I was just suggesting that I need help with the JSON config, as it seems like a Caddyfile can’t do a lot of the things in the Nginx config.

That’s a pretty good start! I think you can get a bit closer:

{
	email {env.ACME_EMAIL}
}

{env.FQDN} {
	root * /var/www/pterodactyl/public

	tls {
		dns cloudflare {env.CLOUDFLARE_API_TOKEN}
	}

	header {
		X-Content-Type-Options nosniff
		X-XSS-Protection "1; mode=block"
		X-Robots-Tag none
		Content-Security-Policy "frame-ancestors 'self'"
		X-Frame-Options DENY
		Referrer-Policy same-origin
	}

	@htFiles {
		path_regexp /\.ht
	}
	respond @htFiles 403

	php_fastcgi unix//run/php/php-7.3-fpm.sock

	file_server
}

That should be all you need! Many of the things you’d normally configure in Nginx are done for you automatically in Caddy.

Since it looks like you want to use the DNS plugin, don’t forget to compile Caddy with the Cloudflare DNS plugin!

4 Likes

Wow, thanks a lot! I must’ve been blind because I wasn’t able able to differentiate between things like header and add_header in the configs and docs. So I assumed that I had to read on the full JSON config to get such features. It turns out that Caddyfiles are more powerful than I thought!

1 Like

Heh, yeah. That’s what I’d intended to say - perhaps it was ambiguous to say “Caddy” instead of “the Caddyfile”, but the truth is the Caddyfile will handle everything needed for 99/100 people :joy:

2 Likes

I just tried this config, and there is this weird issue where it shows the Caddy page when I first visit the website, but when I refresh it it prompts me to download .dms. I tried restarting Caddy and the server. How could I solve this? You can see it at burnodactyl.marwanamireh.me.

I get a 502 Bad Gateway, meaning that Caddy isn’t able to connect to or communicate with the fastcgi backend…

I’m not sure if there’s an issue with the translation or something, but every time I visit the website, I just get prompted download a .DMS file with my domain name instead of viewing anything. I never got it working. It doesn’t happen when using the Nginx config I posted.

I’ve never heard of .dms files.

You’ll need to elaborate, I don’t think it’s clear what the problem is. What’s your full config? What do you see in your logs? What does a request look like? Can you try with curl -v to see what the request/response looks like when outside of a browser?

This topic was automatically closed 30 days after the last reply. New replies are no longer allowed.