APIWeb ApplicationApril 9, 2022Hacking GraphQL (Pt. 3)

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.

Dirsearch Tool
“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
Source code (app.py)

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.

Mitigation

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.

Redfox Security is a diverse network of expert security consultants with a global mindset and a collaborative culture. If you are looking to improve your organization’s security posture, contact us today to discuss your security testing needs. Our team of security professionals can help you identify vulnerabilities and weaknesses in your systems and provide recommendations to remediate them. To schedule a call with one of our technical specialists, call 1-800-917-0850 now.

“Join us on our journey of growth and development by signing up for our comprehensive courses.

Gaurav Patil

by Gaurav Patil

Associate Security Consultant | Redfox Security