Geschützte Eigenschaften in PHP sind nicht wirklich geschützt

06.03.2011

So wie in PHP private Eigenschaften nicht wirklich privat sind, so sind auch geschützte (protected) nicht wirklich geschützt.

Nehmen wir folgende Klasse:

class Base{
  protected $x;

  public function getX(){
    return $this->x;}}

Abgeleitete Klassen könnten Methoden enthalten, die $x einen Wert geben, sie könnten aber auch getX() überschreiben, natürlich ginge auch beides.

Ein Beispiel für eine solche ist diese hier:

class GoodChild extends Base{
  public function setX($x){
    if (is_integer($x)){
      $this->x=$x;}}}

Diese stellt sicher, dass $x nur Ganzzahlen (oder initial NULL) enthält. Doch tut sie das wirklich?

Hier ist eine weitere abgeleitete Klasse:

class EvilChild extends Base{
  public function setX(Base $b, $x){
    $b->x=$x;}}

Da protected klassen-, nicht objektbezogen ist, funktioniert das. Objekte abgeleiteter Klassen haben Zugriff auf die geschützten Eigenschaften, die in ihrer Basisklasse definiert wurden.

Aber genau das wird nun zum Problem.

$good=new GoodChild();
$evil=new EvilChild();
$evil->setX($good, 'foo'); // Works!

Da $x zur Basisklasse gehört, haben abgeleitete Klassen auch Zugriff auf $x in Objekten anderer abgeleiteter Klassen. $evil hat also vollen Zugriff auf alle geschützten Eigenschaften (und Methoden) von $good.

Somit können unüberschaubare Abhängigkeiten entstehen, ein wahrlich unglücklicher Zustand.