Записване на свойства чрез магия в ООП в PHP

Магическият метод __set се извиква при опит за промяна на стойността на несъществуващо или скрито свойство. Като параметри той приема името на свойството и стойността, която се опитват да му присвоят.

Нека да разгледаме практически пример. Да предположим, че имаме даден следния клас Test:

Test.php<?php
  class Test
  {
    private $prop1;
    private $prop2;
  }
?>

Нека в този клас направим магически метод __set, който с помощта на функцията var_dump ще извежда името на свойството, към което е направено обръщение, и стойността, която се опитват да зададат на това свойство:

Test.php<?php
  class Test
  {
    private $prop1;
    private $prop2;
    
    public function __set($property, $value)
    {
      var_dump($property . ' ' .$value);
    }
  }
?>

Нека проверим работата на нашия клас:

index.php<?php
  $test = new Test;
  $test->prop = 'value'; // var_dump на метода __set ще изведе 'prop value'
?>

Сега нека да задаваме стойност на свойство, чието име се съхранява в променливата $property:

Test.php<?php
  class Test
  {
    private $prop1;
    private $prop2;
    
    public function __set($property, $value)
    {
      $this->$property = $value; // задаваме стойност
    }
  }
?>

Сега ще можем да записваме в частни свойства отвън на класа:

index.php<?php
  $test = new Test;
  
  $test->prop1 = 1; // ще запишем 1
  $test->prop2 = 2; // ще запишем 2
?>

Можем да записваме, но да проверим дали нещо е записано - не, тъй като свойствата са частни.

Може да се направи гетър за тези свойства или просто да се използва магически метод __get. Ще използваме втория вариант:

Test.php<?php
  class Test
  {
    private $prop1;
    private $prop2;
    
    public function __set($property, $value)
    {
      $this->$property = $value;
    }
    
    // Магически гетър за свойства:
    public function __get($property)
    {
      return $this->$property;
    }
  }
?>

Сега вече можем да проверим работата на нашия клас. Нека проверим:

index.php<?php
  $test = new Test;
  
  $test->prop1 = 1; // записваме 1
  $test->prop2 = 2; // записваме 2
  
  echo $test->prop1; // ще изведе 1
  echo $test->prop2; // ще изведе 2
?>

Разбира се, не би трябвало да се разрешава на всички да записват в частни свойства, иначе смисълът на тези частни свойства (по-лесно е да се направят публични и това е всичко).

Затова този метод трябва да се прилага само тогава, когато наистина има необходимост. В следващите уроци ще разгледаме примери за успешно приложение.