Exceptions provide a structured way to handle problems that occur
while a PHP program is running. Using try,
catch, and throw, you can detect
unexpected situations and respond appropriately without exposing
sensitive technical details to users.
An exception is an object representing an unusual condition that interrupts the normal flow of a program.
PHP provides the built-in Exception class.
You can also create your own exception classes.
<?php
$age = 15;
if ($age < 18) {
throw new Exception("Age must be at least 18.");
}
echo "You are eligible.";
?>
The throw statement creates and throws an
exception. If no matching handler catches it, PHP treats
it as an uncaught exception and reports a fatal error.
To handle the exception and continue safely, use
try and catch.
The try block contains code that may throw
an exception. A matching catch block
handles the exception.
<?php
try {
throw new Exception("Something went wrong.");
} catch (Exception $e) {
echo "Error: " . $e->getMessage();
}
echo "<br>Program continues.";
?>
Output:
Error: Something went wrong.
Program continues.
When the exception is caught, execution continues after the try-catch structure unless another statement changes the flow.
The variable $e contains the exception
object. Its getMessage() method returns
the exception message.
Use throw when your program detects a
condition that should be handled as an exception.
<?php
function checkMarks(int $marks): string {
if ($marks < 0 || $marks > 100) {
throw new InvalidArgumentException(
"Marks must be between 0 and 100."
);
}
return "Valid marks: " . $marks;
}
try {
echo checkMarks(120);
} catch (InvalidArgumentException $e) {
echo $e->getMessage();
}
?>
Output:
Marks must be between 0 and 100.
In this example, InvalidArgumentException
is appropriate because the supplied marks are outside
the permitted range.
Choose an exception type that describes the problem whenever a suitable built-in exception exists.
You can use multiple catch blocks to handle
different exception types differently.
<?php
function calculate(int $a, int $b): float {
if ($b === 0) {
throw new DivisionByZeroError(
"Cannot divide by zero."
);
}
return $a / $b;
}
try {
echo calculate(20, 0);
} catch (DivisionByZeroError $e) {
echo "Calculation error: " . $e->getMessage();
} catch (TypeError $e) {
echo "Invalid data type.";
} catch (Throwable $e) {
echo "An unexpected problem occurred.";
}
?>
PHP checks the catch blocks in order. A matching block handles the thrown object, so specific exception types should appear before broader types.
Throwable is the common interface for PHP
Exception and Error objects.
Catching it should be done thoughtfully because it can
also catch serious programming errors.
The finally block is used for cleanup code
that should run after the try-catch process, whether
an exception occurred or not.
<?php
try {
echo "Opening a resource.<br>";
throw new Exception("Operation failed.");
} catch (Exception $e) {
echo "Caught: " . $e->getMessage() . "<br>";
} finally {
echo "Cleanup completed.<br>";
}
echo "End of program.";
?>
Output:
Opening a resource.
Caught: Operation failed.
Cleanup completed.
End of program.
The finally block is useful for cleanup
operations, such as releasing resources or performing
final housekeeping.
It is not a replacement for proper resource management,
and execution can still be affected by termination
methods such as exit().
PHP includes several exception classes for common situations.
Exception — general exception.InvalidArgumentException — invalid argument supplied to a function.RuntimeException — an error that occurs during execution.LogicException — a problem related to program logic.LengthException — an invalid length.DomainException — a value outside a required domain.Example:
<?php
function setUsername(string $username): string {
if (trim($username) === "") {
throw new InvalidArgumentException(
"Username cannot be empty."
);
}
return $username;
}
try {
echo setUsername("");
} catch (InvalidArgumentException $e) {
echo $e->getMessage();
}
?>
Output:
Username cannot be empty.
Select exception classes based on what went wrong. This makes your code easier to understand and maintain.
You can create a custom exception by extending PHP's
built-in Exception class.
<?php
class InsufficientBalanceException extends Exception {
}
function withdraw(float $balance, float $amount): float {
if ($amount <= 0) {
throw new InvalidArgumentException(
"Withdrawal amount must be positive."
);
}
if ($amount > $balance) {
throw new InsufficientBalanceException(
"Insufficient account balance."
);
}
return $balance - $amount;
}
try {
$remaining = withdraw(1000, 1500);
echo "Remaining balance: " . $remaining;
} catch (InsufficientBalanceException $e) {
echo $e->getMessage();
} catch (InvalidArgumentException $e) {
echo $e->getMessage();
}
?>
Output:
Insufficient account balance.
Custom exceptions are useful in applications such as banking systems, student fee management, library management, and online admission systems.
An exception object provides methods that help you understand and investigate a problem.
getMessage() — returns the exception message.getCode() — returns the exception code.getFile() — returns the file where the exception was created.getLine() — returns the line where the exception was created.getTrace() — returns the stack trace as an array.getTraceAsString() — returns the stack trace as a string.Example:
<?php
try {
throw new Exception("Student record not found.");
} catch (Exception $e) {
echo "Message: " . $e->getMessage() . "<br>";
echo "File: " . $e->getFile() . "<br>";
echo "Line: " . $e->getLine();
}
?>
These methods are useful for debugging. Avoid displaying file paths and stack traces to public users because they may reveal internal application details.
This example checks a student's payment amount and throws an exception if the amount is invalid.
<?php
class InvalidPaymentException extends Exception {
}
function processPayment(
float $courseFee,
float $paidAmount
): float {
if ($courseFee <= 0) {
throw new InvalidArgumentException(
"Course fee must be greater than zero."
);
}
if ($paidAmount <= 0) {
throw new InvalidPaymentException(
"Payment amount must be greater than zero."
);
}
if ($paidAmount > $courseFee) {
throw new InvalidPaymentException(
"Payment cannot exceed the course fee."
);
}
return $courseFee - $paidAmount;
}
try {
$courseFee = 10000;
$paidAmount = 3000;
$remainingFee = processPayment(
$courseFee,
$paidAmount
);
echo "Course Fee: Rs. " . number_format($courseFee, 2);
echo "<br>Paid Amount: Rs. " . number_format($paidAmount, 2);
echo "<br>Remaining Fee: Rs. " . number_format($remainingFee, 2);
} catch (InvalidPaymentException $e) {
error_log($e->getMessage());
echo "Payment could not be processed.";
} catch (InvalidArgumentException $e) {
error_log($e->getMessage());
echo "Invalid course fee.";
} catch (Throwable $e) {
error_log($e->getMessage());
echo "An unexpected error occurred.";
}
?>
Output:
Course Fee: Rs. 10,000.00
Paid Amount: Rs. 3,000.00
Remaining Fee: Rs. 7,000.00
This is a demonstration of exception handling, not a complete payment system. Real payment processing also requires database transactions, authorization, and verification of payment records.
1. Which keyword is used to throw an exception?
2. Which block handles a matching exception?
3. Which method returns the exception message?