0xERR0R / blocky

Fast and lightweight DNS proxy as ad-blocker for local network with many features
https://0xERR0R.github.io/blocky/
Apache License 2.0
4.6k stars 202 forks source link

add support for the PROXY protocol #320

Open Akruidenberg opened 2 years ago

Akruidenberg commented 2 years ago

I would like to run blocky behind my traefik proxy. With the upcoming version of blocky, DOT server is added.

However, if blocky is running behind Traefik only, because TCP, only the IP of traefik is forwarded, not the Client itself. It would be nice to add traefik behind the traefik with the PROXY procotol. Adguard did get such feature in a next release, however, no ETA is confirmed.

See traefik docs for info about PROXY.

Thanks in advance!

0xERR0R commented 2 years ago

Hey,

hm, I was not aware of the proxy protocol, this looks interesting. Currently, I'm working on a dns-proxy as Proof-of-concept (see my repositories), which serves DoT and sends requests via DoH (with origin IP in header and client id). The goal was to create a server, which manages SSL certificates and can load-balance DNS queries to 2 blocky instances. I'll take a look on the proxy protocol, if it works, there is no need for my "dns-proxy"

Akruidenberg commented 2 years ago

Nice! If blocky supports this, I'm switching from adguard to Blocky.

0xERR0R commented 2 years ago

It looks like only the origin IP will be passed, not the request host name. For DoT it is possible to use the client identifier in the host name (like clientA.example.com), this name will be used in logs and for filtering purposes. With proxy protocol, only origin IP can be passed to blocky. If the service is externally accessible, you'll get the external client IP, but you can't assign the IP to the client name.

I'll try it out, this is not really clear for me from the spec

Akruidenberg commented 2 years ago

Will you implementation works with Traefik behind it (using the certs from Traefik itself?)

0xERR0R commented 2 years ago

Will you implementation works with Traefik behind it (using the certs from Traefik itself?)

If you mean the https://github.com/0xERR0R/dns-proxy implementation: no, it generates own Let's encrypt certificates with DNS challenge. If you mean blocky, I think the best way would be to create TLS entry point in traefik (port 853) and leave the certificate management in traefik. Traefik should proxy the request to blocky (TCP on 53). If it could also pass the origin IP and the origin hostname, then we could use this information in blocky. I'll test the proxy protocol implementation with traefik

0xERR0R commented 2 years ago

I tested traefik as TLS entry point and blocky as TCP service (port 53) with activated proxy protocol 2. Traefik sends only IP addresses. The TLS informations (like hostname) will not be passed (https://github.com/traefik/traefik/issues/5371 + https://github.com/traefik/traefik/issues/5859). As long this is not possible to receive the origin hostname, it makes not really sense to use this feature (you'll get the requestor IP address, but the more interesting would be the client id/name, which is used for filtering and logging. And this part of information is missing :disappointed: )

Akruidenberg commented 2 years ago

Is it possible for you to add a pull request for the Traefik repo for this?

0xERR0R commented 2 years ago

I don't think so. I'm not familiar with traefik's code base and it would be a lot of effort to implement this feature. I make my projects in my spare time and that is unfortunately limited.

If your use case is to simple install DoT endpoint and use blocky for ad-blocking (per client) and logging the queries (also per client), you can try dns-proxy. I have similar use case and want to install 2 instances of blocky (redundancy and simple maintenance) and also to install a public reachable DoT for my android phones.

github-actions[bot] commented 2 years ago

This issue is stale because it has been open 90 days with no activity. Remove stale label or comment or this will be closed in 5 days.

kwitsch commented 2 years ago

I looked into trafik to solve another problem I had regarding service scalability. The proxy protocol would be applicable if DNS requests are routed through traefik TCP endpoints as it preserves the original IP . This has a significant disadvantage as it adds ~3-4ms to the DNS response times(in my test scenarios). Far better results are achieved using virtual IPs and switching the actual server behind it using a service like keepalived.

celevra commented 1 year ago

got the same problems with haproxy i'm using haproxy for ssl termination with letsencrypt (no reload function in blocky) and ;-) to balance between multiple blocky instances but it does not log the client-id and the original ip.

support for proxy-protocoll would be awesome.

as of this line 560: https://github.com/simonsj/haproxy/blob/master/doc/proxy-protocol.txt

server_name (SNI) ist passed