Closed rwjack closed 2 years ago
Config which returns 403 to everyone, excluding 172.16.1.1/24
:
middlewares:
crowdsec:
plugin:
bouncer:
enabled: true
updateIntervalSeconds: 60
crowdsecMode: stream
crowdsecLapiKey: foobar
crowdsecLapiHost: host.fqdn:1234
crowdsecLapiScheme: http
clientTrustedIPs:
- 172.16.1.1/24
Config which returns 20* to everyone:
clientTrustedIPs:
- 0.0.0.0/0
Config which returns 403 to everyone:
#clientTrustedIPs:
# - 0.0.0.0/0
Cool, thanks for more advanced configuration, maybe you can use logLevel: DEBUG
option to get information.
The first thing that comes to mind is that your crowdsec instance is unavailable or cannot be reached by the plugin.
Hi @rwjack
We usually use the following container to debug things with Traefik: https://hub.docker.com/r/traefik/whoami
When you access it, and it gives you a 200 status, it will show you what are the IPs are seen by the end service.
For instance:
Hostname: 78f9564adb82
IP: 127.0.0.1
IP: 192.168.48.3
RemoteAddr: 192.168.48.2:40642
GET /foo HTTP/1.1
Host: 10.0.20.40
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/107.0.0.0 Safari/537.36
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3;q=0.9
Accept-Encoding: gzip, deflate
Accept-Language: fr-FR,fr;q=0.9,en-US;q=0.8,en;q=0.7
Dnt: 1
Upgrade-Insecure-Requests: 1
X-Forwarded-For: 10.0.10.5
X-Forwarded-Host: 10.0.20.40
X-Forwarded-Port: 80
X-Forwarded-Proto: http
X-Forwarded-Server: 98e7afca71de
X-Real-Ip: 10.0.10.5
Here 10.0.10.5 is my true IP as seen with traefik/whoami container 10.0.20.40 si my destination
You used clientTrustedIPs:[172.16.1.1/24] It looks to me like the docker internal network, is that the case ?
I'm using Traefik 2.8.4, and the latest commit of this plugin (deployed in the plugins-local dir).
Do you mean you deployed the plugin with the sourcecode of the repository binded in the container ?
command:
- "--log.level=DEBUG"
- "--accesslog"
- "--accesslog.filepath=/var/log/traefik/access.log"
- "--api.insecure=true"
- "--providers.docker=true"
- "--providers.docker.exposedbydefault=false"
- "--entrypoints.web.address=:80"
- "--experimental.localplugins.bouncer.modulename=github.com/maxlerebourg/crowdsec-bouncer-traefik-plugin"
volumes:
- /var/run/docker.sock:/var/run/docker.sock:ro
- logs-local:/var/log/traefik
- ./:/plugins-local/src/github.com/maxlerebourg/crowdsec-bouncer-traefik-plugin
I recommand you to try and deploy it if that's the case with the release way:
command:
...
- "--experimental.plugins.bouncer.modulename=github.com/maxlerebourg/crowdsec-bouncer-traefik-plugin"
- "--experimental.plugins.bouncer.version=v1.1.4"
It would be much easier to fix this issue if you could try and run the plugin in debug mode:
In the label of your service add the following;
- "traefik.http.middlewares.CROWDSEC-FIXME-INSTANCENAME.plugin.bouncer.loglevel=DEBUG"
Also we could use the logs from crowdsec container.
Please remove any sensitive information before posting but keep a consistent naming about what IP replaced in the logs is supposed to be (client, container, proxy?)
Thanks you by advance
Hey, I attached the last 5000 lines of the Crowdsec container, and replaced my Traefik VM IP with traefik.vm.ip.addr
.
The Crowdsec container seems reachable from the Traefik VM, and do note that I'm running Traefik on Debian, not as a container.
Also, I did not really use clientTrustedIPs:[172.16.1.1/24]
, it was just an example, but maybe better to use the A class as an example (which I actually use), so 10.0.0.0/24
.
Do you mean you deployed the plugin with the sourcecode of the repository binded in the container ?
Technically, yes, but not bound in the container since I'm running traefik on Debian with systemd. This entire git repo of this plugin is located in: /opt/traefik/plugins-local/src/github.com/maxlerebourg/crowdsec-bouncer-traefik-plugin/
traefik.yml
:
experimental:
#plugins:
localPlugins:
bouncer:
moduleName: github.com/maxlerebourg/crowdsec-bouncer-traefik-plugin
#version: "v1.1.0"
I recommand you to try and deploy it if that's the case with the release way:
I couldn't get that working, because this VM has blocked all outbound internet access unless it's permitted URLs through a proxy, so traefik is having problems talking to github. That's why I manually deployed the plugin in plugins-local
, as stated in Traefik documentation.
It would be much easier to fix this issue if you could try and run the plugin in debug mode:
I have added the following in the dynamic conf:
http:
middlewares:
crowdsec:
plugin:
bouncer:
...
logLevel: DEBUG
...
Do I also need to change this in the static conf:
log:
filePath: /var/log/traefik/traefik.log
level: INFO # -> DEBUG?
Because the logs don't show much:
$ systemctl restart traefik && tail -f /var/log/traefik/traefik.log
time="2022-11-26T13:57:53+01:00" level=error msg="Error while Peeking first byte: read tcp traefik.vm.ip.addr:443->external.ip:64950: read: connection timed out"
time="2022-11-26T14:08:49+01:00" level=error msg="Error while Peeking first byte: read tcp traefik.vm.ip.addr:443->external.ip:22724: read: connection timed out"
time="2022-11-26T14:13:45+01:00" level=info msg="I have to go..."
time="2022-11-26T14:13:45+01:00" level=info msg="Stopping server gracefully"
time="2022-11-26T14:13:45+01:00" level=error msg="accept tcp [::]:443: use of closed network connection" entryPointName=web-secure
time="2022-11-26T14:13:45+01:00" level=error msg="Error while starting server: accept tcp [::]:443: use of closed network connection" entryPointName=web-secure
time="2022-11-26T14:13:45+01:00" level=error msg="accept tcp [::]:80: use of closed network connection" entryPointName=web
time="2022-11-26T14:13:45+01:00" level=error msg="Error while starting server: accept tcp [::]:80: use of closed network connection" entryPointName=web
time="2022-11-26T14:13:55+01:00" level=info msg="Server stopped"
time="2022-11-26T14:13:55+01:00" level=info msg="Shutting down"
time="2022-11-26T14:13:55+01:00" level=info msg="Traefik version 2.8.4 built on 2022-09-02T14:42:59Z"
time="2022-11-26T14:13:55+01:00" level=info msg="\nStats collection is disabled.\nHelp us improve Traefik by turning this feature on :)\nMore details on: https://doc.traefik.io/traefik/contributing/data-collection/\n"
time="2022-11-26T14:13:55+01:00" level=warning msg="Traefik Pilot is deprecated and will be removed soon. Please check our Blog for migration instructions later this year."
time="2022-11-26T14:13:55+01:00" level=info msg="Starting provider aggregator aggregator.ProviderAggregator"
time="2022-11-26T14:13:55+01:00" level=info msg="Starting provider *file.Provider"
time="2022-11-26T14:13:55+01:00" level=info msg="Starting provider *traefik.Provider"
time="2022-11-26T14:13:55+01:00" level=info msg="Starting provider *acme.Provider"
time="2022-11-26T14:13:55+01:00" level=info msg="Testing certificate renew..." providerName=le.acme ACME CA="https://acme-v02.api.letsencrypt.org/directory"
time="2022-11-26T14:13:55+01:00" level=info msg="Starting provider *acme.ChallengeTLSALPN"
Okay, changing traefik logs to debug as well just printed out a bunch of stuff, but nothing seems relevant. Are you guys having trouble replicating this issue?
Could it be my other middleware interfering somehow:
security-headers:
headers:
referrerPolicy: same-origin
forceSTSHeader: true
stsSeconds: 31536000
stsIncludeSubdomains: true
stsPreload: true
contentTypeNosniff: true
browserXssFilter: true
customRequestHeaders:
X-Forwarded-Proto: https
frameDeny: true
I just want to make sure we all understand each other:
clientTrustedIPs:
- 10.0.0.0/24
The above config, as I understood, should work in the following manner:
Expected Case 1:
Expected Case 2:
^ What actually happens in Case 2:
Maybe this is a problem with the cache? Is it written to memory or a file? Maybe Traefik can't write the cache file?
that I'm running Traefik on Debian, not as a container.
That's good to know!
but maybe better to use the A class as an example (which I actually use), so 10.0.0.0/24.
Did you meant a class C (containing 256 IP) with the identifier 10.0.0.X ?
Network: 10.0.0.0
CIDR: 24
Mask: 255.255.255.0
Range: 10.0.0.0 - 10.0.0.255
Total addresses in range: 256
Technically, yes, but not bound in the container since I'm running traefik on Debian with systemd. This entire git repo of this plugin is located in: /opt/traefik/plugins-local/src/github.com/maxlerebourg/crowdsec-bouncer-traefik-plugin/
Alright that's clear, could you try to pin the local repository to the version 1.1.4 ?
https://github.com/maxlerebourg/crowdsec-bouncer-traefik-plugin/releases/tag/v1.1.4
Until we release we might discover some bugs on the main branch
I have added the following in the dynamic conf:
http: middlewares: crowdsec: plugin: bouncer: ... logLevel: DEBUG ...
Can you please check the indentation ? Settings should be 2 char from the name of the plugin like this:
http:
middlewares:
crowdsec:
plugin:
bouncer:
...
logLevel: DEBUG
...
For an exemple, I currently uses on my main proxy:
http:
middlewares:
crowdsec-demo:
plugin:
bouncer:
enabled: true
crowdseclapikey: KEEEEEEEEEEEEEEY-demo
updateintervalseconds: 60
crowdsecmode: stream
logLevel: "DEBUG"
clientTrustedips: MY_PERSONAL_IP/32
Do I also need to change this in the static conf:
log: filePath: /var/log/traefik/traefik.log level: INFO # -> DEBUG?
I'm not sure, for the moment if we have to look at the debug logs of Traefik, the plugin should be logging independantly of Traefik log level
Because the logs don't show much:
That "may" be a good thing, at least no error visible, but clearly debug logs are not activated on the plugin, we have to find out why
Okay, changing traefik logs to debug as well just printed out a bunch of stuff, but nothing seems relevant. Are you guys having trouble replicating this issue?
I'll setup a demo environnement with a VM without container. Can you tell me which version of debian are you using ? 10, 11 ? Could you also share this log file (a few requests)
Could it be my other middleware interfering somehow:
I do not believe it's connected, your other middleware is only changing headers
The above config, as I understood, should work in the following manner:
Yes, you're right, I'll check on my side if everything is working as intended
Maybe this is a problem with the cache? Is it written to memory or a file? Maybe Traefik can't write the cache file? I have not thought about this, i'll respond after digging
Summary: I tried to answer all question, and ask you new informations Right now, we need to activate debug logs on the plugin, this should really guide us. We added a lot of logging through each step the plugin takes.
On my side, i'll setup the demo environnement and tell you if I find anything random ideas i'll check:
identify what can cause the 403 except the ban IP (canno't contact crowdsec, cannot write to cache..)
is the public IP really is the one the plugin receives
is there a bug in the main branch not seen in release 1.1.4
On your side, can you anwser the questions above
Thanks for taking the time to debug this with us!
Did you meant a class C (containing 256 IP) with the identifier 10.0.0.X ?
Ugh, I'm trying to reveal as less information as I can, but I'll just be direct now to ease the debugging process. I use 10.0.0.0/8
- The literal class A, as the parameter for clientTrustedIPs
.
Can you please check the indentation ? Settings should be 2 char from the name of the plugin like this:
My bad, indentation was good in the traefik config file, I edited it wrongly here.
I'm not sure, for the moment if we have to look at the debug logs of Traefik, the plugin should be logging independantly of Traefik log level
Okay, so where does it send logs to?
is the public IP really is the one the plugin receives
This could be related to the issue.
My current config: client request -> DMZ traefik VM (with this plugin) -> docker hypervisor (with crowdsec container)
HEY @mathieuHa
is there a bug in the main branch not seen in release 1.1.4
This might be it! I just did git checkout v1.1.4
, set ClientTrustedIPs
to the A class, and I'm not getting 403s externally anymore. Checked from my phone.
I guess this narrows the search to v1.1.4 <-> Main
https://github.com/maxlerebourg/crowdsec-bouncer-traefik-plugin/compare/v1.1.4...main
HEY @mathieuHa
is there a bug in the main branch not seen in release 1.1.4
This might be it! I just did
git checkout v1.1.4
, setClientTrustedIPs
to the A class, and I'm not getting 403s externally anymore. Checked from my phone.I guess this narrows the search to
v1.1.4 <-> Main
Thanks for the feedback @rwjack Please let me know if you get any error with version 1.1.4 I'll work on fixing the problem before we can release 1.1.5
- The literal class A, as the parameter for clientTrustedIPs.
You can add multiples classes if you want in the parameter clusterTrustedIPs (it expects an array of IP/CIDR), but I know it can be hard to keep track of all ranges of IPs
Please let me know if you get any error with version 1.1.4
Will do, thank you for helping out to get through this.
Guess this is a lesson for me to sometimes stick to releases, instead of going for bleeding edge all the time :)
I think I found the guilty line of code
We did a major cleaning and rewrite last week and this condition has flipped.
Awesome! Glad we got it sorted
Hey @mathieuHa, just wanted to let you know that I'm having some issues accessing services from the outside.
Now everyone gets 403 responses. Disabling the bouncer from the traefik static config fixes the issue, meaning the plugin is definitely the culprit.
Consider that everything on localnet is 172.16.1.1/24
I've set:
And this works as expected, these clients are not rate limited and don't go through crowdsec.
Though when adding
- 0.0.0.0/0
, I have access all services externally.It seems now that only clientTrustedIPs are allowed to connect, regardless of what crowdsec says.
Any thoughts?
I'm using Traefik 2.8.4, and the latest commit of this plugin (deployed in the plugins-local dir). I don't use redis for now. I'll look into debug mode a bit later, if it's even required at all, though this seems like some sort of funny semantic issue :)