Oracle PL/SQL IF...ELSE T-SQL · Control-of-Flow · IF...ELSE

T-SQL IF...ELSE Statement

Master T-SQL IF...ELSE — Boolean conditions, BEGIN/END for multi-statement bodies, ELSE IF chains, nested IF, IF EXISTS pattern for row-existence checks, and common pitfalls including the missing END IF and NULL comparisons.

IF ... ELSE is T-SQL's basic conditional branch. You give it a Boolean expression; if it's TRUE the IF block runs, otherwise the optional ELSE block does. It works exactly like if/else in any other language — with one or two T-SQL-specific gotchas covered below.

IF condition BEGIN -- runs when condition is TRUE END ELSE BEGIN -- runs when condition is FALSE (optional) END
  • condition — any Boolean expression: comparison (@x > 5), logical combination (a = 1 AND b = 2), EXISTS (SELECT ...), etc.
  • BEGIN ... END — needed only when the body has more than one statement. A single statement can sit directly after the IF condition.
⚠️ T-SQL has no END IF keyword. Unlike PL/SQL or shell scripts, you don't terminate an IF with anything special — it ends after its statement (or BEGIN/END block). Forgetting this is a common cause of "I added a second line and now the ELSE doesn't fire" bugs.
💡 ELSE IF is two keywords, not one. T-SQL doesn't have ELSEIF (one word). Write ELSE IF condition with a space.
Example 1 — Simple IF (no ELSE)
T-SQL — Simplest form
DECLARE @value INT = 10;

IF @value > 5
    PRINT 'Value is greater than 5';
OUTPUT
Messages
Commands completed successfully.
Value is greater than 5
Example 2 — IF ... ELSE
T-SQL — Two-way branch
DECLARE @value INT = 3;

IF @value > 5
    PRINT 'Value is greater than 5';
ELSE
    PRINT 'Value is 5 or less';
OUTPUT
Messages
Commands completed successfully.
Value is 5 or less
Example 3 — ELSE IF Chain

Multiple conditions checked in order, falling through to the next as each one fails:

T-SQL — Multi-way branching
DECLARE @value INT = 5;

IF @value > 10
BEGIN
    PRINT 'Value is greater than 10.';
END
ELSE IF @value > 5
BEGIN
    PRINT 'Value is greater than 5 but 10 or less.';
END
ELSE
BEGIN
    PRINT 'Value is 5 or less.';
END
OUTPUT
Messages
Commands completed successfully.
Value is 5 or less.
📌 Order matters. The first matching condition wins; later branches are never tested. If you swap "greater than 10" and "greater than 5", a value of 7 would never reach the "greater than 10" check anyway, but a value of 100 would be claimed by "greater than 5" first — likely not what you wanted.
Example 4 — Nested IF ... ELSE

An IF can sit inside another IF's body — useful when one decision depends on another:

T-SQL — Nested branching
DECLARE @value INT = 7;

IF @value > 5
BEGIN
    PRINT 'Value is greater than 5.';

    IF @value > 10
    BEGIN
        PRINT 'Value is also greater than 10.';
    END
    ELSE
    BEGIN
        PRINT 'Value is 10 or less.';
    END
END
ELSE
BEGIN
    PRINT 'Value is 5 or less.';
END
OUTPUT
Messages
Commands completed successfully.
Value is greater than 5.
Value is 10 or less.
Example 5 — IF EXISTS for Row Checks

One of the most useful patterns: branch on whether a query returns any rows. IF EXISTS is faster and clearer than IF (SELECT COUNT(*) FROM t) > 0 because the optimizer can stop at the first matching row:

SQL — Setup
CREATE TABLE Employees (
    EmployeeID  INT PRIMARY KEY,
    Name        NVARCHAR(50)
);

INSERT INTO Employees VALUES (1, 'Alice'), (2, 'Bob');
T-SQL — IF EXISTS pattern
DECLARE @id INT = 2;

IF EXISTS (SELECT 1 FROM Employees WHERE EmployeeID = @id)
    PRINT 'Employee found.';
ELSE
    PRINT 'No employee with that ID.';
OUTPUT
Messages
Commands completed successfully.
Employee found.

A typical business-logic example: pull a row of data, then branch on its values.

Example 6 — Customer Credit Check
SQL — Setup
CREATE TABLE Customers (
    CustomerID         INT PRIMARY KEY,
    CustomerName       NVARCHAR(50),
    CreditLimit        DECIMAL(10, 2),
    OutstandingBalance DECIMAL(10, 2)
);

INSERT INTO Customers VALUES
    (1, 'John Doe',      1000.00,  800.00),    -- under limit
    (2, 'Jane Smith',    1500.00, 1600.00),    -- OVER limit
    (3, 'Alice Johnson', 2000.00, 1500.00);    -- under limit
T-SQL — IF/ELSE driven by query data
DECLARE @CustomerID         INT = 2,
        @CustomerName       NVARCHAR(50),
        @CreditLimit        DECIMAL(10, 2),
        @OutstandingBalance DECIMAL(10, 2);

-- Pull the row into variables
SELECT @CustomerName       = CustomerName,
       @CreditLimit        = CreditLimit,
       @OutstandingBalance = OutstandingBalance
FROM   Customers
WHERE  CustomerID = @CustomerID;

-- Branch on the values
IF @OutstandingBalance > @CreditLimit
    PRINT 'Warning: balance exceeds credit limit for ' + @CustomerName;
ELSE
    PRINT 'Balance is within the credit limit for '   + @CustomerName;
OUTPUT
Messages
Commands completed successfully.
Warning: balance exceeds credit limit for Jane Smith

Re-running with @CustomerID = 1 takes the ELSE branch instead:

OUTPUT
Messages
Commands completed successfully.
Balance is within the credit limit for John Doe
  • "Forgotten BEGIN/END" silent bugs. When an IF body is a single statement, only that one statement is conditional. If you later add a second line below it expecting it to be conditional too, it won't be — it'll always run. Wrap multi-statement bodies in BEGIN ... END.
  • Truthy values don't exist in T-SQL. IF @x is a syntax error — you need a real Boolean: IF @x <> 0 or IF @x IS NOT NULL.
  • NULL is not FALSE. IF @x = NULL is never true (because NULL = NULL is unknown). Use IF @x IS NULL.
  • Always use IF EXISTS for "row exists" checks rather than SELECT COUNT(*) — short-circuits at the first match.
  • IF condition runs the next statement (or BEGIN ... END block) when the condition is TRUE; the optional ELSE handles the FALSE case.
  • T-SQL has no END IF keyword — IF ends after its statement or block. Forgetting this leads to "added a second line and broke the ELSE" bugs.
  • ELSE IF is two keywords with a space — not ELSEIF.
  • Chains of ELSE IF ... ELSE work top-down; the first matching condition wins. For value-based selection, also consider the CASE expression.
  • Use IF EXISTS (SELECT 1 FROM ...) for "row exists" checks — fast and idiomatic.
  • Watch out for NULL: use IS NULL / IS NOT NULL, never = NULL.