Usamos cookies para medir audiência e melhorar sua experiência. Você pode aceitar ou recusar a qualquer momento. Veja sobre o iMasters.
Usando o serialize do PHP, nao estou conseguindo descobrir por que ele converte determinados caracteres. Andei pesquisando e alguns dizem para usar html_entity_decode, porém, neste caso não da certo.
Exemplo:
class Player
{
protected $tipo;
//as duas propriedades abaixo não são serializadas pela classe Jogador.
//Pois, propriedade private não é visivel no escopo da classe filha. No caso da propriedade estatica, ela por default não é serializada.
private $maxPlayer;
private $experiencia;
public static $roupa;
public function __construct()
{
$this->maxPlayer = 2;
$this->experiencia = 1500;
static::$roupa = 'casual';
}
protected function defaultMaxPlayer()
{
$this->maxPlayer = 4;
}
}
class Jogador extends Player
{
public $nome;
private $hp;
protected $score;
public function __construct($nome)
{
$this->nome = $nome;
$this->hp = 120;
$this->score = 3;
$this->tipo = 'Jogador';
}
public function __sleep()
{
//omitimos a propriedade 'hp', pois ela será redefinida na wakeup, então não é interessante te-la na nossa string de serialização.
return array("nome", "score", "tipo");
}
public function __wakeup()
{
$this->hp = 100;
parent::defaultMaxPlayer();
}
public function dizerOla()
{
echo "<br /><br /> Olá, método executado.";
}
}
$jogador = new Jogador('Rafael');
$jogadorSerialize = serialize($jogador);
//note que a saida possui caracteres estranhos que nao deviam estar presente. Exemplo ?? devia ser apenas
var_dump($jogadorSerialize);
Isso pode gerar um problema grave.
Por exemplo:
se eu ao invés de debugar a string serializada com var_dump eu der um echo:
echo $jogadorSerialize;
a saida no navegador será (85 caracteres):
O:7:"Jogador":3:{s:4:"nome";s:6:"Felipe";s:8:"score";i:3;s:7:"tipo";s:7:"Jogador";}
e não (89 caracteres):
O:7:"Jogador":3:{s:4:"nome";s:6:"Felipe";s:8:"��score";i:3;s:7:"��tipo";s:7:"Jogador";}
agora imagine o problema se eu copiasse manualmente a string gerada com echo e tentasse criar o objeto numa outra página.
Algo do tipo:
$stringSerialize = <<<DATA
O:7:"Jogador":3:{s:4:"nome";s:6:"Felipe";s:8:"score";i:3;s:7:"tipo";s:7:"Jogador";}
DATA;
$myObject = unserialize($stringSerialize);
a função unserialize geraria um erro Notice com a mensagem 'Error at offset 54 of 85 bytes' - pois não foi passado os bytes completos. (perdemos 5 caracteres).
Alguém sabe o por que o serialize gera este tipo de conversão, se é normal...?
Testei com o uso da interface nativa do PHP, a Serializable e ela não gera essa conversão estranha mencionada.
Deve-se lembrar que a interface Serializable substitui os métodos mágicos __sleep e __wakeup, assim, a conversão dos caracteres pode ocorrer nestes métodos mágicos quando dado serialize().
Fica a dica para quem vai usar serialização com PHP, tomar cuidado com serialização com métodos mágicos.
Mas fica aberta a questão, se alguém souber se esses métodos mágicos realmente fazem conversão informe.
Como sempre, encaro o fórum aqui como um lugar de aprendizado, então segue o código usando a interface Serializable para solucionar talvez essa questão que alguns possam enfrentar.
class Jogador implements Serializable
{
public $nome;
private $hp;
protected $score;
public function __construct($nome)
{
$this->nome = $nome;
$this->hp = 120;
$this->score = 3;
}
public function serialize()
{
return serialize(array(
'nome' => $this->nome,
'score' => $this->score
));
}
public function unserialize($serialized)
{
$data = unserialize($serialized);
if (isset($data['nome']) && isset($data['score']))
{
$this->nome = $data['nome'];
$this->score = $data['score'];
$this->hp = 100;
}
else
{
echo 'Erro ao deserializar objeto';
}
}
public function dizerOla()
{
echo "<br /><br /> Olá, método executado.";
}
}
$jogador = new Jogador('Felipe');
$jogadorSerialize = serialize($jogador);
var_dump($jogadorSerialize);
exit();
se der um echo() ou var_dump vai ter o mesmo número de caracteres, podendo copiar a string diretamente do echo() que não vai dar problema de Offset.
//65 caracteres
echo str($jogadorSerialize);
//65 caracteres
var_dump($jogadorSerialize);
Quem souber a respeito dos caracteres estranhos gerados sem o uso da interface Serializable, colabore respondendo o tópico.
Carregando comentários...