Skip to content

Commit

Permalink
Merge remote-tracking branch 'origin/master'
Browse files Browse the repository at this point in the history
  • Loading branch information
JanHolger committed Nov 6, 2021
2 parents 4754957 + 1203333 commit 7778c20
Show file tree
Hide file tree
Showing 4 changed files with 115 additions and 4 deletions.
2 changes: 1 addition & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -18,4 +18,4 @@ JWS Utilties
<artifactId>web-utils</artifactId>
<version>1.0.0</version>
</dependency>
```
```
Original file line number Diff line number Diff line change
@@ -0,0 +1,107 @@
package org.javawebstack.webutils.middlewares;

import org.javawebstack.httpserver.Exchange;
import org.javawebstack.httpserver.handler.Middleware;

import java.util.HashMap;
import java.util.Map;
import java.util.Timer;
import java.util.TimerTask;
import java.util.concurrent.ConcurrentHashMap;

public class RateLimitMiddleware implements Middleware {
private int rateLimit;
private long millis;
private Map<String, RateLimit> rateLimits = new ConcurrentHashMap<>();

public RateLimitMiddleware(long millis, int rateLimit){
this.rateLimit = rateLimit;
this.millis = millis;
}

public RateLimitMiddleware(long millis){
this(millis, 1);
}

public Object handle(Exchange exchange) {
String ip = exchange.rawRequest().getRemoteAddr();
if (exchange.header("X-Forwarded-For") != null)
ip = exchange.header("X-Forwarded-For");
RateLimit rateLimit = null;
if (rateLimits.containsKey(ip)) {
rateLimit = rateLimits.get(ip);
if (rateLimit.stillAlive() && rateLimit.getAndDecrease() <= 1)
throw new RateLimitException();
}
if (rateLimit == null || !rateLimit.stillAlive())
rateLimit = new RateLimit(System.currentTimeMillis() + millis, this.rateLimit);
rateLimits.put(ip, rateLimit);
exchange.header("X-Rate-Limit-Limit", String.valueOf(this.rateLimit));
exchange.header("X-Rate-Limit-Remaining", String.valueOf(rateLimit.getRateLimitLeft()));
exchange.header("X-Rate-Limit-Reset", String.valueOf(rateLimit.getTimeMillis()/1000));
return null;
}

public void removeDeadRateLimits(){
rateLimits.forEach((ip, rateLimit)-> {
if (!rateLimit.stillAlive())
rateLimits.remove(ip);
});
}

public RateLimitMiddleware createAutoDeadRateLimitsRemover(long millis){
new Timer().schedule(new TimerTask() {
public void run() {
removeDeadRateLimits();
}
}, millis, millis);
return this;
}

public RateLimitMiddleware createAutoDeadRateLimitsRemover(){
return createAutoDeadRateLimitsRemover(millis);
}

public int getRateLimit() {
return rateLimit;
}

public long getMillis() {
return millis;
}

public void setRateLimit(int rateLimit) {
this.rateLimit = rateLimit;
}

public void setMillis(int millis) {
this.millis = millis;
}

private static class RateLimit {
private long timeMillis;
private int rateLimitLeft;

private RateLimit(long timeMillis, int rateLimitLeft) {
this.timeMillis = timeMillis;
this.rateLimitLeft = rateLimitLeft;
}

public int getRateLimitLeft() {
return rateLimitLeft;
}
public int getAndDecrease() {
return rateLimitLeft--;
}

public long getTimeMillis() {
return timeMillis;
}

public boolean stillAlive(){
return timeMillis > System.currentTimeMillis();
}
}

public static class RateLimitException extends RuntimeException {}
}
6 changes: 3 additions & 3 deletions src/main/java/org/javawebstack/webutils/util/URLUtils.java
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@

public class URLUtils {

public String urlEncode(String content) {
public static String urlEncode(String content) {
try {
return URLEncoder.encode(content, "UTF-8");
} catch (UnsupportedEncodingException e) {
Expand All @@ -17,7 +17,7 @@ public String urlEncode(String content) {
return null;
}

public String urlDecode(String content) {
public static String urlDecode(String content) {
try {
return URLDecoder.decode(content, "UTF-8");
} catch (UnsupportedEncodingException e) {
Expand Down Expand Up @@ -119,7 +119,7 @@ public static URLBuilder from(String url) {
String[] queryParameters = pathAndQueryParameters[1].split("&");
for (String queryParameter : queryParameters) {
String[] keyValue = queryParameter.split("=", 2);
urlBuilder.queryParameters.set(keyValue[0], keyValue.length > 1 ? keyValue[1] : "");
urlBuilder.queryParameters.set(URLUtils.urlDecode(keyValue[0]), URLUtils.urlDecode(keyValue.length > 1 ? keyValue[1] : ""));
}
}
}
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
package org.javawebstack.webutils.test;

public class URLUtilsTests {
}

0 comments on commit 7778c20

Please sign in to comment.