Code Monkey home page Code Monkey logo

caddy-reverse-proxy-cloudflare's Introduction

cloudflared pull pull contributions welcome

Caddy reverse proxy with cloudflare plugin

Table of Contents
  1. About The Project
  2. Getting Started
  3. Usage
  4. License
  5. Contact
  6. Acknowledgements

About The Project

This docker image is based on work from @lucaslorentz which I included the plugin Cloudflare.

This is only difference between this one and his image.

๐Ÿ“” If you need more details about how to use this image I will advise you to go to his GitHub and review the documentation.

It is useful if you are planning to use the reverse proxy from โ„ข๏ธ Caddy together with Let's Encrypt and Cloudflare DNS as a challenge.

The main purpose of creating this image is to have DNS challenge for wildcard domains.

I am using GitHub Actions where it will update weekly docker image and both plugins.

It also can keep the IP address up to date thanks to Caddy DynamicDNS.

โ‰๏ธ Note: you will need the scoped API token for this setup. Please analyze this link.

Getting Started

๐Ÿ”ฐ It will work on any Linux box amd64 or Raspberry Pi with arm64 or arm32.

Prerequisites

Made with Docker !

You will need to have:

Usage

Docker Compose

โš ๏ธ You will have to use labels in docker-compose deployment. Please review below what it means each label. โฌ‡๏ธ

You will tell โ„ข๏ธ Caddy where it has to route traffic in docker network, as โ„ข๏ธ Caddy is ingress on this case.

โฌ‡๏ธ A simple docker-compose.yml:

version: "3.3"

services:
  caddy:
    container_name: caddy
    image: homeall/caddy-reverse-proxy-cloudflare:latest
    restart: unless-stopped
    environment:
      TZ: 'Europe/London'
    volumes:
      - "/var/run/docker.sock:/var/run/docker.sock" #### needs socket to read events
      - "./caddy-data:/data" #### needs volume to back up certificates
    ports:
      - "80:80"
      - "443:443"
    labels: # Global options
      caddy.email: [email protected] #### needs for acme CERT registration account

  whoami0:
    container_name: whoiam
    image: jwilder/whoami:latest
    hostname: TheDocker ############################----->>Expected result using curl
    restart: unless-stopped
    labels:
      caddy: your.example.com #### needs for caddy to redirect traffic
      # caddy.servers.protocols: "experimental_http3" #### For HTTP/3
      # caddy.tls.ca: "https://acme.zerossl.com/v2/DV90" ### Only if you will prefer ZeroSSL. Default it is Let's Encypt.
      caddy.reverse_proxy: "{{upstreams 8000}}" #### needs to tell caddy which port number should send traffic
      caddy.tls.protocols: "tls1.3" #### This is optional. Default it is tls1.2
      caddy.tls.ca: "https://acme-staging-v02.api.letsencrypt.org/directory" # Needs only for testing purpose. Remove this line after you finished your tests.
      caddy.tls.dns: "cloudflare $API-TOKEN" #### You will have to replace here $API-TOKEN with your real scoped API token from Cloudflare.

Please get your scoped API-Token from here.

โฌ†๏ธ Go on TOP โ˜๏ธ

Testing

โฌ‡๏ธ Your can run the following command to see that is working:

$  curl --insecure -vvI https://test.ionut.vip 2>&1 | awk 'BEGIN { cert=0 } /^\* Server certificate:/ { cert=1 } /^\*/ { if (cert) print }'
* Server certificate:
*  subject: CN=test.ionut.vip ################################ CA from Let's Enctrypt Staging 
*  start date: Jan  5 15:15:00 2021 GMT
*  expire date: Apr  5 15:15:00 2021 GMT
*  issuer: CN=Fake LE Intermediate X1 ######################## This is telling you that acme is working as expected!
*  SSL certificate verify result: unable to get local issuer certificate (20), continuing anyway.
* Using HTTP2, server supports multi-use
* Connection state changed (HTTP/2 confirmed)
* Copying HTTP/2 data in stream buffer to connection buffer after upgrade: len=0
* Using Stream ID: 1 (easy handle 0x7fc02180ec00)
* TLSv1.3 (IN), TLS handshake, Newsession Ticket (4):
* Connection state changed (MAX_CONCURRENT_STREAMS == 250)!
$  curl -k https://test.ionut.vip
I'm TheDocker################################### Expected result from hostname above

โ™ฅ๏ธ On the status column of the docker, you will notice the healthy word. This is telling you that docker is running healtcheck itself in order to make sure it is working properly.

โฌ‡๏ธ Please test yourself using the following command:

โฏ docker inspect --format "{{json .State.Health }}" caddy | jq
{
  "Status": "healthy",
  "FailingStreak": 0,
  "Log": [
    {
      "Start": "2021-01-04T11:10:49.2975799Z",
      "End": "2021-01-04T11:10:49.3836437Z",
      "ExitCode": 0,
      "Output": ""
    }
  ]
}

License

๐Ÿ—ž๏ธ Distributed under the MIT license. See LICENSE for more information.

Contact

๐Ÿ”ด Please free to open a ticket on Github.

Acknowledgements

โฌ†๏ธ Go on TOP โ˜๏ธ

caddy-reverse-proxy-cloudflare's People

Contributors

dependabot[bot] avatar ionutz89 avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar

caddy-reverse-proxy-cloudflare's Issues

Can we have bash into this container?

It is my understanding that the base caddy image includes bash for troubleshooting via curl commands. Can this be included in this image? It makes it very challenging to debug issues without this functionality.

docker exec -it <container> bash

docker exec -it caddy bash
OCI runtime exec failed: exec failed: unable to start container process: exec: "bash": executable file not found in $PATH: unknown

Caddyfile

Is it possible to simultaneously use this and an explicit Caddyfile?

logger flooding

Hi there, I keep getting flooded with logs such as:

{"level":"info","ts":1682275271.4406505,"logger":"admin.api","msg":"received request","method":"GET","host":"127.0.0.1:2019","uri":"/config","remote_ip":"127.0.0.1","remote_port":"51052","headers":{"Accept":["*/*"],"User-Agent":["curl/8.0.1"]}}

is this normal? Is there a way to suppress these?

Caddyfile directives volume mapping

I would like to use my own caddyfile directive without labels for services that live on another docker host that are not tied to an existing container where caddy is running. It does not appear to be getting picked up. What is the correct volume mapping?

Volumes:
  - /share/docker/appdata/caddy/data/Caddyfile:/etc/caddy/Caddyfile

Versioned Docker Image Tags

I've noticed that in Docker Hub there are no tags for the Docker Images. It would be great to be able to pin a deployment to a specific version instead of using latest.

Thanks in advance

Redirect loop when using "Cloudflare SSL/TLS encryption mode is Flexible"

When CF encyrption mode is set to flexible, when a request hits CF and it's proxied there, then CF will send the request to the upstream unencrypted. The Caddy reverse proxy will then redir the request to port 443. So the HTTP response never makes it back to the CF server and it throws a "308 redirect too many times" error.

I found that I could use an API call to edit the Caddy config and change "listen" from ":443" to ":80", ":443" so that the reverse would no longer force the redirect. Unfortunately (1) as soon as something happens it rewrites the file and (2) this affects ALL sites on the proxy not just the one I want to modify.

I need a way to tell the proxy to stop doing the 80->443 redirect for this one site.

Is there already a way to do this?

I have disabled the proxy/https thing on Cloudflare because it's probably more important for me to have end-to-end encyrption than to have caching and IP hiding at Cloudflare?

YML example with defined networks

Looking for an example of a docker compose file that shows which networks need to be defined. Or do you need to define any to use this container?

{"level":"error","ts":1644178009.2990136,"logger":"docker-proxy","msg":"Failed to get ingress networks","error":"Cannot find container id in cgroups: 0::/\n"}

{"level":"info","ts":1644178009.386654,"logger":"docker-proxy","msg":"Skipping default Caddyfile because no path is set"}

{"level":"info","ts":1644178014.2153318,"logger":"admin.api","msg":"received request","method":"GET","host":"127.0.0.1:2019","uri":"/config","remote_addr":"127.0.0.1:60384","headers":{"Accept":

If deploying in a swarm, what options would need to be configured?

Getting the Real client IP from a remote session

Greetings I'm using caddy reverse proxy for Plex remote access, everything works but I'm not getting a real client IP for remote clients. All traffic appears using the local caddy IP. I'm using Cloudflare for DNS without proxy to host the domain. As I understand it caddy should get the real IP from my remote clients by default without any additional configs. The host is a QNAP on IP 192.X.X.10, reverse_proxy is a bridge device network 172.X.X.0/24 which houses both caddy and plex container.

All my streams local or remote are showing the 172.x.x.3 IP. Any ideas on what to look at?

Network:

networks:
  reverse_proxy:
    external: true

Caddy service:

  caddy:
    image: homeall/caddy-reverse-proxy-cloudflare:latest
    container_name: caddy
    restart: always
    networks:
      reverse_proxy:
        ipv4_address: 172.X.X.3
    ports:
      - 4480:80
      - 4443:443
    volumes:
      - /var/run/docker.sock:/var/run/docker.sock
      - ${APPDATA}/caddy/data/Caddyfile:/data/Caddyfile:rw
      - ${APPDATA}/caddy/data:/data:rw
    labels: 
      caddy.email: [email protected] #### needs for acme CERT registration account

Plex service:

  plex:
    container_name: plex
    networks:
      reverse_proxy:
        ipv4_address: 172.X.X.6
    ports: 
     - "32400:32400" 
    image: linuxserver/plex:latest
    restart: always
    environment:
      - TZ=${TZ}
      - PUID=${PUID}
      - PGID=${PGID}
      - PLEX_CLAIM=${PLEX_CLAIM}
    devices:
      - /dev/dri:/dev/dri
    volumes:
      - ${APPDATA}/plex:/config
      - ${APPDATA}/plex/transcode:/transcode
      - ${MEDIA}:/data/media
      - ${EXT_MEDIA}:/external/data/media
    labels:
      caddy: plex.********.com
      caddy.reverse_proxy: "{{upstreams 32400}}"
      caddy.tls.dns: "cloudflare ${CF_API_TOKEN}"
      caddy.tls.resolvers: "1.1.1.1"

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.