Skip to content

Module: SQL‐Injection

Moiz Bootwala edited this page Jan 19, 2026 · 1 revision

Overview

Module Name: sql_injection
Requires Sink: SQLite

SQL injection is a code injection that exploits vulnerabilities in applications that use user input to construct SQL queries. Attackers can manipulate queries to access, modify or delete data, bypass authentication or even execute system commands in some cases.

This module creates a real SQL injection vulnerability by executing user-supplied input directly against an in-memory SQLite database.

Supported Placements

The sql_injection module supports the following placements (it can extract input from these places):

Placement Description Example Request
query param URL query string GET /users?id=1
path_param URL path segment GET /user/1
form_field POST form data POST /login with username=admin
json_field JSON body field POST /api/users with {"id": 1}
header HTTP header X-User-Id: 1
cookie Cookie value Cookie: user_id=1

Configuration Options

variant (string)

This defines the type of SQL injection behavior. It determines how results are returned.

Value Description Use Case
error_based Returns query results and SQL errors Testing error-based detection
blind_boolean Returns only success/failure Testing blind boolean injection

Default: error_based

query_template (string) - Required

This is the SQL query template to be executed by the application using the input.

  • {input} is used as a placeholder for user input.
query_template: "SELECT * FROM users WHERE id = {input}"

The {input} placeholder is replaced with the user's input without sanitization.

Examples

# Numeric injection point
query_template: "SELECT * FROM users WHERE id = {input}"

# String injection point (quotes)
query_template: "SELECT * FROM users WHERE username = '{input}'"

# LIKE clause
query_template: "SELECT * FROM products WHERE name LIKE '%{input}%'"

# Multiple columns
query_template: "SELECT * FROM users WHERE username = '{input}' AND active = 1"

show_errors (boolean)

This is used to configure whether to include SQL error messages in the response.

Value Behavior
true SQL errors are included in response (useful for error-based injection)
false Generic "Database error" message returned

Default: true

filter (string)

These are intentionally weak input filtering. They are bypassable protections that can be tested against.

Value Description Bypass Method
none No filtering (fully vulnerable) N/A
basic_quotes Escapes single quotes (''') use numeric type in query
remove_comments Removes SQL comments Alternative comment syntax

Default: none

Data Requirements

sql_injection module requires the data section in the config to define tables.

data:
  tables:
    TABLE_NAME:
      columns: [COL1, COL2, COL3, COL4, COL5]
      rows:
        - [COL1_ENTRY, COL2_ENTRY, COL3_ENTRY, COL4_ENTRY, COL5_ENTRY]
        - [COL1_ENTRY, COL2_ENTRY, COL3_ENTRY, COL4_ENTRY, COL5_ENTRY]
        - [COL1_ENTRY, COL2_ENTRY, COL3_ENTRY, COL4_ENTRY, COL5_ENTRY]

Example:

data:
  tables:
    users:
      columns: [id, username, password, email, role]
      rows:
        - [1, "admin", "supersecret", "admin@example.com", "admin"]
        - [2, "john", "password123", "john@example.com", "user"]
        - [3, "jane", "jane2024", "jane@example.com", "user"]

The above data section creates a users table with 5 columns: id, username, password, email, role and adds 3 rows to it.

note: All columns are created as TEXT type. The values provided are stored as-is (no type conversion). Additionally, the tables are created fresh on each startup.

Configuration Examples

Basic Error-Based SQL Injection

app:
  name: "SQLi Lab 1"
  port: 8081

data:
  tables:
    users:
      columns: [id, username, password, email]
      rows:
        - [1, "admin", "secret123", "admin@example.com"]
        - [2, "user", "password", "user@example.com"]

endpoints:
  - path: /users
    method: GET
    vulnerabilities:
      - type: sql_injection
        placement: query_param
        param: id
        config:
          variant: error_based
          query_template: "SELECT * FROM users WHERE id = {input}"
          show_errors: true

String-Based Injection (Login Form)

app:
  name: "SQLi Lab 2"
  port: 8082

data:
  tables:
    users:
      columns: [id, username, password, email]
      rows:
        - [1, "admin", "secret123", "admin@example.com"]
        - [2, "user", "password", "user@example.com"]

endpoints:
  - path: /login
    method: POST
    vulnerabilities:
      - type: sql_injection
        placement: form_field
        param: username
        config:
          variant: error_based
          query_template: "SELECT * FROM users WHERE username = '{input}' AND password = 'anything'"
          show_errors: true

Blind Boolean Injection

app:
  name: "SQLi Lab 3"
  port: 8083

data:
  tables:
    users:
      columns: [id, username, password, email]
      rows:
        - [1, "admin", "secret123", "admin@example.com"]
        - [2, "user", "password", "user@example.com"]

endpoints:
  - path: /api/check-user
    method: GET
    vulnerabilities:
      - type: sql_injection
        placement: query_param
        param: id
        config:
          variant: blind_boolean
          query_template: "SELECT * FROM users WHERE id = {input}"

Response behavior:

  • If query returns results: {"success": true, "message": "Record found"}
  • If query returns no results: {"success": false, "message": "Record not found"}

Path Parameter Injection

app:
  name: "SQLi Lab 5"
  port: 8085

data:
  tables:
    users:
      columns: [id, username, password, email]
      rows:
        - [1, "admin", "secret123", "admin@example.com"]
        - [2, "user", "password", "user@example.com"]

endpoints:
  - path: /user/{id}
    method: GET
    vulnerabilities:
      - type: sql_injection
        placement: path_param
        param: id
        config:
          query_template: "SELECT * FROM users WHERE id = {input}"

JSON Body Injection

app:
  name: "SQLi Lab 6"
  port: 8086

data:
  tables:
    users:
      columns: [id, username, password, email]
      rows:
        - [1, "admin", "secret123", "admin@example.com"]
        - [2, "user", "password", "user@example.com"]

endpoints:
  - path: /api/search
    method: POST
    vulnerabilities:
      - type: sql_injection
        placement: json_field
        param: filter.user_id    # Supports dot notation
        config:
          query_template: "SELECT * FROM users WHERE id = {input}"

With Basic Filter (Bypassable)

app:
  name: "SQLi Lab 7"
  port: 8087

data:
  tables:
    users:
      columns: [id, username, password, email]
      rows:
        - [1, "admin", "secret123", "admin@example.com"]
        - [2, "user", "password", "user@example.com"]

endpoints:
  - path: /secure/users
    method: GET
    vulnerabilities:
      - type: sql_injection
        placement: query_param
        param: id
        config:
          query_template: "SELECT * FROM users WHERE username = '{input}'"
          filter: basic_quotes
          show_errors: true

Multiple Placements Example

Test SQLi from all possible input locations:

app:
  name: "SQLi All Placements"
  port: 8080

data:
  tables:
    users:
      columns: [id, username, password]
      rows:
        - [1, "admin", "secret"]
        - [2, "user", "pass"]

endpoints:
  # Query parameter
  - path: /users/query
    method: GET
    vulnerabilities:
      - type: sql_injection
        placement: query_param
        param: id
        config:
          query_template: "SELECT * FROM users WHERE id = {input}"

  # Path parameter
  - path: /users/path/{id}
    method: GET
    vulnerabilities:
      - type: sql_injection
        placement: path_param
        param: id
        config:
          query_template: "SELECT * FROM users WHERE id = {input}"

  # Form field
  - path: /users/form
    method: POST
    vulnerabilities:
      - type: sql_injection
        placement: form_field
        param: id
        config:
          query_template: "SELECT * FROM users WHERE id = {input}"

  # JSON field
  - path: /users/json
    method: POST
    vulnerabilities:
      - type: sql_injection
        placement: json_field
        param: id
        config:
          query_template: "SELECT * FROM users WHERE id = {input}"

  # Header
  - path: /users/header
    method: GET
    vulnerabilities:
      - type: sql_injection
        placement: header
        param: X-User-Id
        config:
          query_template: "SELECT * FROM users WHERE id = {input}"

  # Cookie
  - path: /users/cookie
    method: GET
    vulnerabilities:
      - type: sql_injection
        placement: cookie
        param: user_id
        config:
          query_template: "SELECT * FROM users WHERE id = {input}"

Clone this wiki locally