Gravação de propriedades através de magia em OOP em PHP

O método mágico __set é chamado ao tentar alterar o valor de uma propriedade inexistente ou inacessível. Ele aceita como parâmetros o nome da propriedade e o valor que está sendo atribuído a ela.

Vamos ver um exemplo prático. Suponha que temos a seguinte classe Test:

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

Vamos criar neste classe o método mágico __set, que usando a função var_dump exibirá o nome da propriedade que está sendo acessada e o valor que está tentando ser definido para ela:

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

Vamos testar o funcionamento da nossa classe:

index.php<?php
  $test = new Test;
  $test->prop = 'value'; // var_dump do método __set exibirá 'prop value'
?>

Agora, vamos definir o valor para a propriedade cujo nome está armazenado na variável $property:

Test.php<?php
  class Test
  {
    private $prop1;
    private $prop2;
    
    public function __set($property, $value)
    {
      $this->$property = $value; // define o valor
    }
  }
?>

Agora podemos escrever nas propriedades privadas de fora da classe:

index.php<?php
  $test = new Test;
  
  $test->prop1 = 1; // escreverá 1
  $test->prop2 = 2; // escreverá 2
?>

Podemos escrever, no entanto, verificar se algo foi escrito lá - não, pois as propriedades são privadas.

Pode-se criar um getter para essas propriedades ou simplesmente usar o método mágico __get. Vamos usar a segunda opção:

Test.php<?php
  class Test
  {
    private $prop1;
    private $prop2;
    
    public function __set($property, $value)
    {
      $this->$property = $value;
    }
    
    // Getter mágico de propriedades:
    public function __get($property)
    {
      return $this->$property;
    }
  }
?>

Agora podemos verificar o funcionamento da nossa classe. Vamos testar:

index.php<?php
  $test = new Test;
  
  $test->prop1 = 1; // escreverá 1
  $test->prop2 = 2; // escreverá 2
  
  echo $test->prop1; // exibirá 1
  echo $test->prop2; // exibirá 2
?>

Na verdade, claro, não devemos permitir que qualquer um escreva em propriedades privadas, caso contrário, perde-se o sentido dessas propriedades privadas (seria mais fácil torná-las públicas e pronto).

Portanto, este método deve ser usado apenas quando há uma real necessidade. Nas próximas lições, veremos ainda mais exemplos de aplicações bem-sucedidas.