diff --git a/azure-pipelines.yml b/azure-pipelines.yml deleted file mode 100644 index e341fc3..0000000 --- a/azure-pipelines.yml +++ /dev/null @@ -1,100 +0,0 @@ -# HawkScan Scanning in Azure Pipelines -# This is a demonstration of running JavaSpringVulny (a web applications) in azure-pipelines (a cicd pipeline) with the StackHawk extension (DAST testing) -# https://marketplace.visualstudio.com/items?itemName=StackHawk.stackhawk-extensions -# https://github.com/kaakaww/javaspringvulny -# https://aka.ms/yaml - -# matrix builds for different build systems -# use `condition: eq(variables['imageName'], 'ubuntu-latest')` property to filter tasks for specific operating systems - -strategy: - matrix: - windows-msi: - imageName: "windows-latest" - installerType: "msi" - windows-zip: - imageName: "windows-latest" - installerType: "zip" - linux-zip: - imageName: "ubuntu-latest" - installerType: "zip" - windows-auto: - imageName: "windows-latest" - installerType: "auto" - linux-auto: - imageName: "ubuntu-latest" - installerType: "auto" - -pool: - vmImage: $(imageName) - -trigger: none - -steps: - - checkout: self - - - script: echo Azure Pipelines build for $(imageName)! - displayName: "🦅 $(imageName)" - - # install the latest version of hawkscan - - task: HawkScanInstall@1 - inputs: - version: "4.0.3" - installerType: "$(installerType)" - condition: not(and(eq(variables['installerType'], 'auto'), eq(variables['imageName'], 'ubuntu-latest'))) - - - task: HawkScanInstall@1 - inputs: - version: "4.0.3" - installerType: "$(installerType)" - installPath: '/home/vsts/custom' - condition: and(eq(variables['installerType'], 'auto'), eq(variables['imageName'], 'ubuntu-latest')) - - # azure pipelines default jdk is 8, so we upgrade to 11 to run JavaSpringVulny - # the hawkscan msi bundles java with it, so this step isn't necesarry for running HawkScan - - task: JavaToolInstaller@0 - inputs: - versionSpec: "17" - jdkArchitectureOption: "x64" - jdkSourceOption: "PreInstalled" - - # download, then start javaspringVulny in the background - - script: | - curl -Ls https://github.com/kaakaww/javaspringvulny/releases/download/0.2.0/java-spring-vuly-0.2.0.jar -o ./java-spring-vuly-0.2.0.jar - java -jar ./java-spring-vuly-0.2.0.jar & - displayName: Start JavaSpringVulny on linux - condition: eq(variables['imageName'], 'ubuntu-latest') - - # download, then start javaspringVulny in the background - - powershell: | - Invoke-WebRequest -Uri "https://github.com/kaakaww/javaspringvulny/releases/download/0.2.0/java-spring-vuly-0.2.0.jar" -OutFile "java-spring-vuly-0.2.0.jar" - java --version - Start-Process java -ArgumentList "-jar","java-spring-vuly-0.2.0.jar","--spring.profiles.active=windows" - displayName: Start JavaSpringVulny on windows with gradle in the background - env: - SPRING_DATASOURCE_URL: 'jdbc:h2:file:D:\\a\\1\\db\\vulny;DB_CLOSE_ON_EXIT=FALSE;AUTO_RECONNECT=TRUE' - condition: eq(variables['imageName'], 'windows-latest') - - # run hawkscan with the StackHawk Azure Extension - - task: RunHawkScan@1 - inputs: - configFile: "stackhawk.yml" - version: "4.0.3" - env: - HAWK_API_KEY: $(HAWK_API_KEY) # use variables in the azure devops ui to configure secrets and env vars - APP_ENV: $(imageName) - APP_ID: $(appId2) - SARIF_ARTIFACT: true - condition: not(and(eq(variables['installerType'], 'auto'), eq(variables['imageName'], 'ubuntu-latest'))) - - - task: RunHawkScan@1 - inputs: - configFile: "stackhawk.yml" - version: "4.0.3" - installPath: '/home/vsts/custom' - env: - HAWK_API_KEY: $(HAWK_API_KEY) # use variables in the azure devops ui to configure secrets and env vars - APP_ENV: $(imageName) - APP_ID: $(appId2) - SARIF_ARTIFACT: true - condition: and(eq(variables['installerType'], 'auto'), eq(variables['imageName'], 'ubuntu-latest')) diff --git a/hawkscripts/README.md b/hawkscripts/README.md deleted file mode 100644 index 5731d3e..0000000 --- a/hawkscripts/README.md +++ /dev/null @@ -1,33 +0,0 @@ - -## Hawkscripts - -A directory of kotlin scripts to customize [HawkScan](https://docs.stackhawk.com/stackhawk-cli/#install-with-zip-file) with -[IntelliJ IDE](https://www.jetbrains.com/idea/download) support via gradle. - -To enable IDE support... - -1. Open a shell in the root of the javaspringvulny repository and run... - ```shell - ./gradlew :hawkscripts:download - ``` - This will download the hawk scripts sdk zip into the `hawkscripts/build` directory as - required by the dependencies defined in [hawkscripts.gradle.kts](hawkscripts.gradle.kts). -1. Start the [IntelliJ IDE](https://www.jetbrains.com/idea/download) -1. Open javaspringvulny as a new gradle project - - ![intellij-new-project-1.png](help-images%2Fintellij-new-project-1.png) - - ![intellij-new-project-2.png](help-images%2Fintellij-new-project-2.png) - - ![intellij-new-project-3.png](help-images%2Fintellij-new-project-3.png) - -1. **Wait for the indexer!** - ![intellij-new-project-4.png](help-images%2Fintellij-new-project-4.png) - -When indexing is complete open any of the `.kts` files in the -defined source directories `authentication, session, httpsender, active, proxy` -to see activated code highlighting, auto-completion, and inline compilation errors. - -Use the [hawk perch]() and [hawk validate auth --watch]() to -develop and test authentication and session scripts against your -running web API's. \ No newline at end of file diff --git a/hawkscripts/active/fuzzer.kts b/hawkscripts/active/fuzzer.kts deleted file mode 100644 index f7a82ad..0000000 --- a/hawkscripts/active/fuzzer.kts +++ /dev/null @@ -1,69 +0,0 @@ -import com.github.javafaker.Faker -import com.stackhawk.hste.extension.script.ScriptVars -import com.stackhawk.hste.extension.scripts.scanrules.ScriptsActiveScanner -import org.apache.log4j.LogManager -import org.parosproxy.paros.network.HttpMessage - -val logger = LogManager.getLogger("fuzzer") - -val faker = Faker() -val scriptVars = ScriptVars.getScriptVars("fuzzer.kts") - -fun alert(activeScanner: ScriptsActiveScanner, msg: HttpMessage, evidence: String, param: String, fuzzedParam: String) { - val risk = 2 // 0: info, 1: low, 2: medium, 3: high - val confidence = 3 // 0: falsePositive, 1: low, 2: medium, 3: high, 4: confirmed - val title = "Fuzzer found a 5xx error" - val description = "Fuzzer was able to find a 5xx error" - val solution = "Handle bad input and never throw a 5xx error" - val reference = "" - val otherInfo = "fuzzed param: $param=$fuzzedParam" - val pluginId = 1000000; //Custom Plugin ID - - activeScanner.newAlert() - .setPluginId(pluginId) - .setRisk(risk) - .setConfidence(confidence) - .setName(title) - .setDescription(description) - .setEvidence(evidence) - .setOtherInfo(otherInfo) - .setSolution(solution) - .setReference(reference) - .setMessage(msg) - .raise(); -} - -fun scanNode(activeScanner: ScriptsActiveScanner, origMessage: HttpMessage) { - logger.debug("scanNode fuzzer hook: ${origMessage.requestHeader.uri}") - return -} - -fun scan(activeScanner: ScriptsActiveScanner, origMessage: HttpMessage, param: String, value: String) { - logger.debug("scan fuzzer hook: ${origMessage.requestHeader.uri} | ${param}=${value}") - val iterations = scriptVars["iterations"]?.toInt() ?: 1 - val stringStartLength = scriptVars["stringStartLength"]?.toInt() ?: 1 - val stringEndLength = scriptVars["stringEndLength"]?.toInt() ?: 100 - (1..iterations).forEach { i -> - val msg = origMessage.cloneRequest() - val fuzzedParamValue = if (i % 2 == 0) { - faker.lorem().characters(stringStartLength, stringEndLength) - } else { - faker.harryPotter().spell() - } - - if (param.isNotBlank()) { - activeScanner.setParam(msg, param, fuzzedParamValue) - } - try { - activeScanner.sendAndReceive(msg, false, false) - if (msg.responseHeader.statusCode >= 500) { - logger.debug("request: ${msg.requestHeader}${msg.requestBody}") - alert(activeScanner, msg, msg.responseHeader.primeHeader, param, fuzzedParamValue) - logger.debug("response: ${msg.responseHeader.statusCode} ${msg.responseHeader}${msg.responseBody}") - } - } catch (e: Exception) { - logger.error("Error sending request: ${e.message}") - } - } - -} \ No newline at end of file diff --git a/hawkscripts/authentication/form-auth-multi.kts b/hawkscripts/authentication/form-auth-multi.kts deleted file mode 100644 index 423d952..0000000 --- a/hawkscripts/authentication/form-auth-multi.kts +++ /dev/null @@ -1,87 +0,0 @@ -import com.fasterxml.jackson.databind.ObjectMapper -import com.stackhawk.hste.extension.talon.HawkConfExtensions -import com.stackhawk.hste.extension.talon.cleanHost -import com.stackhawk.hste.extension.talon.hawkscan.ExtensionTalonHawkscan -import org.apache.commons.httpclient.URI -import org.apache.log4j.LogManager -import org.parosproxy.paros.control.Control -import org.parosproxy.paros.network.HttpHeader -import org.parosproxy.paros.network.HttpMessage -import org.parosproxy.paros.network.HttpRequestHeader -import com.stackhawk.hste.authentication.AuthenticationHelper -import com.stackhawk.hste.authentication.GenericAuthenticationCredentials - -val logger = LogManager.getLogger("form-auth-multi") - -val talon = Control - .getSingleton() - .extensionLoader - .getExtension(ExtensionTalonHawkscan::class.java) - -fun hostUrl(path: String): String { - return "${HawkConfExtensions.cleanHost(talon.talonHawkScanConf.hawkscanConf.app)}$path" -} - -// This function is called before a scan is started and when the loggedOutIndicator is matched indicating re-authentication is needed. -fun authenticate( - helper: AuthenticationHelper, - paramsValues: Map, - credentials: GenericAuthenticationCredentials, -): HttpMessage { - logger.info("Kotlin auth template") - logger.info("TalonConf: ${talon.talonHawkScanConf}") - logger.info("host ${talon.talonHawkScanConf.hawkscanConf.app.cleanHost()}") - - val mapper = ObjectMapper() - val payload = mapper.writeValueAsString( - mapOf( - "username" to credentials.getParam("username"), - "password" to credentials.getParam("password"), - ), - ) - - logger.info("payload? $payload") - - val loginPagePathUrl = hostUrl(paramsValues["loginPagePath"]!!) - logger.info("TARGET_URL: $loginPagePathUrl") - val msg = helper.prepareMessage() - msg.requestHeader = HttpRequestHeader( - HttpRequestHeader.GET, - URI(loginPagePathUrl, true), - HttpHeader.HTTP11, - ) - logger.info("msg: ${msg.requestHeader} ${msg.requestBody} ${msg.requestHeader.headers.size}") - msg.requestHeader.headers.forEach { println(it) } - helper.sendAndReceive(msg) - logger.info("resp: ${msg.responseHeader} ${msg.responseBody} ") - - if (msg.responseBody.length() > 0) { - val map = mapper.readValue(msg.responseBody.bytes, Map::class.java) - logger.info("map $map") - } else { - logger.info("no body to parse") - } - return msg -} - -// The required parameter names for your script, your script will throw an error if these are not supplied in the script.parameters configuration. -fun getRequiredParamsNames(): Array { - return arrayOf("loginPagePath", "loginPage", "remember") -} - -// The required credential parameters, your script will throw an error if these are not supplied in the script.credentials configuration. -fun getCredentialsParamsNames(): Array { - return arrayOf("username", "password") -} - -fun getOptionalParamsNames(): Array { - return arrayOf("logging", "formType", "csrfExtra") -} - -fun getLoggedInIndicator(): String { - return "" -} - -fun getLoggedOutIndicator(): String { - return "" -} diff --git a/hawkscripts/authentication/okta-client-credentials-basic.kts b/hawkscripts/authentication/okta-client-credentials-basic.kts deleted file mode 100644 index 0fd8667..0000000 --- a/hawkscripts/authentication/okta-client-credentials-basic.kts +++ /dev/null @@ -1,85 +0,0 @@ -import com.fasterxml.jackson.databind.ObjectMapper -import com.fasterxml.jackson.databind.node.ObjectNode -import java.util.Base64 -import java.util.TreeSet -import org.apache.commons.httpclient.URI -import org.apache.hc.client5.http.auth.AuthenticationException -import org.apache.hc.core5.http.ContentType -import org.apache.hc.core5.http.HttpHeaders -import org.apache.hc.core5.http.Method -import org.apache.log4j.LogManager -import org.parosproxy.paros.network.HtmlParameter -import org.parosproxy.paros.network.HttpHeader -import org.parosproxy.paros.network.HttpMessage -import org.parosproxy.paros.network.HttpRequestHeader -import com.stackhawk.hste.authentication.AuthenticationHelper -import com.stackhawk.hste.authentication.GenericAuthenticationCredentials - -val logger = LogManager.getLogger("okta-auth") -val mapper = ObjectMapper() - -fun authenticate( - helper: AuthenticationHelper, - paramsValues: Map, - credentials: GenericAuthenticationCredentials, -): HttpMessage { - logger.info("auth hook") - - val oktaDomain = paramsValues["okta_domain"] - val scope = paramsValues["scope"] - val clientId = credentials.getParam("client_id") - val clientSecret = credentials.getParam("client_secret") - val base64Creds = Base64.getEncoder().encodeToString("$clientId:$clientSecret".toByteArray()) - - - val msg = helper.prepareMessage() - msg.requestHeader = HttpRequestHeader( - Method.POST.name, - URI("https://$oktaDomain/oauth2/default/v1/token", true), - HttpHeader.HTTP11 - ) - msg.requestHeader.addHeader(HttpHeaders.ACCEPT, ContentType.APPLICATION_JSON.toString()) - msg.requestHeader.addHeader(HttpHeaders.AUTHORIZATION, "Basic $base64Creds") - - val formTree = TreeSet() - formTree.add(HtmlParameter(HtmlParameter.Type.form, "grant_type", "client_credentials")) - formTree.add(HtmlParameter(HtmlParameter.Type.form, "scope", scope)) - msg.requestBody.setFormParams(formTree) - msg.requestHeader.contentLength = msg.requestBody.length() - - logger.info("::::::auth request:::::\n${msg.requestHeader}${msg.requestBody}") - - helper.sendAndReceive(msg) - - logger.info("::::::auth response:::::\n${msg.responseHeader}${msg.responseBody}") - - // Throw an authentication exception if the status code is not 2xx - if (!(200..299).contains(msg.responseHeader.statusCode)) { - val jsonObject = mapper.readValue(msg.responseBody.bytes, ObjectNode::class.java) - val err = jsonObject.get("error").asText() - val errDesc = jsonObject.get("error_description").asText() - throw AuthenticationException("$err $errDesc") - } - - return msg -} - -fun getRequiredParamsNames(): Array { - return arrayOf("okta_domain", "scope") -} - -fun getCredentialsParamsNames(): Array { - return arrayOf("client_id", "client_secret") -} - -fun getOptionalParamsNames(): Array { - return arrayOf() -} - -fun getLoggedInIndicator(): String { - return "" -} - -fun getLoggedOutIndicator(): String { - return "" -} diff --git a/hawkscripts/build/hawkscriptsdk.version b/hawkscripts/build/hawkscriptsdk.version deleted file mode 100644 index ae15394..0000000 --- a/hawkscripts/build/hawkscriptsdk.version +++ /dev/null @@ -1 +0,0 @@ -4.5.0 \ No newline at end of file diff --git a/hawkscripts/hawkscripts.gradle.kts b/hawkscripts/hawkscripts.gradle.kts deleted file mode 100644 index 4f31ba8..0000000 --- a/hawkscripts/hawkscripts.gradle.kts +++ /dev/null @@ -1,115 +0,0 @@ -import java.net.HttpURLConnection -import java.net.URL -import java.nio.file.Files -import kotlin.math.roundToLong - -plugins { - kotlin("jvm") version "1.8.22" -} - -val kotlinVersion = "1.8.22" -val hawkScriptSdkVersion = lazy { sdkVersion() } -val sdkZipName = lazy { "hawkscript-sdk-${hawkScriptSdkVersion.value}.zip" } -val hawkScriptSDKZip = lazy { "$buildDir/${sdkZipName.value}" } - -tasks.compileKotlin.configure { - if (!File(hawkScriptSDKZip.value).exists()) { - logger.warn("hawkscripts sdk zip ${hawkScriptSDKZip.value} not found") - logger.lifecycle("Run ./gradlew :hawkscripts:download to enable kotlin scripting support for IntelliJ") - } - enabled = File(hawkScriptSDKZip.value).exists() -} - -kotlin { - sourceSets { - main { - kotlin { - srcDirs( - "authentication", - "session", - "httpsender", - "active", - "proxy", - ) - } - } - } -} - -repositories { - mavenCentral() -} - -dependencies { - compileOnly("org.jetbrains.kotlin:kotlin-stdlib:$kotlinVersion") - compileOnly("org.jetbrains.kotlin:kotlin-script-runtime:$kotlinVersion") - compileOnly(zipTree(hawkScriptSDKZip.value)) -} -tasks.register("download") { - - group = "StackHawk" - description = "Download the latest hawk scripting sdk zip" - - doLast { - - Files.createDirectories(buildDir.toPath()) - val localSdkZip = File("$buildDir/${sdkZipName.value}") - if (!localSdkZip.exists()) { - val hawkscriptSdkUrl = URL("https://download.stackhawk.com/hawk/sdk/${sdkZipName.value}") - val zipConn = hawkscriptSdkUrl.openConnection() as HttpURLConnection - zipConn.connect() - if ((200..299).contains(zipConn.responseCode)) { - logger.lifecycle("Downloading $hawkscriptSdkUrl -> $localSdkZip") - val delay = 1000L - var curLen = 0 - val len = zipConn.getHeaderField("Content-Length").toLong() - val input = zipConn.inputStream - localSdkZip.outputStream().use { output -> - var buf = ByteArray(8192) - var c = input.read(buf, 0, buf.size) - var lastPct = 0L - while (c != -1) { - curLen += c - output.write(buf, 0, c) - c = input.read(buf, 0, buf.size) - val pc = ((curLen.toDouble() / len.toDouble()) * 100).roundToLong() - if ((System.currentTimeMillis() % delay) == 0L && lastPct != pc) { - logger.lifecycle("${sdkZipName.value} [${curLen / 1024 / 1024}mb] ${pc}%") - lastPct = pc - } - } - val pc = ((curLen.toDouble() / len.toDouble()) * 100).roundToLong() - logger.lifecycle("${sdkZipName.value} [${curLen / 1024 / 1024}mb] ${pc}%") - } - } else { - logger.error("Error downloading $hawkscriptSdkUrl ${zipConn.responseMessage}") - } - } else { - logger.lifecycle("latest hawkscan sdk already found: ${"$buildDir/${sdkZipName.value}"}") - } - - } -} - -fun sdkVersion(): String { - val verFile = File("$buildDir/hawkscriptsdk.version") - val ret = if (verFile.exists()) { - verFile.readText() - } else { - downloadSdkVersion() - verFile.readText() - } - return ret -} - -fun downloadSdkVersion() { - Files.createDirectories(buildDir.toPath()) - val hawkscanVersionUrl = URL("https://api.stackhawk.com/hawkscan/version") - val verisionConn = hawkscanVersionUrl.openConnection() as HttpURLConnection - verisionConn.connect() - val version = String(verisionConn.inputStream.readAllBytes()) - File("$buildDir/hawkscriptsdk.version").outputStream().use { - it.write(version.toByteArray()) - } -} - diff --git a/hawkscripts/help-images/intellij-new-project-1.png b/hawkscripts/help-images/intellij-new-project-1.png deleted file mode 100644 index b01fcbb..0000000 Binary files a/hawkscripts/help-images/intellij-new-project-1.png and /dev/null differ diff --git a/hawkscripts/help-images/intellij-new-project-2.png b/hawkscripts/help-images/intellij-new-project-2.png deleted file mode 100644 index 7fa228a..0000000 Binary files a/hawkscripts/help-images/intellij-new-project-2.png and /dev/null differ diff --git a/hawkscripts/help-images/intellij-new-project-3.png b/hawkscripts/help-images/intellij-new-project-3.png deleted file mode 100644 index 94b3171..0000000 Binary files a/hawkscripts/help-images/intellij-new-project-3.png and /dev/null differ diff --git a/hawkscripts/help-images/intellij-new-project-4.png b/hawkscripts/help-images/intellij-new-project-4.png deleted file mode 100644 index af8956c..0000000 Binary files a/hawkscripts/help-images/intellij-new-project-4.png and /dev/null differ diff --git a/hawkscripts/httpsender/custom-sender.kts b/hawkscripts/httpsender/custom-sender.kts deleted file mode 100644 index fe0a2d3..0000000 --- a/hawkscripts/httpsender/custom-sender.kts +++ /dev/null @@ -1,22 +0,0 @@ -import com.stackhawk.hste.extension.talon.hawkscan.ExtensionTalonHawkscan -import org.apache.log4j.LogManager -import org.parosproxy.paros.control.Control -import org.parosproxy.paros.network.HttpMessage -import com.stackhawk.hste.extension.script.HttpSenderScriptHelper - -val logger = LogManager.getLogger("custom-http-sender") - -val talon = Control - .getSingleton() - .extensionLoader - .getExtension(ExtensionTalonHawkscan::class.java) - -// modify a request before it's sent to the web application -fun sendingRequest(msg: HttpMessage, initiator: Int, helper: HttpSenderScriptHelper) { - logger.info("req ${msg.requestHeader.uri}") - msg.requestHeader.setHeader("X-HawkScanId", talon.talonHawkScanConf.scanId) -} - -// modify the response from the web application before sending to the client -fun responseReceived(msg: HttpMessage, initiator: Int, helper: HttpSenderScriptHelper) { -} diff --git a/hawkscripts/httpsender/log-http-payloads.kts b/hawkscripts/httpsender/log-http-payloads.kts deleted file mode 100644 index 90ad55f..0000000 --- a/hawkscripts/httpsender/log-http-payloads.kts +++ /dev/null @@ -1,21 +0,0 @@ - -import org.apache.log4j.LogManager -import org.parosproxy.paros.network.HttpMessage -import com.stackhawk.hste.extension.script.HttpSenderScriptHelper - -val logger = LogManager.getLogger("log-http-payloads") - -// modify a request before it's sent to the web application -fun sendingRequest(msg: HttpMessage, initiator: Int, helper: HttpSenderScriptHelper) { - -} - -// modify the response from the web application before sending to the client -fun responseReceived(msg: HttpMessage, initiator: Int, helper: HttpSenderScriptHelper) { - val httpRequestAndResponse = msg.requestHeader.toString() + - msg.requestBody.toString() + - msg.responseHeader.toString() + - msg.responseBody.toString() - - logger.info("request/response: $httpRequestAndResponse") -} diff --git a/hawkscripts/session/jwt-session.kts b/hawkscripts/session/jwt-session.kts deleted file mode 100644 index 647cfc4..0000000 --- a/hawkscripts/session/jwt-session.kts +++ /dev/null @@ -1,62 +0,0 @@ -import com.fasterxml.jackson.databind.ObjectMapper -import com.fasterxml.jackson.databind.node.ObjectNode -import com.nimbusds.jwt.JWTClaimsSet -import com.nimbusds.jwt.SignedJWT -import java.time.Instant -import org.apache.log4j.LogManager -import com.stackhawk.hste.session.ScriptBasedSessionManagementMethodType -import com.stackhawk.hste.extension.script.ScriptVars - -val logger = LogManager.getLogger("okta-json-to-token") -val mapper = ObjectMapper() - -fun extractWebSession(sessionWrapper: ScriptBasedSessionManagementMethodType.SessionWrapper) { - - val tokenField = sessionWrapper.getParam("jwt_token_field") - val tokenType = sessionWrapper.getParam("token_type_field") ?: "Bearer" - - logger.info("get token from json: ${sessionWrapper.httpMessage.responseBody}") - val jsonObject = mapper.readValue(sessionWrapper.httpMessage.responseBody.bytes, ObjectNode::class.java) - val accessToken = jsonObject.get(tokenField).asText() - ScriptVars.setGlobalVar("auth_header_value", "$tokenType $accessToken") - - sessionWrapper.session.setValue("jwt", accessToken) - - val jwt = SignedJWT.parse(accessToken) - logger.info("jwt-expires: ${jwt.jwtClaimsSet.expirationTime}") - sessionWrapper.session.setValue("jwt_claims", jwt.jwtClaimsSet) -} - -fun processMessageToMatchSession(sessionWrapper: ScriptBasedSessionManagementMethodType.SessionWrapper) { - - val nowish = Instant.now().minusMillis(15000) - val jwtClaims = sessionWrapper.session.getValue("jwt_claims") as JWTClaimsSet? - val isExpired = jwtClaims?.expirationTime?.toInstant()?.isBefore(nowish) - - if (isExpired == true) { - logger.info("session expires @ ${jwtClaims.expirationTime}") - synchronized(this) { - sessionWrapper.httpMessage.requestingUser.authenticate() - } - } - - logger.debug("session-jwt: ${sessionWrapper.session.getValue("jwt")}") - - val hdrVal = ScriptVars.getGlobalVar("auth_header_value") - logger.debug("auth_header_value: $hdrVal") - if (!hdrVal.isNullOrEmpty()) { - sessionWrapper.httpMessage.requestHeader.setHeader("Authorization", hdrVal) - } - -} - -fun clearWebSessionIdentifiers(sessionWrapper: ScriptBasedSessionManagementMethodType.SessionWrapper) { -} - -fun getRequiredParamsNames(): Array { - return arrayOf("jwt_token_field") -} - -fun getOptionalParamsNames(): Array { - return arrayOf("token_type_field") -} \ No newline at end of file diff --git a/javaspringvulny_postman_collection.json b/javaspringvulny_postman_collection.json deleted file mode 100644 index 02e6a68..0000000 --- a/javaspringvulny_postman_collection.json +++ /dev/null @@ -1,723 +0,0 @@ -{ - "info": { - "_postman_id": "de483569-ba3b-449e-9688-e68dd4c2f743", - "name": "Postman Collection for JavaSpringVulny", - "schema": "https://schema.getpostman.com/json/collection/v2.1.0/collection.json", - "_exporter_id": "305641" - }, - "item": [ - { - "name": "api", - "item": [ - { - "name": "jwt", - "item": [ - { - "name": "users/search", - "item": [ - { - "name": "search All", - "request": { - "method": "GET", - "header": [ - { - "key": "Accept", - "value": "*/*" - } - ], - "url": { - "raw": "{{baseUrl}}/api/jwt/users/search/", - "host": [ - "{{baseUrl}}" - ], - "path": [ - "api", - "jwt", - "users", - "search", - "" - ] - } - }, - "response": [ - { - "name": "default response", - "originalRequest": { - "method": "GET", - "header": [], - "url": { - "raw": "{{baseUrl}}/api/jwt/users/search/", - "host": [ - "{{baseUrl}}" - ], - "path": [ - "api", - "jwt", - "users", - "search", - "" - ] - } - }, - "status": "OK", - "code": 200, - "_postman_previewlanguage": "text", - "header": [ - { - "key": "Content-Type", - "value": "*/*" - } - ], - "cookie": [], - "body": "ea nisi venia" - } - ] - }, - { - "name": "search", - "request": { - "method": "GET", - "header": [ - { - "key": "Accept", - "value": "*/*" - } - ], - "url": { - "raw": "{{baseUrl}}/api/jwt/users/search/:text", - "host": [ - "{{baseUrl}}" - ], - "path": [ - "api", - "jwt", - "users", - "search", - ":text" - ], - "variable": [ - { - "key": "text", - "value": "ea nisi venia", - "description": "(Required) " - } - ] - } - }, - "response": [ - { - "name": "default response", - "originalRequest": { - "method": "GET", - "header": [], - "url": { - "raw": "{{baseUrl}}/api/jwt/users/search/:text", - "host": [ - "{{baseUrl}}" - ], - "path": [ - "api", - "jwt", - "users", - "search", - ":text" - ], - "variable": [ - { - "key": "text", - "value": "ea nisi venia", - "description": "(Required) " - } - ] - } - }, - "status": "OK", - "code": 200, - "_postman_previewlanguage": "text", - "header": [ - { - "key": "Content-Type", - "value": "*/*" - } - ], - "cookie": [], - "body": "ea nisi venia" - } - ] - } - ] - }, - { - "name": "items/search", - "item": [ - { - "name": "search 1", - "request": { - "method": "POST", - "header": [ - { - "key": "Content-Type", - "value": "application/json" - }, - { - "key": "Accept", - "value": "*/*" - } - ], - "body": { - "mode": "raw", - "raw": "{\n \"searchText\": \"des\"\n}", - "options": { - "raw": { - "language": "json" - } - } - }, - "url": { - "raw": "{{baseUrl}}/api/jwt/items/search", - "host": [ - "{{baseUrl}}" - ], - "path": [ - "api", - "jwt", - "items", - "search" - ] - } - }, - "response": [ - { - "name": "default response", - "originalRequest": { - "method": "POST", - "header": [], - "body": { - "mode": "raw", - "raw": "{\n \"searchText\": \"des\"\n}", - "options": { - "raw": { - "language": "json" - } - } - }, - "url": { - "raw": "{{baseUrl}}/api/jwt/items/search", - "host": [ - "{{baseUrl}}" - ], - "path": [ - "api", - "jwt", - "items", - "search" - ] - } - }, - "status": "OK", - "code": 200, - "_postman_previewlanguage": "text", - "header": [ - { - "key": "Content-Type", - "value": "*/*" - } - ], - "cookie": [], - "body": "ea nisi venia" - } - ] - }, - { - "name": "search All 1", - "request": { - "method": "GET", - "header": [ - { - "key": "Accept", - "value": "*/*" - } - ], - "url": { - "raw": "{{baseUrl}}/api/jwt/items/search/", - "host": [ - "{{baseUrl}}" - ], - "path": [ - "api", - "jwt", - "items", - "search", - "" - ] - } - }, - "response": [ - { - "name": "default response", - "originalRequest": { - "method": "GET", - "header": [], - "url": { - "raw": "{{baseUrl}}/api/jwt/items/search/", - "host": [ - "{{baseUrl}}" - ], - "path": [ - "api", - "jwt", - "items", - "search", - "" - ] - } - }, - "status": "OK", - "code": 200, - "_postman_previewlanguage": "text", - "header": [ - { - "key": "Content-Type", - "value": "*/*" - } - ], - "cookie": [], - "body": "ea nisi venia" - } - ] - }, - { - "name": "search 2", - "request": { - "method": "GET", - "header": [ - { - "key": "Accept", - "value": "*/*" - } - ], - "url": { - "raw": "{{baseUrl}}/api/jwt/items/search/:text", - "host": [ - "{{baseUrl}}" - ], - "path": [ - "api", - "jwt", - "items", - "search", - ":text" - ], - "variable": [ - { - "key": "text", - "value": "ea nisi venia", - "description": "(Required) " - } - ] - } - }, - "response": [ - { - "name": "default response", - "originalRequest": { - "method": "GET", - "header": [], - "url": { - "raw": "{{baseUrl}}/api/jwt/items/search/:text", - "host": [ - "{{baseUrl}}" - ], - "path": [ - "api", - "jwt", - "items", - "search", - ":text" - ], - "variable": [ - { - "key": "text", - "value": "ea nisi venia", - "description": "(Required) " - } - ] - } - }, - "status": "OK", - "code": 200, - "_postman_previewlanguage": "text", - "header": [ - { - "key": "Content-Type", - "value": "*/*" - } - ], - "cookie": [], - "body": "ea nisi venia" - } - ] - } - ] - }, - { - "name": "signin", - "request": { - "method": "POST", - "header": [ - { - "key": "Content-Type", - "value": "application/json" - }, - { - "key": "Accept", - "value": "*/*" - } - ], - "body": { - "mode": "raw", - "raw": "{\n \"username\": \"laborum dolore\",\n \"password\": \"tempor ullamco\"\n}", - "options": { - "raw": { - "language": "json" - } - } - }, - "url": { - "raw": "{{baseUrl}}/api/jwt/auth/signin", - "host": [ - "{{baseUrl}}" - ], - "path": [ - "api", - "jwt", - "auth", - "signin" - ] - } - }, - "response": [ - { - "name": "default response", - "originalRequest": { - "method": "POST", - "header": [], - "body": { - "mode": "raw", - "raw": "{\n \"username\": \"laborum dolore\",\n \"password\": \"tempor ullamco\"\n}", - "options": { - "raw": { - "language": "json" - } - } - }, - "url": { - "raw": "{{baseUrl}}/api/jwt/auth/signin", - "host": [ - "{{baseUrl}}" - ], - "path": [ - "api", - "jwt", - "auth", - "signin" - ] - } - }, - "status": "OK", - "code": 200, - "_postman_previewlanguage": "text", - "header": [ - { - "key": "Content-Type", - "value": "*/*" - } - ], - "cookie": [], - "body": "ea nisi venia" - } - ] - } - ] - }, - { - "name": "basic/items/search", - "item": [ - { - "name": "search 3", - "request": { - "method": "GET", - "header": [ - { - "key": "Accept", - "value": "*/*" - } - ], - "url": { - "raw": "{{baseUrl}}/api/basic/items/search/", - "host": [ - "{{baseUrl}}" - ], - "path": [ - "api", - "basic", - "items", - "search", - "" - ] - } - }, - "response": [ - { - "name": "default response", - "originalRequest": { - "method": "GET", - "header": [], - "url": { - "raw": "{{baseUrl}}/api/basic/items/search/", - "host": [ - "{{baseUrl}}" - ], - "path": [ - "api", - "basic", - "items", - "search", - "" - ] - } - }, - "status": "OK", - "code": 200, - "_postman_previewlanguage": "text", - "header": [ - { - "key": "Content-Type", - "value": "*/*" - } - ], - "cookie": [], - "body": "ea nisi venia" - } - ] - }, - { - "name": "search 4", - "request": { - "method": "GET", - "header": [ - { - "key": "Accept", - "value": "*/*" - } - ], - "url": { - "raw": "{{baseUrl}}/api/basic/items/search/:text", - "host": [ - "{{baseUrl}}" - ], - "path": [ - "api", - "basic", - "items", - "search", - ":text" - ], - "variable": [ - { - "key": "text", - "value": "ea nisi venia", - "description": "(Required) " - } - ] - } - }, - "response": [ - { - "name": "default response", - "originalRequest": { - "method": "GET", - "header": [], - "url": { - "raw": "{{baseUrl}}/api/basic/items/search/:text", - "host": [ - "{{baseUrl}}" - ], - "path": [ - "api", - "basic", - "items", - "search", - ":text" - ], - "variable": [ - { - "key": "text", - "value": "ea nisi venia", - "description": "(Required) " - } - ] - } - }, - "status": "OK", - "code": 200, - "_postman_previewlanguage": "text", - "header": [ - { - "key": "Content-Type", - "value": "*/*" - } - ], - "cookie": [], - "body": "ea nisi venia" - } - ] - } - ] - }, - { - "name": "token/items/search", - "item": [ - { - "name": "search 5", - "request": { - "method": "GET", - "header": [ - { - "key": "Accept", - "value": "*/*" - } - ], - "url": { - "raw": "{{baseUrl}}/api/token/items/search/", - "host": [ - "{{baseUrl}}" - ], - "path": [ - "api", - "token", - "items", - "search", - "" - ] - } - }, - "response": [ - { - "name": "default response", - "originalRequest": { - "method": "GET", - "header": [], - "url": { - "raw": "{{baseUrl}}/api/token/items/search/", - "host": [ - "{{baseUrl}}" - ], - "path": [ - "api", - "token", - "items", - "search", - "" - ] - } - }, - "status": "OK", - "code": 200, - "_postman_previewlanguage": "text", - "header": [ - { - "key": "Content-Type", - "value": "*/*" - } - ], - "cookie": [], - "body": "ea nisi venia" - } - ] - }, - { - "name": "search 6", - "request": { - "method": "GET", - "header": [ - { - "key": "Accept", - "value": "*/*" - } - ], - "url": { - "raw": "{{baseUrl}}/api/token/items/search/:text", - "host": [ - "{{baseUrl}}" - ], - "path": [ - "api", - "token", - "items", - "search", - ":text" - ], - "variable": [ - { - "key": "text", - "value": "ea nisi venia", - "description": "(Required) " - } - ] - } - }, - "response": [ - { - "name": "default response", - "originalRequest": { - "method": "GET", - "header": [], - "url": { - "raw": "{{baseUrl}}/api/token/items/search/:text", - "host": [ - "{{baseUrl}}" - ], - "path": [ - "api", - "token", - "items", - "search", - ":text" - ], - "variable": [ - { - "key": "text", - "value": "ea nisi venia", - "description": "(Required) " - } - ] - } - }, - "status": "OK", - "code": 200, - "_postman_previewlanguage": "text", - "header": [ - { - "key": "Content-Type", - "value": "*/*" - } - ], - "cookie": [], - "body": "ea nisi venia" - } - ] - } - ] - } - ] - } - ], - "variable": [ - { - "key": "baseUrl", - "value": "https://localhost:9000", - "type": "string" - } - ] -} \ No newline at end of file diff --git a/local-hawk.sh b/local-hawk.sh deleted file mode 100755 index d7f69d7..0000000 --- a/local-hawk.sh +++ /dev/null @@ -1,5 +0,0 @@ -#!/usr/bin/env bash - -docker run --rm -e API_KEY=$LOCAL_HAWK_API_KEY -e SHAWK_RESULTS_ENDPOINT=http://host.docker.internal:6300/api/v1 -e SHAWK_AUTH_ENDPOINT=http://host.docker.internal:6200 -v $(pwd):/hawk:rw -it stackhawk/hawkscan:latest - -#docker run --rm -e API_KEY=$SANDBOX_HAWK_API_KEY -v $(pwd):/hawk:rw -it stackhawk/hawkscan:latest \ No newline at end of file diff --git a/scan-rules.conf b/scan-rules.conf deleted file mode 100644 index 52c0358..0000000 --- a/scan-rules.conf +++ /dev/null @@ -1,76 +0,0 @@ -# zap-full-scan rule configuration file -# Change WARN to IGNORE to ignore rule or FAIL to fail if rule matches -# Active scan rules set to IGNORE will not be run which will speed up the scan -# Only the rule identifiers are used - the names are just for info -# You can add your own messages to each rule by appending them after a tab on each line. -0 WARN (Directory Browsing - Active/release) -10010 WARN (Cookie No HttpOnly Flag - Passive/release) -10011 WARN (Cookie Without Secure Flag - Passive/release) -10015 WARN (Incomplete or No Cache-control and Pragma HTTP Header Set - Passive/release) -10016 FAIL (Web Browser XSS Protection Not Enabled - Passive/release) -10017 WARN (Cross-Domain JavaScript Source File Inclusion - Passive/release) -10019 WARN (Content-Type Header Missing - Passive/release) -10020 WARN (X-Frame-Options Header Scanner - Passive/release) -10021 WARN (X-Content-Type-Options Header Missing - Passive/release) -10023 WARN (Information Disclosure - Debug Error Messages - Passive/release) -10024 WARN (Information Disclosure - Sensitive Information in URL - Passive/beta) -10025 WARN (Information Disclosure - Sensitive Information in HTTP Referrer Header - Passive/beta) -10026 WARN (HTTP Parameter Override - Passive/beta) -10027 WARN (Information Disclosure - Suspicious Comments - Passive/beta) -10032 WARN (Viewstate Scanner - Passive/release) -10037 WARN (Server Leaks Information via "X-Powered-By" HTTP Response Header Field(s) - Passive/beta) -10040 WARN (Secure Pages Include Mixed Content - Passive/release) -10045 WARN (Source Code Disclosure - /WEB-INF folder - Active/release) -10048 WARN (Remote Code Execution - Shell Shock - Active/beta) -10054 WARN (Cookie Without SameSite Attribute - Passive/beta) -10055 WARN (CSP Scanner - Passive/release) -10056 WARN (X-Debug-Token Information Leak - Passive/beta) -10057 WARN (Username Hash Found - Passive/beta) -10061 WARN (X-AspNet-Version Response Header Scanner - Passive/beta) -10095 WARN (Backup File Disclosure - Active/beta) -10096 WARN (Timestamp Disclosure - Passive/beta) -10098 WARN (Cross-Domain Misconfiguration - Passive/beta) -10105 WARN (Weak Authentication Method - Passive/release) -10202 WARN (Absence of Anti-CSRF Tokens - Passive/release) -2 WARN (Private IP Disclosure - Passive/release) -20012 WARN (Anti CSRF Tokens Scanner - Active/beta) -20014 WARN (HTTP Parameter Pollution scanner - Active/beta) -20015 WARN (Heartbleed OpenSSL Vulnerability - Active/beta) -20016 WARN (Cross-Domain Misconfiguration - Active/beta) -20017 WARN (Source Code Disclosure - CVE-2012-1823 - Active/beta) -20018 WARN (Remote Code Execution - CVE-2012-1823 - Active/beta) -20019 WARN (External Redirect - Active/release) -3 WARN (Session ID in URL Rewrite - Passive/release) -30001 WARN (Buffer Overflow - Active/release) -30002 WARN (Format String Error - Active/release) -30003 WARN (Integer Overflow Error - Active/beta) -40003 WARN (CRLF Injection - Active/release) -40008 WARN (Parameter Tampering - Active/release) -40009 WARN (Server Side Include - Active/release) -40012 FAIL (Cross Site Scripting (Reflected) - Active/release) -40013 WARN (Session Fixation - Active/beta) -40014 FAIL (Cross Site Scripting (Persistent) - Active/release) -40016 FAIL (Cross Site Scripting (Persistent) - Prime - Active/release) -40017 FAIL (Cross Site Scripting (Persistent) - Spider - Active/release) -40018 FAIL (SQL Injection - Active/release) -40019 FAIL (SQL Injection - MySQL - Active/beta) -40020 FAIL (SQL Injection - Hypersonic SQL - Active/beta) -40021 FAIL (SQL Injection - Oracle - Active/beta) -40022 FAIL (SQL Injection - PostgreSQL - Active/beta) -40023 WARN (Possible Username Enumeration - Active/beta) -42 WARN (Source Code Disclosure - SVN - Active/beta) -50000 WARN (Script Active Scan Rules - Active/release) -50001 WARN (Script Passive Scan Rules - Passive/release) -6 WARN (Path Traversal - Active/release) -7 WARN (Remote File Inclusion - Active/release) -90001 WARN (Insecure JSF ViewState - Passive/release) -90011 WARN (Charset Mismatch - Passive/release) -90019 WARN (Server Side Code Injection - Active/release) -90020 WARN (Remote OS Command Injection - Active/release) -90021 WARN (XPath Injection - Active/beta) -90022 WARN (Application Error Disclosure - Passive/release) -90023 WARN (XML External Entity Attack - Active/beta) -90024 WARN (Generic Padding Oracle - Active/beta) -90025 WARN (Expression Language Injection - Active/beta) -90028 WARN (Insecure HTTP Method - Active/beta) -90033 WARN (Loosely Scoped Cookie - Passive/release) diff --git a/scripts/basic-auth.sh b/scripts/basic-auth.sh deleted file mode 100755 index a4e27e0..0000000 --- a/scripts/basic-auth.sh +++ /dev/null @@ -1,4 +0,0 @@ -#!/usr/bin/env bash - -# Base64 encode the username=user and password=password combo -echo -n "user:password" | base64 diff --git a/scripts/json-auth.sh b/scripts/json-auth.sh deleted file mode 100755 index cf74746..0000000 --- a/scripts/json-auth.sh +++ /dev/null @@ -1,10 +0,0 @@ -#!/usr/bin/env bash - -# Fetch a JWT token from JavaSpringVulny using the JSON signin endpoint -RESPONSE=$( curl --request POST 'https://localhost:9000/api/jwt/auth/signin' \ - --header 'Content-Type: application/json' \ - --data-raw '{"password": "password", "username": "user"}' \ - --silent --insecure ) - -# Extract the JWT token from the JSON response -echo $RESPONSE | jq '.token' -r diff --git a/scripts/multi-cookie-auth.sh b/scripts/multi-cookie-auth.sh deleted file mode 100755 index de3fc62..0000000 --- a/scripts/multi-cookie-auth.sh +++ /dev/null @@ -1,21 +0,0 @@ -#!/usr/bin/env bash - -# Request login (XLOGINID) and session (JSESSIONID) cookies from server -curl -k -c cookie-jar.txt https://localhost:9000/login-code -# Set local JSESSIONID variable to the JSESSIONID cookie -JSESSIONID=$(awk 'match($0, /JSESSIONID.*/){print substr($0, RSTART + 11, RLENGTH)}' cookie-jar.txt ) -# Set local XLOGINID variable to the XLOGINID cookie -XLOGINID=$(awk 'match($0, /XLOGINID.*/){print substr($0, RSTART + 9, RLENGTH)}' cookie-jar.txt) -# Request page with XLOGINID and JSESSIONID cookies and extract the _csrf token -CSRF=$(curl -k -b cookie-jar.txt \ - https://localhost:9000/login-form-multi | awk 'match($0,/_csrf".*/) { print substr($0, RSTART+14, RLENGTH -17)}') -# Log into the mutli cooke endpoint using XLOGINID and JSESSIONID cookies and username/password -curl -v -k \ - -d "_csrf=${CSRF}&loginCode=${XLOGINID}&username=user&password=password&remember=on" \ - -b cookie-jar.txt \ - -H "Content-Type: application/x-www-form-urlencoded" \ - "https://localhost:9000/login-form-multi" - -# Run HawkScan injecting local variables as environment variables -hawk scan -e JSESSIONID=${JSESSIONID} -e XLOGINID=${XLOGINID} ./stackhawk.d/stackhawk-multi-cookie-auth.yml - diff --git a/stackhawk-actions.yml b/stackhawk-actions.yml deleted file mode 100644 index 68f9e56..0000000 --- a/stackhawk-actions.yml +++ /dev/null @@ -1,63 +0,0 @@ -app: - # Update your applicationId - applicationId: ${APP_ID:9690bb4a-aa74-4813-bf93-fde705783f64} - env: ${APP_ENV:GitHub Actions} - host: ${APP_HOST:https://localhost:9000} - excludePaths: - - "/logout" - # - "/login-form-multi" - # - "/login-code" - antiCsrfParam: "_csrf" - # Configure Basic Authentication - authentication: - loggedInIndicator: "\\QSign Out\\E" - loggedOutIndicator: ".*Location:.*/login.*" - usernamePassword: - type: FORM - loginPath: /login - loginPagePath: /login - usernameField: username - passwordField: password - scanUsername: "user" - scanPassword: "password" - cookieAuthorization: - cookieNames: - - "JSESSIONID" - testPath: - path: /search - success: "HTTP.*200.*" - # Utilize OpenAPI Spec, Custom data & Faker - openApiConf: - # path: /openapi - filePath: openapi.yaml - fakerEnabled: true #default false - # includeAllMethods: true - includedMethods: - - POST - - PUT - customVariables: - - field: text - values: - - "$faker:uuid" - - field: searchText - values: - - "$faker:Crypto.sha512" - - "Donec ullamcorper nulla non metus auctor fringilla." - - field: username - values: - - "Andy Dwyer" - - field: password - values: - - "$faker:password" -hawk: - spider: - maxDurationMinutes: 5 -# config: -# - "scanner.analyser.redirectEqualsNotFound=false" -# - "scanner.analyser.followRedirect=true" -# Grab Commit SHA and Branch name -tags: - - name: _STACKHAWK_GIT_COMMIT_SHA - value: ${COMMIT_SHA:} - - name: _STACKHAWK_GIT_BRANCH - value: ${BRANCH_NAME:} \ No newline at end of file diff --git a/stackhawk.d/stackhawk-ajax.yml b/stackhawk.d/stackhawk-ajax.yml deleted file mode 100644 index 4561bfd..0000000 --- a/stackhawk.d/stackhawk-ajax.yml +++ /dev/null @@ -1,7 +0,0 @@ -hawk: - spider: - ajax: true - ajaxBrowser: CHROME_HEADLESS - config: - - "ajaxSpider.eventWait=20" - - "ajaxSpider.reloadWait=70" diff --git a/stackhawk.d/stackhawk-auth-basic.yml b/stackhawk.d/stackhawk-auth-basic.yml deleted file mode 100644 index 9ae802a..0000000 --- a/stackhawk.d/stackhawk-auth-basic.yml +++ /dev/null @@ -1,16 +0,0 @@ -app: - env: ${APP_ENV:Basic Web Auth} - authentication: - external: - type: TOKEN - value: ${AUTH_TOKEN} - tokenAuthorization: - type: HEADER - value: Authorization - tokenType: Basic - testPath: - path: /api/basic/items/search/1 - success: ".*200.*" - requestMethod: GET - loggedInIndicator: "\\QSign Out\\E" - loggedOutIndicator: ".*Location:.*/login.*" \ No newline at end of file diff --git a/stackhawk.d/stackhawk-auth-external-jwt.yml b/stackhawk.d/stackhawk-auth-external-jwt.yml deleted file mode 100644 index c69430f..0000000 --- a/stackhawk.d/stackhawk-auth-external-jwt.yml +++ /dev/null @@ -1,21 +0,0 @@ -app: - env: ${APP_ENV:JWT Bearer Token} - openApiConf: - path: /openapi - authentication: - external: - type: TOKEN - value: ${AUTH_TOKEN} - tokenAuthorization: - type: HEADER - value: Authorization - tokenType: Bearer - testPath: - path: /api/jwt/items/search/ - success: ".*200.*" - loggedInIndicator: "\\QSign Out\\E" - loggedOutIndicator: ".*Location:.*/login.*" - -hawk: - spider: - base: false diff --git a/stackhawk.d/stackhawk-auth-external-token.yml b/stackhawk.d/stackhawk-auth-external-token.yml deleted file mode 100644 index b77115d..0000000 --- a/stackhawk.d/stackhawk-auth-external-token.yml +++ /dev/null @@ -1,19 +0,0 @@ -app: - env: ${APP_ENV:External Token} - openApiConf: - path: /openapi - authentication: - external: - type: TOKEN - value: "ITSASECRET" - tokenAuthorization: - type: HEADER - value: "SH_AUTH_TOKEN" - testPath: - path: /api/token/items/search/1 - success: ".*200.*" - loggedInIndicator: "\\QSign Out\\E" - loggedOutIndicator: ".*Location:.*/login.*" -hawk: - spider: - base: false diff --git a/stackhawk.d/stackhawk-auth-form-cookie.yml b/stackhawk.d/stackhawk-auth-form-cookie.yml deleted file mode 100644 index 3bff798..0000000 --- a/stackhawk.d/stackhawk-auth-form-cookie.yml +++ /dev/null @@ -1,22 +0,0 @@ -app: - env: ${APP_ENV:Form Cookie} - excludePaths: - - "/logout" - antiCsrfParam: "_csrf" - authentication: - usernamePassword: - type: FORM - loginPath: /login - loginPagePath: /login - usernameField: username - passwordField: password - scanUsername: "janesmith" - scanPassword: "password" - cookieAuthorization: - cookieNames: - - "JSESSIONID" - testPath: - path: /search - success: ".*200.*" - loggedInIndicator: "\\QSign Out\\E" - loggedOutIndicator: ".*Location:.*/login.*" diff --git a/stackhawk.d/stackhawk-auth-json-token.yml b/stackhawk.d/stackhawk-auth-json-token.yml deleted file mode 100644 index b2cf561..0000000 --- a/stackhawk.d/stackhawk-auth-json-token.yml +++ /dev/null @@ -1,26 +0,0 @@ -app: - env: ${APP_ENV:JSON Token} - excludePaths: - - "/logout" - openApiConf: - path: /openapi - authentication: - usernamePassword: - type: JSON - loginPath: /api/jwt/auth/signin - usernameField: username - passwordField: password - scanUsername: "janesmith" - scanPassword: "password" - tokenExtraction: - type: TOKEN_PATH - value: "token" - tokenAuthorization: - type: HEADER - value: Authorization - tokenType: Bearer - testPath: - path: /api/jwt/items/search/i - success: ".*200.*" - loggedInIndicator: "\\QSign Out\\E" - loggedOutIndicator: ".*Location:.*/login.*" diff --git a/stackhawk.d/stackhawk-auth-script-form-multi.yml b/stackhawk.d/stackhawk-auth-script-form-multi.yml deleted file mode 100644 index f6ab453..0000000 --- a/stackhawk.d/stackhawk-auth-script-form-multi.yml +++ /dev/null @@ -1,45 +0,0 @@ -app: - applicationId: ${APP_ID:f5ee2290-3383-415c-96c7-ee0a398d90b9} - env: ${APP_ENV:dev} - host: ${APP_HOST:https://localhost:9000} - excludePaths: - - "/logout" - - "/login" - - "/login-form-multi" - - "/login-code" - antiCsrfParam: "_csrf" - authentication: - loggedInIndicator: "\\QSign Out\\E|^HTTP.*20[0-9]|^HTTP.*50[0-9]|^HTTP.*40[0-9]" - loggedOutIndicator: ".*Location:.*\\/login.*" - script: - name: form-auth-multi.kts - credentials: - username: user - password: password - parameters: - loginPagePath: /login-form-multi - loginPage: /login-form-multi - logging: "true" - formType: "FORM" - remember: "on" - csrfExtra: "loginCode" - cookieAuthorization: - cookieNames: - - "JSESSIONID" - - "XLOGINID" - testPath: - path: /search - success: "HTTP.*200.*" -hawk: - spider: - maxDurationMinutes: 5 -hawkAddOn: - scripts: - - name: form-auth-multi.kts - language: KOTLIN - type: authentication - path: hawkscripts -# - name: custom-sender.kts -# language: KOTLIN -# type: httpsender -# path: hawkscripts diff --git a/stackhawk.d/stackhawk-custom-spider-curl.yml b/stackhawk.d/stackhawk-custom-spider-curl.yml deleted file mode 100644 index 3ed4bf3..0000000 --- a/stackhawk.d/stackhawk-custom-spider-curl.yml +++ /dev/null @@ -1,32 +0,0 @@ -app: - applicationId: ${APP_ID:f5ee2290-3383-415c-96c7-ee0a398d90b9} - env: ${APP_ENV:dev} - host: ${APP_HOST:https://localhost:9000} - excludePaths: - - "/logout" -# - "/login-form-multi" -# - "/login-code" - antiCsrfParam: "_csrf" - authentication: - loggedInIndicator: "\\QSign Out\\E" - loggedOutIndicator: ".*Location:.*/login.*" - usernamePassword: - type: FORM - loginPath: /login - loginPagePath: /login - usernameField: username - passwordField: password - scanUsername: "janesmith" - scanPassword: "password" - cookieAuthorization: - cookieNames: - - "JSESSIONID" - testPath: - path: /search - success: "HTTP.*200.*" -hawk: - spider: - base: false - custom: - command: curl -x $HTTP_PROXY -k ${APP_HOST:https://localhost:9000}/login?nuance=true - diff --git a/stackhawk.d/stackhawk-custom-spider-newman.yml b/stackhawk.d/stackhawk-custom-spider-newman.yml deleted file mode 100644 index 4f92fcf..0000000 --- a/stackhawk.d/stackhawk-custom-spider-newman.yml +++ /dev/null @@ -1,34 +0,0 @@ -app: - applicationId: ${APP_ID:f5ee2290-3383-415c-96c7-ee0a398d90b9} - env: ${APP_ENV:dev} - host: ${APP_HOST:https://localhost:9000} - excludePaths: - - "/logout" -# - "/login-form-multi" -# - "/login-code" - antiCsrfParam: "_csrf" - authentication: - loggedInIndicator: "\\QSign Out\\E" - loggedOutIndicator: ".*Location:.*/login.*" - usernamePassword: - type: FORM - loginPath: /login - loginPagePath: /login - usernameField: username - passwordField: password - scanUsername: "janesmith" - scanPassword: "password" - cookieAuthorization: - cookieNames: - - "JSESSIONID" - testPath: - path: /search - success: "HTTP.*200.*" -hawk: - spider: - maxDurationMinutes: 5 - base: false - custom: - command: newman run javaspringvulny_postman_collection.json --verbose --global-var baseUrl=${APP_HOST:https://localhost:9000} --insecure - logOutputToForeground: true - diff --git a/stackhawk.d/stackhawk-fuzzer.yaml b/stackhawk.d/stackhawk-fuzzer.yaml deleted file mode 100644 index 006fd01..0000000 --- a/stackhawk.d/stackhawk-fuzzer.yaml +++ /dev/null @@ -1,25 +0,0 @@ -app: - inputVectors: - injectableParam: - urlPath: true - urlQuery: true - urlQueryParam: true - # httpHeaders: true -#hawk: -# scan: -# policyName: CUSTOM_SCRIPTS - -hawkAddOn: - scripts: - - name: fuzzer.kts - type: active - path: hawkscripts - id: 1000000 # Replace with your own registered plugin ID - language: KOTLIN - vars: - - name: iterations - val: 10 - - name: stringStartLength - val: 50 - - name: stringEndLength - val: 10_000 \ No newline at end of file diff --git a/stackhawk.d/stackhawk-github-pr.yml b/stackhawk.d/stackhawk-github-pr.yml deleted file mode 100644 index 9344cdd..0000000 --- a/stackhawk.d/stackhawk-github-pr.yml +++ /dev/null @@ -1,5 +0,0 @@ -tags: - - name: _STACKHAWK_GIT_COMMIT_SHA - value: ${COMMIT_SHA} - - name: _STACKHAWK_GIT_BRANCH - value: ${BRANCH_NAME} \ No newline at end of file diff --git a/stackhawk.d/stackhawk-har.yml b/stackhawk.d/stackhawk-har.yml deleted file mode 100644 index 0d0792e..0000000 --- a/stackhawk.d/stackhawk-har.yml +++ /dev/null @@ -1,43 +0,0 @@ -hawk: - spider: - base: false - har: - dir: - path: ${HOME}/test/resources/har - file: - paths: - - ${HOME}/test/resources/har/localhost-jsv-1.har - - ${HOME}/test/resources/har/localhost-jsv-4.har -app: - applicationId: ${APP_ID:dacc7d3e-babc-47d2-b040-ab117ab04526} - env: ${APP_ENV:Development} - host: ${APP_HOST:https://localhost:9000} - excludePaths: - - "/logout" - antiCsrfParam: "_csrf" - authentication: - loggedInIndicator: "\\QSign Out\\E" - loggedOutIndicator: ".*Location:.*/login.*" - usernamePassword: - type: FORM - loginPath: /login - loginPagePath: /login - usernameField: username - passwordField: password - scanUsername: "janesmith" - scanPassword: "password" - cookieAuthorization: - cookieNames: - - "JSESSIONID" - testPath: - path: /search - success: "HTTP.*200.*" - inputVectors: - injectableParam: - postData: true - urlQuery: true - urlQueryParam: true - enabledRpcParam: - multipartFormData: true - json: true - xmlTag: true diff --git a/stackhawk.d/stackhawk-jsv-form-cookie.yml b/stackhawk.d/stackhawk-jsv-form-cookie.yml deleted file mode 100644 index 5a7fe62..0000000 --- a/stackhawk.d/stackhawk-jsv-form-cookie.yml +++ /dev/null @@ -1,28 +0,0 @@ -hawk: - spider: - maxDurationMinutes: 2 -app: - env: ${APP_ENV:dev} - openApiConf: - path: /openapi.json - host: ${APP_HOST:https://localhost:9000} - excludePaths: - - "/logout" - antiCsrfParam: "_csrf" - authentication: - loggedInIndicator: "\\QSign Out\\E" - loggedOutIndicator: ".*Location:.*/login.*" - usernamePassword: - type: FORM - loginPath: /login - loginPagePath: /login - usernameField: username - passwordField: password - scanUsername: "janesmith" - scanPassword: "password" - cookieAuthorization: - cookieNames: - - "JSESSIONID" - testPath: - path: /search - success: ".*200.*" diff --git a/stackhawk.d/stackhawk-jsv-json-token.yml b/stackhawk.d/stackhawk-jsv-json-token.yml deleted file mode 100644 index a61dc1b..0000000 --- a/stackhawk.d/stackhawk-jsv-json-token.yml +++ /dev/null @@ -1,28 +0,0 @@ -hawk: - spider: - maxDurationMinutes: 2 -app: - env: ${APP_ENV:dev} - openApiConf: - path: /openapi - host: ${APP_HOST:https://localhost:9000} - authentication: - loggedInIndicator: "\\QSign Out\\E" - loggedOutIndicator: ".*Location:.*/login.*" - usernamePassword: - type: JSON - loginPath: /api/jwt/auth/signin - usernameField: username - passwordField: password - scanUsername: "janesmith" - scanPassword: "password" - tokenAuthorization: - type: HEADER - value: Authorization - tokenType: Bearer - tokenExtraction: - type: TOKEN_PATH - value: "token" - testPath: - path: /api/jwt/items/search/i - success: ".*200.*" diff --git a/stackhawk.d/stackhawk-multi-cookie-auth.yml b/stackhawk.d/stackhawk-multi-cookie-auth.yml deleted file mode 100644 index 56f2021..0000000 --- a/stackhawk.d/stackhawk-multi-cookie-auth.yml +++ /dev/null @@ -1,26 +0,0 @@ -app: - applicationId: ${APP_ID:test-app} - env: ${APP_ENV:Multi Cookie Auth} - openApiConf: - path: /openapi - host: ${HOST:https://localhost:9000} - excludePaths: - - "/logout" - - "/login-form-multi" - - "/login-code" - authentication: - external: - values: - - type: COOKIE - value: - name: "XLOGINID" - val: ${XLOGINID} - - type: COOKIE - value: - name: "JSESSIONID" - val: ${JSESSIONID} - testPath: - path: /login-multi-check - success: ".*200.*" - loggedInIndicator: "\\QSign Out\\E" - loggedOutIndicator: ".*Location:.*/login.*" diff --git a/stackhawk.d/stackhawk-okta.yml b/stackhawk.d/stackhawk-okta.yml deleted file mode 100644 index 9bd4cd6..0000000 --- a/stackhawk.d/stackhawk-okta.yml +++ /dev/null @@ -1,37 +0,0 @@ -app: - applicationId: ${APP_ID:f5ee2290-3383-415c-96c7-ee0a398d90b9} - env: ${APP_ENV:dev} - host: ${APP_HOST:https://localhost:9000} - - authentication: - script: - name: okta-client-credentials-basic.kts - parameters: - okta_domain: '${OKTA_DOMAIN:changeme.okta.com}' - scope: api_key - credentials: - client_id: '${OKTA_CLIENT_ID:changeme}' - client_secret: '${OKTA_CLIENT_SECRET:changeme}' - sessionScript: - name: okta-json-to-token.kts - parameters: - jwt_token_field: access_token - testPath: - path: /api/okta/me/token - success: 'HTTP(.*)200.*' - loggedInIndicator: '.*' - loggedOutIndicator: '' -hawkAddOn: - scripts: - - name: okta-client-credentials-basic.kts - type: authentication - path: hawkscripts - language: KOTLIN - - name: okta-json-to-token.kts - type: session - path: hawkscripts - language: KOTLIN - - name: log-http-payloads.kts - type: httpsender - path: hawkscripts - language: KOTLIN \ No newline at end of file diff --git a/stackhawk.d/stackhawk-openapi.yml b/stackhawk.d/stackhawk-openapi.yml deleted file mode 100644 index e96ad5a..0000000 --- a/stackhawk.d/stackhawk-openapi.yml +++ /dev/null @@ -1,61 +0,0 @@ -app: - applicationId: ${APP_ID:f5ee2290-3383-415c-96c7-ee0a398d90b9} - env: ${APP_ENV:dev-api} - host: ${APP_HOST:https://localhost:9000} - excludePaths: - - "/logout" - antiCsrfParam: "_csrf" - authentication: - loggedInIndicator: "HTTP.*200.*" - loggedOutIndicator: ".*Location:.*/login.*" - usernamePassword: - type: JSON - loginPath: /api/jwt/auth/signin - usernameField: username - passwordField: password - scanUsername: "janesmith" - scanPassword: "password" - tokenAuthorization: - type: HEADER - value: Authorization - tokenType: Bearer - tokenExtraction: - type: TOKEN_PATH - value: "token" - testPath: - path: /api/jwt/items/search/i - success: "HTTP.*200.*" - - openApiConf: - forbiddenVariables: - - field: zone_id - values: - - "" - # path: /openapi - filePath: openapi.yaml - includeAllMethods: true - includedMethods: - - POST - - PUT - customVariables: - - field: text - values: - - "customTextValue1" - - "customTextValue2" - - "customTextValue3" - - field: Dana - values: - - "no judgment!" - - "quiet you!" - - "shoosh!" - - "something something... your face!" - - field: searchText - values: - - "customSearchText1" - - "customSearchText2" - - "customSearchText3" - - field: username - values: - - "username1" - - "username2" - - "username3" diff --git a/stackhawk.d/stackhawk.yml b/stackhawk.d/stackhawk.yml deleted file mode 100644 index 84de49a..0000000 --- a/stackhawk.d/stackhawk.yml +++ /dev/null @@ -1,4 +0,0 @@ -app: - applicationId: ${APP_ID:f5ee2290-3383-415c-96c7-ee0a398d90b9} - env: ${APP_ENV:dev} - host: ${APP_HOST:https://localhost:9000} diff --git a/stackhawk.yml b/stackhawk.yml deleted file mode 100644 index 8fe5740..0000000 --- a/stackhawk.yml +++ /dev/null @@ -1,28 +0,0 @@ -app: - applicationId: ${APP_ID:747797df-f803-4cf4-9486-7020f58b8deb} - env: ${APP_ENV:Development} - host: ${APP_HOST:https://localhost:9000} - waitForAppTarget: - path: / - waitTimeoutMillis: 200000 - pollDelay: 500 - excludePaths: - - "/logout" - antiCsrfParam: "_csrf" - authentication: - loggedInIndicator: "\\QSign Out\\E" - loggedOutIndicator: ".*Location:.*/login.*" - usernamePassword: - type: FORM - loginPath: /login - loginPagePath: /login - usernameField: username - passwordField: password - scanUsername: "janesmith" - scanPassword: "password" - cookieAuthorization: - cookieNames: - - "JSESSIONID" - testPath: - path: /search - success: "HTTP.*200.*" diff --git a/tools/update-openapi-files.sh b/tools/update-openapi-files.sh deleted file mode 100755 index 6ea14a8..0000000 --- a/tools/update-openapi-files.sh +++ /dev/null @@ -1,52 +0,0 @@ -#!/bin/bash - -# Exit on error -set -e - -# Define the URL of the running application -APP_URL="https://localhost:9000/openapi" -HEALTH_URL="https://localhost:9000/actuator/health" - -# Define the output files -JSON_OUTPUT="openapi.json" -YAML_OUTPUT="openapi.yaml" - -# Save the current directory -CURRENT_DIR=$(pwd) - -# Change to the parent directory -cd .. - -# Start the application in the background -./gradlew bootRun & -APP_PID=$! - -# Wait for the application to start by checking the health endpoint -until $(curl -k --output /dev/null --silent --head --fail ${HEALTH_URL}); do - printf '.' - sleep 5 -done - -# Fetch the OpenAPI JSON definition and save it to openapi.json -curl -k -s "${APP_URL}" -o "${JSON_OUTPUT}" - -# Kill the application process -kill $APP_PID - -# Reformat the JSON file using jq -jq . "${JSON_OUTPUT}" > "${JSON_OUTPUT}.tmp" && mv "${JSON_OUTPUT}.tmp" "${JSON_OUTPUT}" - -# Convert the JSON definition to YAML and save it to openapi.yaml -# Requires yq (https://github.com/mikefarah/yq) to be installed -if command -v yq &> /dev/null -then - yq eval -P "${JSON_OUTPUT}" > "${YAML_OUTPUT}" -else - echo "yq is not installed. Please install yq to convert JSON to YAML." - kill $APP_PID -fi - -# Change back to the original directory -cd "${CURRENT_DIR}" - -echo "OpenAPI definitions updated successfully."