Should `enforce_origin` and `origins` work over the unix socket?

1. Caddy version (caddy version):

v2.5.0 h1:eRHzZ4l3X6Ag3kUt8nj5IxATprhqKq/wToP7OHlXWA0=

Given “v2.5.0 h1:eRHzZ4l3X6Ag3kUt8nj5IxATprhqKq/wToP7OHlXWA0=” and the Caddyfile:

{
        admin unix//tmp/http.sock {
            # origins configures the list of remotes/origins that are allowed to connect to the endpoint.
            # origins "http://localhost:2019"
            origins "unixsocket"  # https://github.com/caddyserver/caddy/commit/c2327161f725c820826587381f37d651a2b9736d#diff-308a4ab4e9e209d390d0cb79a9301a0f7e9768564a3b3489055bf1f0a3f8a775L655
            # enforce_origin enables enforcement of the Origin header. (This is different from enforcing origins generally, which is always done)
            enforce_origin
        }

        debug
}

that generates the JSON:

{
   "admin":{
      "enforce_origin":true,
      "listen":"unix//tmp/http.sock",
      "origins":[
         "unixsocket"
      ]
   },
   "logging":{
      "logs":{
         "default":{
            "level":"DEBUG"
         }
      }
   }
}

I get these unexpected errors:

# curl --unix-socket /tmp/http.sock --no-buffer -X GET http://unixsocket/config/
{"error":"client is not allowed to access from origin ''"}
# curl --unix-socket /tmp/http.sock -X GET -H'Content-Type: application/json' http://unixsocket/config/
{"error":"client is not allowed to access from origin ''"}
# curl --unix-socket /tmp/http.sock -X GET -H'Content-Type: application/json' unixsocket/config/
{"error":"client is not allowed to access from origin ''"}
# curl --unix-socket /tmp/http.sock -X GET -H'Content-Type: application/json' -H'Origin: unixsocket' http://unixsocket/config/
{"error":"client is not allowed to access from origin 'unixsocket'"}
# curl --unix-socket /tmp/http.sock -X GET -H'Content-Type: application/json' -H'Origin: unixsocket' unixsocket/config/
{"error":"client is not allowed to access from origin 'unixsocket'"}

The same exact commands work exactly as expected, without errors if enforce_origin is turned off.

Background: Stumbled across an interesting post about admin endpoint over unix sockets: 2.5.0 enforce_origin bug - #11 by gcss
The reason why I made this post and said “I get these unexpected errors” because it would make sense to support origins over the unix socket as well, because it could be some other service proxying a HTTP/TCP connection to the unix socket.

PS: caddy-docker-proxy does not seem to respect enforce_origin and origins labels: Interest in enabling `enforce_origin` and `origins`? · Issue #359 · lucaslorentz/caddy-docker-proxy · GitHub

Hi :wave:

this bug has been fixed by @francislavoie and will land in caddy v2.5.1 :innocent:
See cmd: Fix unix socket addresses for admin API requests by francislavoie · Pull Request #4742 · caddyserver/caddy · GitHub

If you need that fix immediately, you could use xcaddy to build your own caddy binary from the current master branch, which has this fix merged:

xcaddy build master

## or specify the commit sha of the merge
xcaddy build 2e4c0915
4 Likes

With this Dockerfile:

ARG CADDY_VERSION=latest
FROM caddy:builder-alpine AS caddy-builder

# Either faild
RUN xcaddy build master # -> v2.5.1-0.20220502205534-e84e19a04eef h1:rZdtY/ar5HuldqChkZQKjNCPwe7vbxwJ98hxfMizVRI=
# RUN xcaddy build 2e4c0915 # -> v2.5.1-0.20220428143159-2e4c09155a75 h1:U6SJt0DEajgtnWZ4rS+jhqF7Nsta/Bjb7aGwuZ3SFBE=

# None of these images have curl (has wget) so add it
FROM caddy:alpine
RUN apk update && apk upgrade && apk add curl

WORKDIR /usr/bin/
COPY --from=caddy-builder /usr/bin/caddy /usr/bin/caddy

ENTRYPOINT ["/usr/bin/caddy"]

CMD ["run", "--config", "/etc/caddy/Caddyfile", "--adapter", "caddyfile"]

running the curl in the containers continue to show the errors:

# curl --unix-socket /tmp/http.sock --no-buffer -X GET http://unixsocket/config/
{"error":"client is not allowed to access from origin ''"}
# curl --unix-socket /tmp/http.sock -X GET -H'Content-Type: application/json' http://unixsocket/config/
{"error":"client is not allowed to access from origin ''"}
# curl --unix-socket /tmp/http.sock -X GET -H'Content-Type: application/json' unixsocket/config/
{"error":"client is not allowed to access from origin ''"}
# curl --unix-socket /tmp/http.sock -X GET -H'Content-Type: application/json' -H'Origin: unixsocket' http://unixsocket/config/
{"error":"client is not allowed to access from origin 'unixsocket'"}
# curl --unix-socket /tmp/http.sock -X GET -H'Content-Type: application/json' -H'Origin: unixsocket' unixsocket/config/
{"error":"client is not allowed to access from origin 'unixsocket'"}

You might need http://unixsocket… (I’d have to go look when I have a chance, but if you are able to try it sooner, that should be faster.) – Origins are typically scheme + host.

1 Like

Indeed.

/usr/bin # curl --unix-socket /tmp/http.sock -X GET -H'Content-Type: application/json' -H'Origin: http://unixsocket' http://unixsocket/config/
{"admin":{"enforce_origin":true,"listen":"unix//tmp/http.sock","origins":["unixsocket"]},"logging":{"logs":{"default":{"level":"DEBUG"}}}}
/usr/bin # curl --unix-socket /tmp/http.sock -X GET -H'Content-Type: application/json' -H'Origin: http://unixsocket' unixsocket/config/
{"admin":{"enforce_origin":true,"listen":"unix//tmp/http.sock","origins":["unixsocket"]},"logging":{"logs":{"default":{"level":"DEBUG"}}}}

I looked at the actual commit as well cmd: Fix unix socket addresses for admin API requests (#4742) · caddyserver/caddy@2e4c091 · GitHub

For reference, the ones without the scheme and just the host continue to fail (as expected?)

/usr/bin # curl --unix-socket /tmp/http.sock -X GET -H'Content-Type: application/json' http://unixsocket/config/
{"error":"client is not allowed to access from origin ''"}
/usr/bin # curl --unix-socket /tmp/http.sock -X GET -H'Content-Type: application/json' unixsocket/config/
{"error":"client is not allowed to access from origin ''"}
/usr/bin # curl --unix-socket /tmp/http.sock -X GET -H'Content-Type: application/json' -H'Origin: unixsocket' http://unixsocket/config/
{"error":"client is not allowed to access from origin 'unixsocket'"}
/usr/bin # curl --unix-socket /tmp/http.sock -X GET -H'Content-Type: application/json' -H'Origin: unixsocket' unixsocket/config/
{"error":"client is not allowed to access from origin 'unixsocket'"}

I’ll now go and followup at Interest in enabling `enforce_origin` and `origins`? · Issue #359 · lucaslorentz/caddy-docker-proxy · GitHub

Thank you @matt @IndeedNotJames and @francislavoie

1 Like

My understanding is that the Origin header should always contain a scheme:

2 Likes

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