Reputation: 17256
I am implementing an Adapter pattern for testing purposes, and I would like to type hint the return of the Adapter with the methods of two distinct classes, how can I achieve that?
class Foo {
public function somethingOnlyFooHave() {};
}
class Adapter {
protected $handler;
public function __construct(object $handler) {
$this->handler = $handler;
}
public function __call($name, ...$args) {
$this->handler->$name($args);
}
public function somethingOnlyTheAdapterHave() {}
}
$foo = new Adapter(new Foo);
// How can I get type-hinting for both the Adapter and Foo?
$foo->somethingOnlyFooHave();
$foo->somethingOnlyTheAdapterHave();
Upvotes: 0
Views: 981
Reputation: 3959
Honestly this is why the adapter pattern is generally seen as an anti-pattern, whereas strategy is the one that is preferred - adapters can get you in all sorts of problems :)
As stated above, however - with recent versions of PHP you can now use union types, and typehint both class return values. It is much better however, from a code stability perspective, to instead have each of your adapters implement an interface, and typehint that interface.
Upvotes: 0
Reputation: 17256
Seems PHP can't do this natively, but If you're using PHPStorm 2018.3+, you can use Union Types (or Intersection Types), as long as it's not on the __construct
:
class Foo {
public function somethingOnlyFooHave() {}
}
class Adapter {
protected $handler;
public function __construct(object $handler) {
$this->handler = $handler;
}
public function __call($name, ...$args) {
$this->handler->$name($args);
}
/**
* @return Adapter|Foo
*/
public function get() {
return $this;
}
public function somethingOnlyAdapterHave() {}
}
$foo_adapter = ( new Adapter(new Foo) )->get();
// The following methods receives type-hinting:
$foo_adapter->somethingOnlyFooHave();
$foo_adapter->somethingOnlyAdapterHave();
Useful links:
Upvotes: 0