Hello! Welcome to your next lesson on SQL injection.
In our last session, we delved into boolean-based blind SQL injection. We learned how to extract data by asking the database a series of true/false questions and observing a visible change in the application's response, such as a "Welcome back!" message appearing or disappearing.
But what happens when an application is so locked down that its response is identical whether your injected query is true or false? There are no error messages, no reflected data, and no change in the page content. This is the "totally blind" scenario. To overcome this, we must rely on the only channel of information we have left: time.
Today, we will master time-based blind SQL injection. You will learn how to force the database to reveal its secrets by manipulating the time it takes to respond to your requests. This technique is subtle, powerful, and an essential part of any advanced penetration tester's toolkit.
1. Identifying the Vulnerability with Time Delays
The core principle of a time-based attack is to inject a command that instructs the database to pause or "sleep" for a specific duration. If we can make the server's response take noticeably longer, we have confirmation that our SQL payload was executed. This time delay becomes our new "true" signal.
The specific function to cause a delay varies between database systems:
- PostgreSQL:
pg_sleep(seconds) - MySQL:
SLEEP(seconds) - MS SQL Server:
WAITFOR DELAY '0:0:seconds' - Oracle:
DBMS_LOCK.SLEEP(seconds)
When probing a target, you often don't know the backend database. A common first step is to try each of these payloads until one of them causes a delay. Remember from our previous lessons, it's crucial to correctly terminate the existing query and comment out the rest.
Let's see this process in action. The following video demonstrates how to test for a time-based vulnerability by injecting different database-specific sleep payloads and observing the response time in Burp Suite.
SQL Injection - Lab #13 Blind SQL injection with time delays
The video 'SQL Injection - Lab #13 Blind SQL injection with time delays' by Rana Khalil is an excellent starting point. It shows how to systematically test for a time-based vulnerability.
Watch from 02:58 to 07:50. Pay close attention to these points: Initial Failure: Notice how the first attempts with MySQL and PostgreSQL payloads fail because the rest of the original query is not commented out, resulting in a syntax error. The Fix: The presenter realizes the need to add a comment (--) to neutralize the rest of the original query string. Success: After adding the comment, the PostgreSQL payload '; SELECT pg_sleep(10)-- works, and the response is delayed by 10 seconds. This confirms both the vulnerability and the database type.
2. From Simple Delays to Conditional Data Exfiltration
Now that we can force a delay, we need to make it conditional. We'll combine the sleep function with a conditional statement, like IF or CASE WHEN. This allows us to ask the database true/false questions, where the "answer" is a time delay.
The logic is straightforward:
IF [our question is true] THEN sleep for 5 seconds ELSE do nothing.
For example, to check if the administrator user exists, you could inject a payload like this (for PostgreSQL):'; SELECT CASE WHEN (username='administrator' FROM users) THEN pg_sleep(5) ELSE pg_sleep(0) END--
If the response takes 5 seconds, the user exists. If it's immediate, the user does not.
The following article gives clear examples of constructing these conditional payloads to extract information like database version and name length.
Exploiting Time-Based SQL Injections: Data Exfiltration
The article 'Exploiting Time-Based SQL Injections: Data Exfiltration' provides excellent payload examples for building conditional time-based queries.
Read the sections 'What is Time-Based SQL Injection?', 'Discovering the time-Based SQL Injection', and 'Extracting Data with Time-Based SQL Injection'. Focus on how the IF and SUBSTRING functions are combined with SLEEP() to ask specific questions about the database version and table contents.
Test your understanding!
You are testing a parameter on a website that uses a MySQL database. You want to find out if the administrator's password is longer than 15 characters. You inject the following payload:
' AND IF((SELECT LENGTH(password) FROM users WHERE username='administrator') > 15, SLEEP(10), 0)--
The server takes approximately 10 seconds to respond. What does this tell you?
Show answer
This tells you that the administrator's password is indeed longer than 15 characters. The condition LENGTH(password) > 15 evaluated to true, which triggered the SLEEP(10) function.
3. Automating Extraction with Burp Suite Intruder
Manually testing each character one by one is far too slow. As with boolean-based attacks, we'll use automation. Your familiarity with Burp Suite Intruder's "Cluster Bomb" attack will be very useful here. The process is nearly identical, with one key difference: instead of analyzing the response content, we analyze the response time.
The following video is a complete walkthrough of discovering and exploiting a time-based blind SQLi, culminating in a full password extraction using Burp Intruder.
Time-Based Blind SQL Injection!
The video 'Time-Based Blind SQL Injection!' from Intigriti is a masterclass in this technique. We will watch it in a few parts to break down the process.
First, watch from 00:41 to 04:56. This section covers the manual discovery process, which you should now be familiar with. The attacker: Confirms the time-based vulnerability using a CASE WHEN statement and pg_sleep(). Verifies the existence of the 'administrator' user. Manually determines the exact length of the password (20 characters) by adjusting the length(password) > X query. This is a crucial step for automating the next phase.
Now for the automation. Pay very close attention to the setup in Burp Intruder.
Time-Based Blind SQL Injection!
Continuing with the 'Time-Based Blind SQL Injection!' video, this part details the automation using Burp Intruder.
Watch from 04:49 to 09:25. Focus on these critical configuration details: Attack Type & Payloads: A 'Cluster Bomb' attack is used with two payload positions: one for the character position (1-20) and one for the character guess (a-z, 0-9). Resource Pool: The video highlights a vital step for time-based attacks: setting Maximum concurrent requests to 1. This ensures that network latency from parallel requests doesn't interfere with your timing measurements. Analyzing Results: After running the attack, the results are sorted by the 'Response received' column. The requests that took ~5 seconds are the 'true' results, revealing one character of the password at a time. The attacker then filters and sorts to reconstruct the full password.
4. Scripting the Attack with Python
As a developer, you know that for maximum flexibility and control, nothing beats a custom script. The logic for a time-based exploitation script is similar to the boolean-based one from our last lesson. The main difference is that instead of checking if "Welcome back!" in response.text, you'll measure the time taken for the request.
Your script will:
- Record the time before sending the request (
start_time = time.time()). - Send the request with the payload.
- Record the time after receiving the response (
end_time = time.time()). - Calculate the duration (
duration = end_time - start_time). - If the duration is greater than your sleep delay, you've found a correct character.
The following resource provides an excellent, concise Python script that implements this exact logic.
SQL Injection: All Concepts, All Payloads, All In One
The article 'SQL Injection: All Concepts, All Payloads, All In One' contains a section with a Python script for automating time-based blind SQLi in PostgreSQL.
Scroll down to the subsection '7.2 Time-Based Blind Injection' and find the Python script under 'PostgreSQL Delay via Sleep'. Study how it uses the time library to measure the request duration and identify the correct characters. This is a perfect template for your own tools.

Conclusion
You've now added another sophisticated and stealthy technique to your SQL injection arsenal. When an application gives you no visual feedback at all, you can still bend it to your will by making time your ally.
Key Takeaways:
- The Signal: Time-based blind SQL injection is used when the application gives no differential response. The only indicator is the server's response time.
- The Payload: The attack relies on injecting database-specific sleep functions (
pg_sleep,SLEEP,WAITFOR DELAY) inside a conditional statement (CASEorIF). - The Automation: Manual extraction is infeasible. Using Burp Suite Intruder and sorting by response time is the standard approach. Remember to set concurrent requests to 1 for accurate timing.
- The Scripting: Your programming skills can be used to create highly customized and efficient exploitation scripts by measuring request duration with Python's
timelibrary.
Next Lesson Preview:
In the past few lessons, we've done an incredible amount of work manually and with semi-automated tools like Burp Intruder. We've identified injection points, determined column counts, and exfiltrated data bit by bit. Now, it's time to see how the professionals automate this entire process. In our next lesson, we will learn to use SQLMap, the definitive tool for automating the detection and exploitation of SQL injection vulnerabilities.
