Interfaces in PHP

PHP Interfaces
Interfaces in PHP are an essential aspect of Object-Oriented Programming (OOP). They allow developers to define a set of methods that a class must implement, providing a way to specify a contract for classes without dictating how the methods should be implemented.

This article explores how to declare interfaces, implement them, and how interface inheritance works in PHP, complete with code examples.

Declaring Interfaces

What is an Interface?

An interface is a blueprint for a class. It defines a set of methods that any class implementing the interface must provide. Interfaces do not contain any implementation details; they only declare method signatures. This promotes a consistent interface across different classes, ensuring that they adhere to a specific contract.

Defining an Interface

In PHP, interfaces are declared using the interface keyword. Here is a basic example:

				
					<?php
interface Logger {
    public function log($message);
}
?>

				
			

In this example, the Logger interface declares a single method log that accepts a $message parameter. Any class implementing this interface must provide an implementation for this method.

Multiple Method Declarations

Interfaces can declare multiple methods. Here’s an example:

				
					<?php
interface Database {
    public function connect($host, $user, $password, $dbname);
    public function query($sql);
    public function fetch($result);
}
?>

				
			

In this example, the Database interface declares three methods: connect, query, and fetch. Any class implementing this interface must provide implementations for all three methods.

Implementing Interfaces

Implementing a Single Interface

A class implements an interface using the implements keyword. Here’s an example:

				
					<?php
interface Logger {
    public function log($message);
}

class FileLogger implements Logger {
    public function log($message) {
        // Log message to a file
        file_put_contents('log.txt', $message . PHP_EOL, FILE_APPEND);
    }
}

$logger = new FileLogger();
$logger->log("This is a log message.");
?>

				
			

In this example, the FileLogger class implements the Logger interface by providing an implementation of the log method. When log is called on an instance of FileLogger, the message is appended to a file.

Implementing Multiple Interfaces

A class can implement multiple interfaces, allowing for more flexible and reusable code. Here’s an example:

				
					<?php
interface Logger {
    public function log($message);
}

interface ErrorHandler {
    public function handleError($error);
}

class ApplicationLogger implements Logger, ErrorHandler {
    public function log($message) {
        // Log message to a file
        file_put_contents('app_log.txt', $message . PHP_EOL, FILE_APPEND);
    }

    public function handleError($error) {
        // Handle error by logging it
        $this->log("Error: " . $error);
    }
}

$logger = new ApplicationLogger();
$logger->log("This is a log message.");
$logger->handleError("This is an error message.");
?>

				
			

In this example, the ApplicationLogger class implements both the Logger and ErrorHandler interfaces, providing implementations for both the log and handleError methods.

Interface Inheritance

What is Interface Inheritance?

Interface inheritance allows an interface to inherit methods from another interface. This enables the creation of more specific interfaces that extend the functionality of existing ones.

Defining and Implementing Inherited Interfaces

Here’s an example of interface inheritance:

				
					<?php
interface Logger {
    public function log($message);
}

interface AdvancedLogger extends Logger {
    public function logWarning($message);
    public function logError($message);
}

class SystemLogger implements AdvancedLogger {
    public function log($message) {
        // Log general message
        file_put_contents('system_log.txt', $message . PHP_EOL, FILE_APPEND);
    }

    public function logWarning($message) {
        // Log warning message
        file_put_contents('system_log.txt', "WARNING: " . $message . PHP_EOL, FILE_APPEND);
    }

    public function logError($message) {
        // Log error message
        file_put_contents('system_log.txt', "ERROR: " . $message . PHP_EOL, FILE_APPEND);
    }
}

$logger = new SystemLogger();
$logger->log("This is a general log message.");
$logger->logWarning("This is a warning message.");
$logger->logError("This is an error message.");
?>

				
			

In this example, the AdvancedLogger interface extends the Logger interface, adding logWarning and logError methods. The SystemLogger class implements the AdvancedLogger interface, providing implementations for all methods, including the inherited log method.

Multiple Interface Inheritance

Interfaces can also inherit from multiple other interfaces, creating complex hierarchies. Here’s an example:

				
					<?php
interface Logger {
    public function log($message);
}

interface ErrorHandler {
    public function handleError($error);
}

interface AdvancedLogger extends Logger, ErrorHandler {
    public function logWarning($message);
    public function logError($message);
}

class ApplicationLogger implements AdvancedLogger {
    public function log($message) {
        // Log general message
        file_put_contents('app_log.txt', $message . PHP_EOL, FILE_APPEND);
    }

    public function handleError($error) {
        // Handle error by logging it
        $this->log("Error: " . $error);
    }

    public function logWarning($message) {
        // Log warning message
        file_put_contents('app_log.txt', "WARNING: " . $message . PHP_EOL, FILE_APPEND);
    }

    public function logError($message) {
        // Log error message
        file_put_contents('app_log.txt', "ERROR: " . $message . PHP_EOL, FILE_APPEND);
    }
}

$logger = new ApplicationLogger();
$logger->log("This is a general log message.");
$logger->handleError("This is an error message.");
$logger->logWarning("This is a warning message.");
$logger->logError("This is an error message.");
?>

				
			

In this example, the AdvancedLogger interface inherits from both Logger and ErrorHandler, and the ApplicationLogger class implements the AdvancedLogger interface, providing implementations for all methods.

Practical Use Case: Payment Processing

Interfaces are particularly useful in scenarios where multiple classes need to follow the same contract, such as in a payment processing system.

Defining Payment Interfaces

				
					<?php
interface PaymentGateway {
    public function processPayment($amount);
}

interface RefundablePaymentGateway extends PaymentGateway {
    public function processRefund($transactionId, $amount);
}
?>

				
			

Implementing Payment Interfaces

				
					<?php
class StripePaymentGateway implements RefundablePaymentGateway {
    public function processPayment($amount) {
        // Process payment using Stripe API
        return "Processed payment of $amount using Stripe.";
    }

    public function processRefund($transactionId, $amount) {
        // Process refund using Stripe API
        return "Processed refund of $amount for transaction $transactionId using Stripe.";
    }
}

class PayPalPaymentGateway implements RefundablePaymentGateway {
    public function processPayment($amount) {
        // Process payment using PayPal API
        return "Processed payment of $amount using PayPal.";
    }

    public function processRefund($transactionId, $amount) {
        // Process refund using PayPal API
        return "Processed refund of $amount for transaction $transactionId using PayPal.";
    }
}

$stripeGateway = new StripePaymentGateway();
echo $stripeGateway->processPayment(100) . "\n";  // Outputs: Processed payment of 100 using Stripe.
echo $stripeGateway->processRefund("TXN12345", 50) . "\n";  // Outputs: Processed refund of 50 for transaction TXN12345 using Stripe.

$paypalGateway = new PayPalPaymentGateway();
echo $paypalGateway->processPayment(200) . "\n";  // Outputs: Processed payment of 200 using PayPal.
echo $paypalGateway->processRefund("TXN67890", 75) . "\n";  // Outputs: Processed refund of 75 for transaction TXN67890 using PayPal.
?>

				
			

In this example, the PaymentGateway interface defines a method for processing payments, and the RefundablePaymentGateway interface extends it with a method for processing refunds. The StripePaymentGateway and PayPalPaymentGateway classes implement the RefundablePaymentGateway interface, providing specific implementations for processing payments and refunds using their respective APIs.

Conclusion

Interfaces in PHP are powerful tools for defining consistent contracts for classes. They allow developers to specify a set of methods that must be implemented, promoting code consistency and reusability. By using interfaces, developers can ensure that different classes adhere to a common interface, making the code more maintainable and extensible.

In this article, we explored how to declare interfaces, implement them in classes, and use interface inheritance to create complex hierarchies. We also looked at practical examples, such as a payment processing system, to illustrate the real-world applications of interfaces. Understanding and effectively using interfaces is crucial for writing robust, scalable, and maintainable object-oriented code in PHP.

Scroll to Top