Skip to content
This repository was archived by the owner on Feb 26, 2021. It is now read-only.

Commit 7c2e989

Browse files
authored
Merge pull request #34 from secureCodeBox/develop
Develop
2 parents 29d5dd7 + 8aac686 commit 7c2e989

7 files changed

Lines changed: 206 additions & 216 deletions

File tree

Dockerfile

Lines changed: 5 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -14,22 +14,18 @@ ENV SCB_REPOSITORY_URL ${REPOSITORY_URL}
1414

1515
RUN gradle clean build -Pvcs_commit=${SCB_COMMIT_ID} -Pvcs_version=${SCB_BRANCH} -Pvcs_url=${SCB_REPOSITORY_URL}
1616

17-
FROM owasp/zap2docker-bare
17+
FROM owasp/zap2docker-weekly:w2019-02-05
1818

1919
COPY dockerfiles/init.sh /home/zap/init.sh
2020
COPY dockerfiles/csrfAuthScript.js /home/zap/scripts/templates/authentication/csrfAuthScript.js
2121
COPY --from=builder /home/gradle/build/libs/scanner-webapplication-zap-0.4.0-SNAPSHOT.jar /home/zap/app.jar
2222

2323
USER root
2424

25-
RUN apk --update --no-cache add curl
26-
HEALTHCHECK --interval=30s --timeout=5s --start-period=120s --retries=3 CMD curl --fail http://localhost:8080/internal/health || exit 1
27-
28-
RUN chmod g+w /etc/passwd
29-
30-
RUN apk add --update ca-certificates openssl
25+
RUN wget -O /home/zap/wait-for-it.sh https://raw.githubusercontent.com/vishnubob/wait-for-it/54d1f0bfeb6557adf8a3204455389d0901652242/wait-for-it.sh
3126

3227
RUN chmod +x /home/zap/init.sh && \
28+
chmod +x /home/zap/wait-for-it.sh && \
3329
chgrp -R 0 /home/zap/ && \
3430
chmod -R g=u /home/zap/ && \
3531
chown -R zap /home/zap
@@ -48,6 +44,8 @@ LABEL org.opencontainers.image.title="secureCodeBox scanner-webapplication-zap"
4844
org.opencontainers.image.revision=$COMMIT_ID \
4945
org.opencontainers.image.created=$BUILD_DATE
5046

47+
HEALTHCHECK --interval=30s --timeout=5s --start-period=120s --retries=3 CMD curl --fail http://localhost:8080/internal/health || exit 1
48+
5149
EXPOSE 8080 8090
5250

5351
ENV JAVA_OPTS ""

dockerfiles/init.sh

Lines changed: 2 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -1,14 +1,4 @@
11
#!/bin/bash
2+
/zap/zap.sh -Xmx3G -daemon -dir /home/zap/ -port 8090 -host 0.0.0.0 -config api.disablekey=true -config api.addrs.addr.name=.* -config api.addrs.addr.regex=true -addoninstall soap -addoninstall openapi -addoninstall ascanrulesBeta -addoninstall ascanrulesAlpha -addoninstall pscanrulesBeta -addoninstall pscanrulesAlpha &
23

3-
if [ `id -u` -ge 1000 ]; then
4-
cat /etc/passwd | sed -e "s/^osUser:/builder:/" > /tmp/passwd
5-
echo "osUser:x:`id -u`:`id -g`:,,,:/home/zap:/bin/bash" >> /tmp/passwd
6-
cat /tmp/passwd > /etc/passwd
7-
rm /tmp/passwd
8-
fi
9-
10-
/zap/zap.sh -Xmx3G -daemon -dir /home/zap/ -port 8090 -host 0.0.0.0 -config api.disablekey=true -config api.addrs.addr.name=.* -config api.addrs.addr.regex=true -addoninstall soap -addoninstall openapi &
11-
12-
sleep 10
13-
14-
java -Djava.security.egd=file:/dev/./urandom -Xmx2G -jar /home/zap/app.jar
4+
/home/zap/wait-for-it.sh --timeout=120 localhost:8090 -- java -Djava.security.egd=file:/dev/./urandom -Xmx2G -jar /home/zap/app.jar

src/main/java/io/securecodebox/zap/jobs/definition/EngineWorkerJob.java

Lines changed: 13 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -63,7 +63,7 @@ public class EngineWorkerJob implements JobRunnable {
6363
@Autowired
6464
private ZapTaskService taskService;
6565
@Autowired
66-
private ZapService service;
66+
private ZapService zapService;
6767

6868
@Override
6969
public JobDefinition getJobDefinition() {
@@ -138,7 +138,7 @@ private void performSpiderTask(JobEventPublisher publisher, ZapTask task) throws
138138
ZapTargetAttributes attributes = target.getAttributes();
139139

140140
//Create a new Context for each target
141-
String contextId = service.createContext(attributes.getBaseUrl(),
141+
String contextId = zapService.createContext(attributes.getBaseUrl(),
142142
attributes.getSpiderIncludeRegex(), attributes.getSpiderExcludeRegex());
143143

144144
String userId = configureAuthentication(target, contextId);
@@ -184,7 +184,7 @@ private void performScannerTask(JobEventPublisher publisher, ZapTask task) throw
184184
}
185185

186186
// Save only one Raw Report, as zap doesn't support to get reports on the individual targets.
187-
rawFindings.add(service.getRawReport());
187+
rawFindings.add(zapService.getRawReport());
188188

189189
if (config.isFilterScannerResults()) {
190190
log.info("Removing duplicate findings");
@@ -223,27 +223,28 @@ private List<Finding> executeSpider(Target target, String contextId, String user
223223
ZapReplacerRule[] zapReplacerRules = target.getAttributes().getZapReplacerRules();
224224

225225
log.debug("Start Spider with URL: " + target.getLocation());
226-
String scanId = (String) service.startSpiderAsUser(target.getLocation(), spiderApiSpecUrl,
226+
String scanId = zapService.startSpiderAsUser(target.getLocation(), spiderApiSpecUrl,
227227
spiderMaxDepth, contextId, userId, zapReplacerRules);
228-
return service.retrieveSpiderResult(scanId);
228+
return zapService.retrieveSpiderResult(scanId);
229229
}
230230

231231
private List<Finding> executeScanner(Target target, String contextId, String userId) throws ClientApiException {
232-
log.debug("Start Sitemap recreation");
233-
service.recallTarget(target);
234232
Integer delayInMs = target.getAttributes().getScannerDelayInMs();
235233
Integer threadsPerHost = target.getAttributes().getThreadsPerHost();
236234
ZapReplacerRule[] zapReplacerRules = target.getAttributes().getZapReplacerRules();
237235

236+
log.debug("Start Sitemap recreation");
237+
zapService.recallTarget(target, zapReplacerRules);
238+
238239
log.debug("Start Scanner with URL: " + target.getLocation());
239-
String scanId = (String) service.startScannerAsUser(target.getLocation(), contextId, userId, delayInMs, threadsPerHost, zapReplacerRules);
240-
return service.retrieveScannerResult(scanId, target.getLocation());
240+
String scanId = zapService.startScannerAsUser(target.getLocation(), contextId, userId, delayInMs, threadsPerHost, zapReplacerRules);
241+
return zapService.retrieveScannerResult(scanId, target.getLocation());
241242
}
242243

243244
private String configureScannerContext(String targetUrl, Target target) throws ClientApiException {
244245
ZapTargetAttributes attributes = target.getAttributes();
245246
// Create a new Context for all the targets belonging to this context
246-
return service.createContext(targetUrl, attributes.getScannerIncludeRegex(), attributes.getScannerExcludeRegex());
247+
return zapService.createContext(targetUrl, attributes.getScannerIncludeRegex(), attributes.getScannerExcludeRegex());
247248
}
248249

249250
private String configureAuthentication(Target target, String contextId) throws ClientApiException, UnsupportedEncodingException {
@@ -260,7 +261,7 @@ private String configureAuthentication(Target target, String contextId) throws C
260261
String csrfToken = target.getAttributes().getCsrfTokenId();
261262

262263
if (authentication) {
263-
return service.configureAuthentication(
264+
return zapService.configureAuthentication(
264265
contextId, loginSite,
265266
usernameFieldId, passwordFieldId,
266267
loginUser, password,
@@ -278,7 +279,7 @@ private void completeTask(ZapTask task, JobEventPublisher publisher, List<Findin
278279
CompleteTask completedTask = taskService.completeTask(task, findings, rawFindingsString, zapTopic);
279280
publisher.info("Completed " + ((zapTopic == ZapTopic.ZAP_SCANNER) ? "scanner" : "spider") + " task: " + completedTask.getJobId());
280281

281-
service.clearSession();
282+
zapService.clearSession();
282283
} catch (JsonProcessingException e) {
283284
log.warn("Could not persist rawFindings");
284285
}

src/main/java/io/securecodebox/zap/service/engine/EngineTaskApiClient.java

Lines changed: 4 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -87,25 +87,13 @@ public void init() {
8787
* @return Returns true if the configured SCB Engine API is available and at least one processModell is deployed.
8888
*/
8989
boolean isApiAvailable() {
90-
return (this.countProcesses() > 0);
91-
}
92-
93-
/**
94-
* @return Returns the number of currently deployed process models which are available at the SCB Engine.
95-
*/
96-
int countProcesses() {
97-
98-
String url = config.getProcessEngineApiUrl() + "/box/processes/";
99-
log.debug("Call countProcesses() via {}", url);
90+
String url = config.getProcessEngineApiUrl() + "/status";
91+
log.debug("Call engine status via {}", url);
10092

10193
ResponseEntity<String> response = restTemplate.getForEntity(url, String.class);
102-
log.debug(String.format("Result for countProcesses(): %s", response));
94+
log.debug(String.format("Engine api status: %s", response));
10395

104-
if (response.getStatusCode().is2xxSuccessful() && response.getHeaders().getContentType().isCompatibleWith(MediaType.APPLICATION_JSON) && !response.toString().isEmpty()) {
105-
return response.toString().split("id").length;
106-
} else {
107-
return 0;
108-
}
96+
return response.getStatusCode().is2xxSuccessful();
10997
}
11098

11199
ZapTask fetchAndLockTask(ZapTopic zapTopic, String jobId) {

src/main/java/io/securecodebox/zap/service/engine/ZapTaskService.java

Lines changed: 2 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -88,11 +88,9 @@ public boolean isApiAvailable() {
8888
@Override
8989
public StatusDetail statusDetail() {
9090
try {
91-
boolean isApiAvailable = this.isApiAvailable();
92-
93-
if (isApiAvailable) {
91+
if (this.isApiAvailable()) {
9492
log.debug("Internal health check: OK");
95-
return StatusDetail.statusDetail("Engine SCB API", Status.OK, "The Engine API is up and running", singletonMap("Deployed Processes", String.valueOf(this.taskApiClient.countProcesses())));
93+
return StatusDetail.statusDetail("Engine SCB API", Status.OK, "The Engine API is up and running");
9694
} else {
9795
return StatusDetail.statusDetail("Engine SCB API", Status.WARNING, "Couldn't reach the Engine API!");
9896
}
Lines changed: 129 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,129 @@
1+
package io.securecodebox.zap.service.zap;
2+
3+
import io.securecodebox.zap.service.engine.model.zap.ZapReplacerRule;
4+
import javax.validation.constraints.NotNull;
5+
import lombok.extern.slf4j.Slf4j;
6+
import org.zaproxy.clientapi.core.ApiResponseList;
7+
import org.zaproxy.clientapi.core.ApiResponseSet;
8+
import org.zaproxy.clientapi.core.ClientApi;
9+
import org.zaproxy.clientapi.core.ClientApiException;
10+
11+
@Slf4j
12+
public class ReplacerPluginConfigurator {
13+
14+
private ClientApi api;
15+
16+
public ReplacerPluginConfigurator(ClientApi api) {
17+
this.api = api;
18+
}
19+
20+
public void configureZapWithReplacerRules(ZapReplacerRule[] replacerRules) throws ClientApiException {
21+
resetReplacerRules();
22+
if (replacerRules != null && replacerRules.length > 0) {
23+
log.debug("Adding {} custom ZAP replacer rules", replacerRules.length);
24+
addReplacerRules(replacerRules);
25+
} else {
26+
log.info("No custom ZAP replacer rule defined.");
27+
}
28+
}
29+
30+
/**
31+
* Gets and converts the API wrapper request "replacer.rules()"
32+
*
33+
* @return array of replacer rules
34+
* @throws ClientApiException can be thrown for any api request
35+
*/
36+
final ZapReplacerRule[] getCurrentReplacerRules() throws ClientApiException {
37+
return ((ApiResponseList) api.replacer.rules()).getItems().stream()
38+
.map(i -> ((ApiResponseSet) i))
39+
.map(i -> {
40+
ZapReplacerRule rule = new ZapReplacerRule();
41+
rule.setMatchType(i.getStringValue("matchType"));
42+
rule.setDescription(i.getStringValue("description"));
43+
rule.setMatchString(i.getStringValue("matchString"));
44+
rule.setInitiators(i.getStringValue("initiators"));
45+
rule.setMatchRegex(i.getStringValue("matchRegex"));
46+
rule.setReplacement(i.getStringValue("replacement"));
47+
rule.setEnabled(i.getStringValue("enabled"));
48+
return rule;
49+
})
50+
.toArray(ZapReplacerRule[]::new);
51+
}
52+
53+
/**
54+
* Adds ZAP replacer rules
55+
*
56+
* @param rules
57+
* @throws ClientApiException thrown if at least one rule cannot be set
58+
*/
59+
void addReplacerRules(ZapReplacerRule[] rules) throws ClientApiException {
60+
if (rules != null && rules.length > 0) {
61+
log.debug("Adding #{} exiting replacer rules", rules.length);
62+
for (ZapReplacerRule rule: rules) {
63+
if (rule != null) {
64+
addReplacerRule(rule);
65+
} else {
66+
log.warn("Couldn't add the replacer rule, the rule must not be null ot empty.");
67+
}
68+
}
69+
} else {
70+
log.warn("There is no replacer rule to add.");
71+
}
72+
}
73+
74+
void resetReplacerRules() throws ClientApiException {
75+
log.debug("Resetting ZAP replacer rules");
76+
ZapReplacerRule[] currentRules = getCurrentReplacerRules();
77+
if (currentRules != null && currentRules.length > 0) {
78+
removeReplacerRules(currentRules);
79+
}
80+
}
81+
82+
/**
83+
* Adds ZAP replacer rule
84+
*
85+
* @param rule
86+
* @throws ClientApiException thrown if rule cannot be set
87+
*/
88+
private void addReplacerRule(@NotNull ZapReplacerRule rule) throws ClientApiException {
89+
api.replacer.addRule(
90+
rule.getDescription(),
91+
rule.getEnabled(),
92+
rule.getMatchType(),
93+
rule.getMatchRegex(),
94+
rule.getMatchString(),
95+
rule.getReplacement(),
96+
rule.getInitiators());
97+
}
98+
99+
/**
100+
* Removes the given list of ZAP replacer rules.
101+
*
102+
* @param rules The list of ZAP replacer rules to remove.
103+
* @throws ClientApiException thrown if at least one of the rules cannot be removed
104+
*/
105+
private void removeReplacerRules(@NotNull ZapReplacerRule[] rules) throws ClientApiException {
106+
if (rules != null && rules.length > 0) {
107+
log.debug("Removing #{} exiting replacer rules", rules.length);
108+
for (ZapReplacerRule rule : rules){
109+
removeReplacerRule(rule);
110+
}
111+
} else {
112+
log.warn("There are no replacer rules to remove.");
113+
}
114+
}
115+
116+
/**
117+
* Removes a single ZAP replacer rule.
118+
*
119+
* @param rule The ZAP replacer rule to remove.
120+
* @throws ClientApiException thrown if rule cannot be removed
121+
*/
122+
private void removeReplacerRule(@NotNull ZapReplacerRule rule) throws ClientApiException {
123+
if (rule != null) {
124+
api.replacer.removeRule(rule.getDescription());
125+
} else {
126+
log.warn("You can't remove a replacer rule which is null.");
127+
}
128+
}
129+
}

0 commit comments

Comments
 (0)