Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix 165 #166

Merged
merged 11 commits into from
Jul 8, 2019
5 changes: 5 additions & 0 deletions spring-cloud-zuul-ratelimit-core/pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -165,6 +165,11 @@
<artifactId>spring-security-test</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>commons-net</groupId>
<artifactId>commons-net</artifactId>
<version>3.6</version>
</dependency>

</dependencies>

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@

import com.marcosbarbero.cloud.autoconfigure.zuul.ratelimit.config.RateLimitUtils;
import org.apache.commons.lang3.StringUtils;
import org.apache.commons.net.util.SubnetUtils;
import org.springframework.cloud.netflix.zuul.filters.Route;

import javax.servlet.http.HttpServletRequest;
Expand All @@ -30,6 +31,15 @@ public enum RateLimitType {
ORIGIN {
@Override
public boolean apply(HttpServletRequest request, Route route, RateLimitUtils rateLimitUtils, String matcher) {
if(matcher.contains("/")) {
try {
SubnetUtils subnetUtils = new SubnetUtils(matcher);
return subnetUtils.getInfo().isInRange(rateLimitUtils.getRemoteAddress(request));
}
catch(Exception e) {
return false;
}
}
return matcher.equals(rateLimitUtils.getRemoteAddress(request));
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -61,5 +61,15 @@ public ResponseEntity<String> serviceF() {
public ResponseEntity<String> serviceG() {
return ResponseEntity.ok(RESPONSE_BODY);
}

@GetMapping("/serviceH")
public ResponseEntity<String> serviceH() {
return ResponseEntity.ok(RESPONSE_BODY);
}

@GetMapping("/serviceI")
public ResponseEntity<String> serviceI() {
return ResponseEntity.ok(RESPONSE_BODY);
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,18 @@ zuul:
serviceE:
path: /serviceE
url: forward:/
serviceF:
path: /serviceF
url: forward:/
serviceG:
path: /serviceG
url: forward:/
serviceH:
path: /serviceH
url: forward:/
serviceI:
path: /serviceI
url: forward:/
ratelimit:
enabled: true
repository: JPA
Expand Down Expand Up @@ -74,6 +86,7 @@ zuul:
refresh-interval: 60
type:
- origin
breakOnMatch: true
serviceG:
- limit: 2
refresh-interval: 60
Expand All @@ -84,6 +97,29 @@ zuul:
refresh-interval: 60
type:
- origin
breakOnMatch: true
serviceH:
- limit: 2
refresh-interval: 60
type:
- origin=127.0.0.0/22
breakOnMatch: true
- limit: 1
refresh-interval: 60
type:
- origin
breakOnMatch: true
serviceI:
- limit: 2
refresh-interval: 60
type:
- origin=126.0.0.0/22
breakOnMatch: true
- limit: 1
refresh-interval: 60
type:
- origin
breakOnMatch: true
strip-prefix: true

logging:
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -129,27 +129,56 @@ public void testExceedingQuotaCapacityRequest() {
public void testUsingBreakOnMatchSpecificCase() {
ResponseEntity<String> response = this.restTemplate.getForEntity("/serviceF", String.class);
HttpHeaders headers = response.getHeaders();
String key = "rate-limit-application_serviceF_127.0.0.1";
assertHeaders(headers, key, true, false);
String key = "rate-limit-application_serviceF_127.0.0.1_127.0.0.1";
assertHeaders(headers, key, false, false);
assertEquals(OK, response.getStatusCode());

response = this.restTemplate.getForEntity("/serviceF", String.class);
headers = response.getHeaders();
assertHeaders(headers, key, true, false);
assertHeaders(headers, key, false, false);
assertEquals(OK, response.getStatusCode());
}

@Test
public void testUsingBreakOnMatchSpecificCaseWithCidr() {
ResponseEntity<String> response = this.restTemplate.getForEntity("/serviceH", String.class);
HttpHeaders headers = response.getHeaders();
String key = "rate-limit-application_serviceH_127.0.0.1_127.0.0.0_22";
assertHeaders(headers, key, false, false);
assertEquals(OK, response.getStatusCode());

response = this.restTemplate.getForEntity("/serviceH", String.class);
headers = response.getHeaders();
assertHeaders(headers, key, false, false);
assertEquals(OK, response.getStatusCode());
}

@Test
public void testUsingBreakOnMatchGeneralCase() {
ResponseEntity<String> response = this.restTemplate.getForEntity("/serviceG", String.class);
HttpHeaders headers = response.getHeaders();
String key = "rate-limit-application_serviceG_127.0.0.1";
assertHeaders(headers, key, true, false);
assertHeaders(headers, key, false, false);
assertEquals(OK, response.getStatusCode());

response = this.restTemplate.getForEntity("/serviceG", String.class);
headers = response.getHeaders();
assertHeaders(headers, key, true, false);
assertHeaders(headers, key, false, false);
assertEquals(TOO_MANY_REQUESTS, response.getStatusCode());
}

@Test
public void testUsingBreakOnMatchGeneralCaseWithCidr() {
ResponseEntity<String> response = this.restTemplate.getForEntity("/serviceI", String.class);
HttpHeaders headers = response.getHeaders();
String key = "rate-limit-application_serviceI_127.0.0.1";
assertHeaders(headers, key, false, false);
assertEquals(OK, response.getStatusCode());

response = this.restTemplate.getForEntity("/serviceI", String.class);
headers = response.getHeaders();
assertHeaders(headers, key, false, false);
assertEquals(TOO_MANY_REQUESTS, response.getStatusCode());
}

private void assertHeaders(HttpHeaders headers, String key, boolean nullable, boolean quotaHeaders) {
Expand Down