In Part 2 of the Hacking GraphQL series, we discussed the GraphQL DoS attack. In Part 3, we’re going to try to exploit the SQLi vulnerability, included in the OWASP Top Ten Web Application Security Risks. In this blog post, we will use the same setup as Part 1 of the series i.e., GraphQL Security Labs.
A SQL injection attack consists of insertion or “injection” of a SQL query via the input data from the client to the application. A successful SQL injection exploit can read sensitive data from the database, modify database data (Insert/Update/Delete), execute administration operations on the database (such as shutdown the DBMS), recover the content of a given file present on the DBMS file system and in some cases issue commands to the operating system. SQL injection attacks are a type of injection attack, in which SQL commands are injected into data-plane input in order to affect the execution of predefined SQL commands.
GraphQL, on its own, doesn’t provide protection against injection attacks. For instance, if the development team fails to use parameterized queries, and if parameters in queries and mutations interact directly with back-end code, then there is a high chance that the application may fall prey to a SQL injection attack. For this reason, the same web application security risks apply to GraphQL.
GraphQL & SQL Injection
To begin with, we’ll use dirsearch to search for potential directories and files in the web server. The tool reveals one interesting page i.e., the “admin” page.
Locate the GraphQL query that executes this transaction. Now we’ll try to fetch some information for valid as well as invalid users. For this we can use the following payload:
' UNION SELECT uuid, username, null, null FROM users --")
Note: To get to the GraphQL client navigate to the /graphql page.
By now we are certain that the username parameter is vulnerable to SQL injection and it appears to be a UNION based SQL Injection. Now, we’ll try to retrieve the admins:
Next, we can try to get the password of user ‘user1’:
As can be seen above, we’re unable to retrieve the password of user ‘user1’. The following could be potential reasons:
- The query only returns one row (the first row)
- We cannot see the password value as the GraphQL User Object model excludes the password column/field
This means that if we want to retrieve the password, we’ll need to exfiltrate it from the database in another variable that is not explicitly excluded.
The easiest approach, to retrieve the password, is to return ‘password’ for all columns.
As we can be see above, we get the password in the Username field.
The source of the problem is when the user input is passed from GraphQL to another interpreter such as SQL/NoSQL/ORM, OS, LDAP, XML etc.
- Validate the input when receiving the data via a GraphQL query.
- Use parameterized queries at the backend to handle the data.
- Sanitize the GraphQL response before the client renders it.
- Use and implement proper content security policy for all web pages.
By partnering with Redfox Security, you’ll get the best security and technical skills required to execute an effective and thorough penetration test. Our offensive security experts have years of experience assisting organizations in protecting their digital assets through penetration testing services. To schedule a call with one of our technical specialists, call 1-800-917-0850 now.
Redfox Security is a diverse network of expert security consultants with a global mindset and a collaborative culture. With a combination of data-driven, research-based, and manual testing methodologies, we proudly deliver robust security solutions.
“Join us on our journey of growth and development by signing up for our comprehensive courses, if you want to excel in the field of cybersecurity.”