feat: show directly requested file in requests overview
When a call directly hits a file it is now show up in the requests overview. This helps the user whether an attack from WebGoat actually requested the uploaded file. Closes: gh-1551
This commit is contained in:
parent
3d651526be
commit
ae261f201a
@ -22,8 +22,6 @@
|
|||||||
|
|
||||||
package org.owasp.webgoat.webwolf.requests;
|
package org.owasp.webgoat.webwolf.requests;
|
||||||
|
|
||||||
import static java.util.stream.Collectors.toList;
|
|
||||||
|
|
||||||
import com.fasterxml.jackson.core.JsonProcessingException;
|
import com.fasterxml.jackson.core.JsonProcessingException;
|
||||||
import com.fasterxml.jackson.databind.ObjectMapper;
|
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||||
import java.time.Instant;
|
import java.time.Instant;
|
||||||
@ -67,10 +65,10 @@ public class Requests {
|
|||||||
var model = new ModelAndView("requests");
|
var model = new ModelAndView("requests");
|
||||||
String username = (null != authentication) ? authentication.getName() : "anonymous";
|
String username = (null != authentication) ? authentication.getName() : "anonymous";
|
||||||
var traces =
|
var traces =
|
||||||
traceRepository.findAllTraces().stream()
|
traceRepository.findAll().stream()
|
||||||
.filter(t -> allowedTrace(t, username))
|
.filter(t -> allowedTrace(t, username))
|
||||||
.map(t -> new Tracert(t.getTimestamp(), path(t), toJsonString(t)))
|
.map(t -> new Tracert(t.getTimestamp(), path(t), toJsonString(t)))
|
||||||
.collect(toList());
|
.toList();
|
||||||
model.addObject("traces", traces);
|
model.addObject("traces", traces);
|
||||||
|
|
||||||
return model;
|
return model;
|
||||||
@ -93,7 +91,7 @@ public class Requests {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private String path(HttpExchange t) {
|
private String path(HttpExchange t) {
|
||||||
return (String) t.getRequest().getUri().getPath();
|
return t.getRequest().getUri().getPath();
|
||||||
}
|
}
|
||||||
|
|
||||||
private String toJsonString(HttpExchange t) {
|
private String toJsonString(HttpExchange t) {
|
||||||
|
@ -22,6 +22,9 @@
|
|||||||
|
|
||||||
package org.owasp.webgoat.webwolf.requests;
|
package org.owasp.webgoat.webwolf.requests;
|
||||||
|
|
||||||
|
import static org.owasp.webgoat.webwolf.requests.WebWolfTraceRepository.Exclusion.contains;
|
||||||
|
import static org.owasp.webgoat.webwolf.requests.WebWolfTraceRepository.Exclusion.endsWith;
|
||||||
|
|
||||||
import com.google.common.collect.EvictingQueue;
|
import com.google.common.collect.EvictingQueue;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
@ -36,31 +39,50 @@ import org.springframework.boot.actuate.web.exchanges.HttpExchangeRepository;
|
|||||||
* @since 8/13/17.
|
* @since 8/13/17.
|
||||||
*/
|
*/
|
||||||
public class WebWolfTraceRepository implements HttpExchangeRepository {
|
public class WebWolfTraceRepository implements HttpExchangeRepository {
|
||||||
|
private enum MatchingMode {
|
||||||
|
CONTAINS,
|
||||||
|
ENDS_WITH,
|
||||||
|
EQUALS;
|
||||||
|
}
|
||||||
|
|
||||||
|
record Exclusion(String path, MatchingMode mode) {
|
||||||
|
public boolean matches(String path) {
|
||||||
|
return switch (mode) {
|
||||||
|
case CONTAINS -> path.contains(this.path);
|
||||||
|
case ENDS_WITH -> path.endsWith(this.path);
|
||||||
|
case EQUALS -> path.equals(this.path);
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
public static Exclusion contains(String exclusionPattern) {
|
||||||
|
return new Exclusion(exclusionPattern, MatchingMode.CONTAINS);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static Exclusion endsWith(String exclusionPattern) {
|
||||||
|
return new Exclusion(exclusionPattern, MatchingMode.ENDS_WITH);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
private final EvictingQueue<HttpExchange> traces = EvictingQueue.create(10000);
|
private final EvictingQueue<HttpExchange> traces = EvictingQueue.create(10000);
|
||||||
private final List<String> exclusionList =
|
private final List<Exclusion> exclusionList =
|
||||||
List.of(
|
List.of(
|
||||||
"/tmpdir",
|
contains("/tmpdir"),
|
||||||
"/home",
|
contains("/home"),
|
||||||
"/files",
|
endsWith("/files"),
|
||||||
"/images/",
|
contains("/images/"),
|
||||||
"/js/",
|
contains("/js/"),
|
||||||
"/webjars/",
|
contains("/webjars/"),
|
||||||
"/requests",
|
contains("/requests"),
|
||||||
"/css/",
|
contains("/css/"),
|
||||||
"/mail");
|
contains("/mail"));
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public List<HttpExchange> findAll() {
|
public List<HttpExchange> findAll() {
|
||||||
return List.of();
|
|
||||||
}
|
|
||||||
|
|
||||||
public List<HttpExchange> findAllTraces() {
|
|
||||||
return new ArrayList<>(traces);
|
return new ArrayList<>(traces);
|
||||||
}
|
}
|
||||||
|
|
||||||
private boolean isInExclusionList(String path) {
|
private boolean isInExclusionList(String path) {
|
||||||
return exclusionList.stream().anyMatch(e -> path.contains(e));
|
return exclusionList.stream().anyMatch(e -> e.matches(path));
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
@ -0,0 +1,41 @@
|
|||||||
|
package org.owasp.webgoat.webwolf.requests;
|
||||||
|
|
||||||
|
import static org.mockito.Mockito.mock;
|
||||||
|
import static org.mockito.Mockito.when;
|
||||||
|
|
||||||
|
import java.net.URI;
|
||||||
|
import org.assertj.core.api.Assertions;
|
||||||
|
import org.junit.jupiter.api.DisplayName;
|
||||||
|
import org.junit.jupiter.api.Test;
|
||||||
|
import org.springframework.boot.actuate.web.exchanges.HttpExchange;
|
||||||
|
|
||||||
|
class WebWolfTraceRepositoryTest {
|
||||||
|
|
||||||
|
@Test
|
||||||
|
@DisplayName("When a user hits a file upload it should be recorded")
|
||||||
|
void shouldAddFilesRequest() {
|
||||||
|
HttpExchange httpExchange = mock();
|
||||||
|
HttpExchange.Request request = mock();
|
||||||
|
when(httpExchange.getRequest()).thenReturn(request);
|
||||||
|
when(request.getUri()).thenReturn(URI.create("http://localhost:9090/files/test1234/test.jpg"));
|
||||||
|
WebWolfTraceRepository repository = new WebWolfTraceRepository();
|
||||||
|
|
||||||
|
repository.add(httpExchange);
|
||||||
|
|
||||||
|
Assertions.assertThat(repository.findAll()).hasSize(1);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
@DisplayName("When a user hits file upload page ('/files') it should be recorded")
|
||||||
|
void shouldAddNotAddFilesRequestOverview() {
|
||||||
|
HttpExchange httpExchange = mock();
|
||||||
|
HttpExchange.Request request = mock();
|
||||||
|
when(httpExchange.getRequest()).thenReturn(request);
|
||||||
|
when(request.getUri()).thenReturn(URI.create("http://localhost:9090/files"));
|
||||||
|
WebWolfTraceRepository repository = new WebWolfTraceRepository();
|
||||||
|
|
||||||
|
repository.add(httpExchange);
|
||||||
|
|
||||||
|
Assertions.assertThat(repository.findAll()).hasSize(0);
|
||||||
|
}
|
||||||
|
}
|
Loading…
x
Reference in New Issue
Block a user