interface_exists

Checks whether an interface with the given name is defined, optionally running autoloaders first.

Signature
interface_exists(string $interface, bool $autoload = true): bool
  • Added in PHP 5.0.2

Parameters

ParameterTypeDescription
$interfacestringThe interface name, fully qualified with its namespace and no leading backslash.
$autoloadoptionalbool= trueWhether registered autoloaders may be invoked to try to load the interface.

Return value

booltrue if the interface is defined, false otherwise.

Errors

Does not throw by itself, but with $autoload left at true a registered autoloader may throw or fatal while trying to load the name.

interface_exists() answers one narrow question: has this exact interface been declared in the current request? It returns false for classes, traits and enums with the same name, so it is stricter than class_exists().

When to reach for it

  • Optional integrations. Your library can implement a PSR interface only if the consuming project actually ships it. Guard the class ... implements ... declaration with a check.
  • Feature detection across versions. An interface added in a newer release of a dependency can be probed before you rely on it.
  • Plugin loading, where a contract file may or may not be present.

What trips people up

Namespaces are the usual bug. The name is resolved as-is, never against the current use statements or the enclosing namespace, so interface_exists('Logger') from inside App\Log looks for a global Logger. Pass Psr\Log\LoggerInterface::class or build the string with __NAMESPACE__ . '\\Logger'.

The second gotcha is autoloading. With the default true, a poorly written autoloader that does require without checking the file exists will fatal on a name that was only being probed. Pass false when you are just testing a guess, and leave it true when the interface really should be loadable.

Example

Try it yourself
Loading editor…
Press Run to execute the code.

When to use it

  • Declaring a class that implements a PSR interface only when that package is installed.
  • Checking a framework contract exists before registering an optional adapter in a plugin bootstrap.
  • Verifying a generated stub interface was written before compiling code against it.

Frequently asked questions

What is the difference between class_exists and interface_exists?

class_exists() returns true only for classes, and interface_exists() only for interfaces; neither matches the other's kind. Use enum_exists() for enums and trait_exists() for traits.

Does interface_exists trigger the autoloader?

Yes, by default. Pass false as the second argument to check only what is already loaded, which is safer when you are probing a name that may not exist.

Why does interface_exists return false for an interface I can see?

Almost always a namespace problem — the name is not resolved against `use` statements. Pass MyInterface::class instead of the short string.

More examples

Declaring a class conditionally

The interface is defined only if it is not already present, so the file is safe to include twice. Box then implements it either way, and the instanceof check confirms the contract is in place.

Example · php
<?php
if (!interface_exists('Renderer', false)) {
    interface Renderer { public function render(): string; }
}

class Box implements Renderer {
    public function render(): string { return '[box]'; }
}

$b = new Box();
echo $b->render(), "\n";
var_dump($b instanceof Renderer);

Namespaced names must be fully qualified

The bare name fails because it is looked up in the global namespace. Both the __NAMESPACE__ concatenation and ::class produce "App\Contracts\Cacheable", which is what the function needs.

Example · php
<?php
namespace App\Contracts;

interface Cacheable {}

var_dump(interface_exists('Cacheable', false));
var_dump(interface_exists(__NAMESPACE__ . '\\Cacheable', false));
var_dump(interface_exists(Cacheable::class, false));
echo Cacheable::class, "\n";

Discussion

  • Be the first to comment on this lesson.