Object Interfaces

Object interfaces allow you to create code which specifies which methods a
class must implement, without having to define how these methods are
handled.

Interfaces are defined in the same way as a class, but with the interface
keyword replacing the class keyword and without any of the methods having
their contents defined.

All methods declared in an interface must be public; this is the nature of an
interface.

implements

To implement an interface, the implements operator is used.
All methods in the interface must be implemented within a class; failure to do
so will result in a fatal error. Classes may implement more than one interface
if desired by separating each interface with a comma.

Note:

Prior to PHP 5.3.9, a class could not implement two interfaces that
specified a method with the same name, since it would cause ambiguity.
More recent versions of PHP allow this as long as the duplicate methods
have the same signature.

User Contributed Notes 48 notes

It seems like many contributors are missing the point of using an INTERFACE. An INTERFACE is not specifically provided for abstraction. That's what a CLASS is used for. Most examples in this article of interfaces could be achieved just as easily using just classes alone.

An INTERFACE is provided so you can describe a set of functions and then hide the final implementation of those functions in an implementing class. This allows you to change the IMPLEMENTATION of those functions without changing how you use it.

For example: I have a database. I want to write a class that accesses the data in my database. I define an interface like this:

Then let's say we start out using a MySQL database. So we write a class to access the MySQL database:

class MySqlDatabase implements Database {function listOrders() {...}we write these methods as needed to get to the MySQL database tables. Then you can write your controller to use the interface as such:

Then - to switch our application to use the Oracle database instead of the MySQL database we only have to change ONE LINE of code:

$database = new OracleDatabase();

all other lines of code, such as:

foreach ($database->listOrders() as $order) {

will remain unchanged. The point is - the INTERFACE describes the methods that we need to access our database. It does NOT describe in any way HOW we achieve that. That's what the IMPLEMENTing class does. We can IMPLEMENT this interface as many times as we need in as many different ways as we need. We can then switch between implementations of the interface without impact to our code because the interface defines how we will use it regardless of how it actually works.

This is quite useful when you're using interfaces for identity more than the rigidity it places upon an API. You can get the same result by implementing multiple interfaces.

An example of where I've used this in the past is with EventListener objects ala Java's Swing UI. Some listeners are effectively the same thing but happen at different times therefore we can keep the same API but change the naming for clarity.

When should you use interfaces? What are they good for? Here are two examples.

1. Interfaces are an excellent way to implement reusability. You can create a general interface for a number of situations (such as a save to/load from disk interface.) You can then implement the interface in a variety of different ways (e.g. for formats such as tab delimited ASCII, XML and a database.) You can write code that asks the object to "save itself to disk" without having to worry what that means for the object in question. One object might save itself to the database, another to an XML and you can change this behavior over time without having to rewrite the calling code.

This allows you to write reusable calling code that can work for any number of different objects -- you don't need to know what kind of object it is, as long as it obeys the common interface.

2. Interfaces can also promote gradual evolution. On a recent project I had some very complicated work to do and I didn't know how to implement it. I could think of a "basic" implementation but I knew I would have to change it later. So I created interfaces in each of these cases, and created at least one "basic" implementation of the interface that was "good enough for now" even though I knew it would have to change later.

When I came back to make the changes, I was able to create some new implementations of these interfaces that added the extra features I needed. Some of my classes still used the "basic" implementations, but others needed the specialized ones. I was able to add the new features to the objects themselves without rewriting the calling code in most cases. It was easy to evolve my code in this way because the changes were mostly isolated -- they didn't spread all over the place like you might expect.

example(new One()); // One is doing somethingexample(new Two()); // Two is doing something

?>

If you have PHP 5.2 you can still declare static methods in interfaces. While you won't be able to call them via LSB, the "implements IDoSomething" can serve as a hint/reminder to other developers by saying "this class has a ::doSomething() method".Besides, you'll be upgrading to 5.3 soon, right? Right?

On an incidental note, it is not necessary for the implementation of an interface method to use the same variable names for its parameters that were used in the interface declaration.

More significantly, your interface method declarations can include default argument values. If you do, you must specify their implementations with default arguments, too. Just like the parameter names, the default argument values do not need to be the same. In fact, there doesn't seem to be any functionality to the one in the interface declaration at all beyond the fact that it is there.

To two notes below: There is one situation where classes and interfaces can be used interchangeably. In function definitions you can define parameter types to be classes or interfaces. If this was not so then there would not be much use for interfaces at all.

Note that not only do the parameters have different names ($ratio and $stuffing), but their default values are free to be different as well. There doesn't seem to be any purpose to the interface's default argument value except as a dummy placeholder to show that there is a default (a class implementing isStuffable will not be able to implement methods with the signatures getStuffed(), getStuffed($a), or getStuffed($a,$b)).

php at wallbash dot com's comment of "It's important to note this because it is very unexpected behavior and renders many common Interface completly useless" doesn't make sense.

the idea of the interface is to force objects that aren't related to be reused in a common way. without them, to force that requirement, all objects that need those methods implemented would have to be descended from a base class that's known to have those methods. that's clearly not a smart idea if these objects aren't actually related.

one example (that i'm currently working on) is a background service that pulls information down from different content providers. i have a transport and i have an import. for both, what actually happens in the background is different from provider to provider, but since i'm implementing a transport & import interface, i only need to write code once, because i know exactly the what methods will be implemented to get the job done. then, i just have a config file that loads the class dynamically. i don't need something like

if ( $provider == "some company" ){ // use this set of code}elseif ( $provider == "another company" ){ // use this other set of code}

it is expected behavior that when a class implements two interfaces that share one or more method names, an error is thrown, because interfaces don't relate to each other. if you want that sort of inferred behavior (i.e. A and B are different except for these shared methods), stick to [abstract] classes.

it sucks that interface methods might collide for some common types of tasks (get(), set(), etc.), so knowing that, design your interfaces with more unique method names.

PHP prevents interface a contant to be overridden by a class/interface that DIRECTLY inherits it. However, further inheritance allows it. That means that interface constants are not final as mentioned in a previous comment. Is this a bug or a feature?

Class T805 implements the interface Auxiliary_Platform. T806 does the same thing, but the method Health() is inherited from T805 (not the exact case, but you get the idea). PHP seems to be fine with this and everything still works fine. Do note that the rules for class inheritance doesn't change in this scenario.

If the code were to be the same, but instead T805 (or T806) DOES NOT implement Auxiliary_Platform, then it'll still work. Since T805 already follows the interface, everything that inherits T805 will also be valid. I would be careful about that. Personally, I don't consider this a bug.

This seems to work in PHP5.2.9-2, PHP5.3 and PHP5.3.1 (my current versions).

By asking your colleague to implement your interface, you are asking him to guarantee that he has implemented all the methods you need. He can implement multiple interfaces, each being a contract, so that the guy cleaning up the cruft down the road can see which methods belong to which area of concern; but since interfaces are primarily contracts rather than documentation, a class cannot implement two interfaces containing the same method since that would make the contract lose credibility through ambiguity. Thus a class can implement two interfaces with overlapping concerns only by factoring their common methods into a third interface that serves as a base for the first two, which resolves the contractual ambiguity.

The statement, that you have to implement _all_ methods of an interface has not to be taken that seriously, at least if you declare an abstract class and want to force the inheriting subclasses to implement the interface.Just leave out all methods that should be implemented by the subclasses. But never write something like this:

<?php

interface Foo {

function bar();

}

abstract class FooBar implements Foo {

abstract function bar(); // just for making clear, that this // method has to be implemented

While a subclass may implement an interface by extending an abstract class that implements the interface, I question whether it is good design to to do so. Here's what I would suggest while taking the liberty of modifying the above weather/wet model:

If you want to ensure implementation classes are correctly initialised (i.e. due to trickery one needs to do to work around lack of multiple inheritance), simply add __construct() to your interface, so risk of init being forgotten is reduced.

If you use namespaces and autoloading, do not forget to mention the use statement for each class used in yours arguments, before your class:

<?php #file : fruit/squeezable.phpnamespace fruituse Bar\Foo;

interface squeezable { public function squeeze (Foo $foo);}?>

<?php #file: orange

namespace fruit\citrus;

class orange { public function squeeze(Foo $foo);}#Will throw an exception Fatal error: Declaration of "fruit\citrus\orange::squeeze must be compatible with that of fruit\squeezable() in fruit/squeezable.php?>

to dlovell2011 at yahoo dot com wrote:It seems like many contributors are missing the point of using an INTERFACE. An INTERFACE is not specifically provided for abstraction. ...An INTERFACE is provided so you can describe a set of functions and then hide the final implementation of those functions in an implementing class. This allows you to change the IMPLEMENTATION of those functions without changing how you use it. --------------I believe the unique thing that Interfaces provide is to support the same functions in different classes that are **not descended from a common ancestor**. Different implementations of the same functions does not need interfaces--it can be achieved through subclasses.

If it isn't already obvious, you can create an object of a class above the class declaration if it does NOT implement an interface. However, when a class DOES implement an interface, PHP will throw a "class not found" error unless the instantiation declaration is _below_ the class definition.

<?php$bar = new foo(); // Valid

class foo{

}?>

<?php$bar = new foo(); // Invalid - throws fatal error

interface foo2{

}

class bar implements foo2{

}

$bar = new foo(); // Valid, since it is below the class declaration

?>

Also, @Jeffrey -- Lol? What? Is that a joke? PHP interfaces have nothing to do with connecting to "peripheral devices" or "cameras", etc. Not even in the least sense. This is a very common miscommunication with the word "interface", as interfaces in programming are not at all like interfaces in electronics or drivers, etc.

The structure I am working with has a lot of inheritance going on, but not all methods are specified in one place. I needed a way to make sure an interface would be used, but that the method(s) defined in the interface are defined somewhere.

As such, I learned that the parent can define the interface's methods, and then the children can override that method at will without having to worry about the interface.

To expand on nrg1981's example, the following is possible:

<?phpinterface water{ public function makeItWet();}

class weather{ public function makeItWet() { return 'it may or may not be wet'; }

An interface is in fact the same like an abstract class containing abstract methods, that's why interfaces share the same namespace as classes and why therefore "real" classes cannot have the same name as interfaces.

In their book on Design Patterns, Erich Gamma and his associates (AKA: "The Gang of Four") use the term "interface" and "abstract class" interchangeably. In working with PHP and design patterns, the interface, while clearly a "contract" of what to include in an implementation is also a helpful guide for both re-use and making changes. As long as the implemented changes follow the interface (whether it is an interface or abstract class with abstract methods), large complex programs can be safely updated without having to re-code an entire program or module.

In PHP coding with object interfaces (as a keyword) and "interfaces" in the more general context of use that includes both object interfaces and abstract classes, the purpose of "loose binding" (loosely bound objects) for ease of change and re-use is a helpful way to think about both uses of the term "interface." The focus shifts from "contractual" to "loose binding" for the purpose of cooperative development and re-use.

By asking your colleague to implement your interface, you are asking him to guarantee that he has implemented all the methods you need. He can implement multiple interfaces, each being a contract, so that the guy cleaning the cruft down the road can see which methods belong to which area of concern; but since interfaces are primarily contracts rather than documentation, a class cannot implement two interfaces containing the same method since that would make the contract lose credibility through ambiguity. Thus a class can implement two interfaces with overlapping concerns only by factoring their common methods into a third interface that serves as a base for the first two, which resolves the contractual ambiguity.

The "interface" is a method of enforcing that anyone who implements it must include all the functions declared in the interface. This is an abstraction method, since you cannot just declare a base class and do something like "public abstract function myTest();" and later on extend that class.

If you don't override the default value in a parameter list, it's assumed that the default value was received by time you have any control to read or relay the value on again. There should be no problem in having all or none of your parameters in an interface having a default value, as the value is "auto-filled" if not explicitly provided.

I just came across interfaces in PHP.. but I use them quite a bit in Java and Delphi. Currently building different DB wrappers, but all must enforce common access using a base class.. and also enforce that all of specific routines are implemented.

This may help understand EX.2. Below are modifiers and additions tothe code. Refer to EX.2 to make a complete code block(this saves commentspace!).I found the function definition baz(Baz $baz) baffling. Lucky was able to sus it out fast. Seems method baz requires just one arg and that must be an instance of the class Baz. Here is a way to know how to deal with that sort of arg...<?php# modify iface b...adding $num to get better understandinginterface b extends a{ public function baz(Baz $baz,$num);}# mod claas c class c implements b{ public function foo() { echo'foo from class c'; } public function baz(Baz $baz,$num) {var_dump ($baz);# object(Baz)#2 (1) { ["bb"]=> string(3) "hot" }echo '<br>'; echo $baz->bb." $num";echo '<br>';# hot 6}}# add a class Baz...class Baz{ public $bb='hot'; function ebaz(){ echo'this is BAZ'; }}# set instance of Baz and get some output...$bazI=new Baz;baz::ebaz();echo '<br>';# this is BAZc::baz($bazI,6);?>

FYI, interfaces can define constructors, destructors, and magic methods. This can be very helpful especially in the case of constructors when instantiating an implementing class via reflection in some sort of factory. Of course, it is not recommended to do such a thing since it goes against the nature of a true interface.

By definition, all methods in an interface are abstract. So the above code segment is equivalent to your interface definitions and results in the same error. Why? Let's have a look at the PHP manual. From the second paragraph on class abstraction:

"When inheriting from an abstract class, all methods marked abstract in the parent's class declaration must be defined by the child;"

If both methods need the same name, then you'll have to use non-abstract methods. In this case, interfaces aren't the right tool for the job. You'll want to use abstract classes (or just regular classes).

Classes and interface names share a common name space, so you can't have a class and an interface with the same name, even though the two can never be used ambiguously (i.e. there are no circumstances in which a class and an interface can be used interchangeably). e.g. this will not work:

interface foo {public function bling();}

class foo implements foo {public function bling() {}}

You will get a 'Cannot redeclare class' error, even though it's only been declared as a class once.

Another note about default values in interfaces is that an class must implement at least the arguments as in the interface. that is: an implementation may have more arguments but not less if these additional arguments have an default value and thus can be called as declared in the interface.

Here mySecondClass will print an fatal error while myThirdClass is just fine because myThirdClass::setStuff($id, $name); is valid and thus fullfills the interface requirements. an interface declares as set of requirement on how methods can be called and any class implementing an interface thus agrees that is will provide these methods and that they can be called as in the interface. adding additional arguments with default values is thus allowed because it does not violate the agreement that the method can be called as in the interface.

PHP doesn't generate a Fatal Error in this case, although the method declaration in the class differs from that in the interface. This situation doesn't seem good to me: I'd prefer classes being strictly bound to their interfaces.

Makes them useles a bit. I give an example:I have a class that enumerate (so implements iterator) a interface that has method key() that returns key for the enumerated object.I cannot implement iterator, that enumerates the objects by itself (so current() returns this), because of collision of method key(). But it's not collision - the key in the iterator and the key in the enumerated object has the same meaning and allways returns same values. (Common example of this iterator is iterator, that reads from database - make a special object for each row is waste of time).

Yes - there are workarounds - e.g. rewrite the code so current don't return this - but it's in some cases waste of processor time. Or I can rename the method key in enumerated object - but why should I wrote the same method twice? It's either waste of time (if the function key is simply duplicated) or waste of time (if the renamed key calls original key).Well, the right, clear way there would be to redefine interface iterator -- move the method key to the ancestor of iterator, and makes the ancestor ancestor of enumerated interface too. But it's (with built-in interfaces) impossible too.