mholt / caddy-ratelimit

HTTP rate limiting module for Caddy 2
Apache License 2.0
247 stars 17 forks source link

Limit by IPv6 network range #23

Open jpds opened 1 year ago

jpds commented 1 year ago

For effective usage of this plugin on IPv6 enabled systems - there needs to be a way to rate-limit by IPv6 network range; this can be done by looking at the first four hextets which make up the network identifier of the addresses:

mholt commented 1 year ago

Any idea of IPv6 can be specified using a CIDR range?

jpds commented 1 year ago

I think that for end-user clients, it's just generally assumed that people on the same network would be coming from the same /64.

Golang'd net.ParseCIDR appears to do the right thing if you ask it for the /64 of an IPv6: https://pkg.go.dev/net#example-ParseCIDR (even if you edit the IP to be "2001:db8:a0b:12f0:ae:a512::1/64" for example).

This is already what Docker Hub do for their rate-limiting: https://www.docker.com/blog/docker-hub-registry-ipv6-support-now-generally-available/

mholt commented 1 year ago

In that case, could you use a remote_ip matcher and specify the desired CIDR range?

jpds commented 6 months ago

I've read through the documentation for remote_ip and as far as I can tell: it allows one to statically define desired CIDR ranges.

However what is required here is the ability to dynamically track a group of requests from the same /64. Is there some way to parse {http.request.remote.host} ?

mholt commented 6 months ago

Does {http.request.remote.host}/64 work as a CIDR range? I haven't actually tried it, but I agree that something like this should be made possible if it's not already.

lenovouser commented 4 months ago

@mholt it probably won't work, since {http.request.remote.host} always changes for each IP in the /64, we would have to parse the IP and get the first in the /64 block to use it for that. This could also be useful for IPv4, maybe we could add some universal option where you can say up to which CIDR you want to match for IPv4 and IPv6 each and then we only use the first IP in that block as key.

mholt commented 4 months ago

I think if you use that in the remote_ip matcher, though, it will be evaluated accordingly: https://caddyserver.com/docs/modules/http.matchers.remote_ip

This matcher evaluates CIDR notation and matches on the resulting mask.