## https://sploitus.com/exploit?id=79122113-1486-513A-B7FA-46450A2B768A
# CVE-2026-52614 โ RuoYi v4.8.3 `filterKeyword` bypass SQL injection
[Chinese](#Chinese explanation) | [English](#English)
> **Authorization required / Only for authorized testing**
> This repository is intended for security research and authorized testing only. Do not use it against systems without explicit permission. > This repository is used solely for security research and authorized testing. Do not use it on unauthorized systems. ## Chinese Explanation
### Vulnerability Description
In RuoYi v4.8.3, the `/tool/gen/createTable` endpoint allows authenticated backend users to submit table-creation SQL queries. The endpoint calls `SqlUtil.filterKeyword()` to filter SQL queries based on keyword blacklists. However, the implementation first removes all whitespace from the input before checking for blacklisted keywords that contain trailing spaces, such as `select `, `insert `, and `drop `. As a result, these keywords cannot match the normalized input. A `CREATE TABLE ... AS SELECT ...` (CTAS) statement can pass the Druid `MySqlCreateTableStatement` type check while still executing a `SELECT`. An attacker with a valid backend session can exploit this vulnerability to perform boolean-based SQL injection, extract sensitive information from the database, and create tables. ### Impact Conditions
- Target version: RuoYi v4.8.3.
- The attacker must be logged in to the backend and have a valid `JSESSIONID`.
- The current account must have access to the code-generation module endpoints.
- The database and the current database account must be authorized to execute CTAS commands. ### Vulnerability Mechanism
The validation script uses the following logic to extract the password hash and salt for the `admin` user from the `sys_user` table:
1. Create an intermediate table using CTAS, copying fields like `login_name`, `password`, and `salt`.
2. Create a test table for each character to be checked, and add a `SUBSTRING()` condition in the `WHERE` clause.
3. If the condition is true, CTAS will return data, and the test table will not be automatically added to the code-generation list.
4. If the condition is false, CTAS will return zero rows, and the test table will be automatically added, which can be queried via `/tool/gen/list`.
5. The password hash and salt are recovered based on whether the test table appears in the list. ### Environment Requirements
- Python 3.8+
- A valid and authorized RuoYi backend session
- Python dependencies: `requests`, `urllib3`
Install dependencies:
```bash
python -m pip install requests urllib3
```
### Usage
```bash
python exp.py -u http://127.0.0.1:8080 -c "JSESSIONID=your_session_id"
```
You can also specify the cookie value directly:
```bash
python exp.py --url http://127.0.0.1:8080 --cookie "your_session_id" --timeout 15
```
**Parameter Details**
| Parameter | Required | Description |
| --- | --- | --- |
| `-u`, `--url` | Yes | The target URL; no need for the trailing `/` |
| `-c`, `--cookie` | Yes | A valid `JSESSIONID` value, or the full `JSESSIONID=` |
| `--timeout` | No | Timeout for a single HTTP request; default is 10 seconds |
The script will create an intermediate table and multiple test tables based on boolean checks in the target database. Please use this script only in isolated or authorized environments. Clean up the related tables after testing. ### Verification Screenshots
`exp.png` shows successful verification screenshots in a local authorized environment:

### Recommendations
- Do not use string blacklists to check SQL security, and do not execute user-submitted SQL queries directly.
- Fix the normalization and matching logic of `filterKeyword()`, but do not rely on it as the sole protection mechanism.
- Implement strict permission control, operation auditing, and CSRF protection for the code-generation endpoints.
- Disable or remove any SQL table-creation capabilities. If necessary, use structured parameters to construct fixed statements.
- Use a database account with minimal privileges to limit access to sensitive tables and CTAS/DDL operations.
- Upgrade to the officially fixed version or apply official security patches. ## English
### Summary
The `/tool/gen/createTable` endpoint in the RuoYi v4.8.3 code-generation module allows authenticated backend users to submit table-creation SQL queries. The endpoint calls `SqlUtil.filterKeyword()` to filter SQL queries based on dangerous keywords. However, the implementation removes all whitespace from the input before checking for blacklisted keywords that contain trailing spaces, such as `select `, `insert `, and `drop `. As a result, these keywords cannot match the normalized input. A `CREATE TABLE ... AS SELECT ...` (CTAS) statement can pass the Druid `MySqlCreateTableStatement` type check while still executing a `SELECT`. An attacker with a valid backend session can exploit this vulnerability to perform boolean-based SQL injection, extract sensitive information from the database, and create tables.
### Prerequisites
- The target is running RuoYi v4.8.3.
- The tester has a valid authenticated backend `JSESSIONID`.
- The authenticated account can access the code-generation endpoints.
- The database and its configured accounts allow CTAS operations.
### How the PoC Works
The script retrieves the `admin` password hash and salt from `sys_user` using the following Oracle:
1. Create an intermediate table containing `login_name`, `password`, and `salt`.
2. Create one test table for each candidate character, using a `SUBSTRING()` condition.
3. When the condition is true, CTAS returns a row, and the test table is not automatically imported into the generator table list.
4. When the condition is false, CTAS returns zero rows, and the table is automatically imported, making it visible through `/tool/gen/list`.
5. Use this difference to retrieve the password hash and salt, one character at a time.
### Requirements
- Python 3.8+
- A valid, authorized RuoYi backend session
- Python packages: `requests`, `urllib3`
Install dependencies:
```bash
python -m pip install requests urllib3
```
### Usage
```bash
python exp.py -u http://127.0.0.1:8080 -c "JSESSIONID=your_session_id"
```
The raw session value is also accepted:
```bash
python exp.py --url http://127.0.0.1:8080 --cookie "your_session_id" --timeout 15
```
**Arguments:**
| Argument | Required | Description |
| --- | --- | --- |
| `-u`, `--url` | Yes | Target base URL (without the trailing slash) |
| `-c`, `--cookie` | Yes | Valid `JSESSIONID` value or `JSESSIONID=` |
| `--timeout` | No | Timeout per request in seconds; default is 10 |
> The script creates an intermediate table and several boolean-test tables in the target database. Use it only in an isolated or explicitly authorized environment. Have the database administrator remove the generated tables after testing.
### Screenshot
`exp.png` shows a successful verification in an authorized local environment:

### Mitigations
- Do not rely on SQL keyword blacklists or execute user-supplied SQL directly.
- Correct the normalization and matching logic in `filterKeyword()`, but do not use it as the sole security control.
- Apply strict authorization, auditing, and CSRF protection to code-generation endpoints.
- Remove arbitrary SQL table creation; if necessary, construct fixed statements from structured, validated parameters.
- Use a least-privileged database account that cannot read sensitive tables or perform unnecessary CTAS/DDL operations.
- Upgrade to an officially fixed release or apply the vendorโs security patches.
## Files
- `exp.py` โ Verification script
- `exp.png` โ Successful verification screenshot
- `README.md` โ Bilingual vulnerability documentation