Position actuelle: Accueil> Derniers articles> Un non-service qui se produit lorsqu'il est incompatible avec la version PHP

Un non-service qui se produit lorsqu'il est incompatible avec la version PHP

gitbox 2025-05-29

Dans PHP, Serialize () et Unserialize () sont une paire de fonctions centrales utilisées pour la persistance des objets et des données. Ils permettent de convertir les structures de données complexes (telles que les objets, les tableaux, etc.) en chaînes et stockées ou transférées. Cependant, lorsque vous passez la chaîne sérialisée d'une version PHP à une autre (en particulier sur les grandes versions, comme de PHP 5 à PHP 7 ou PHP 8), puis essayez de la désérialiser, vous pouvez rencontrer des problèmes inattendus.

Problèmes d'incompatibilité courants

1. Structure de classe incohérente

Lorsque l'objet est sérialisé et que la classe a été modifiée dans l'environnement PHP cible (tel que l'addition / la suppression de l'attribut nouvel, les modifications de l'espace de noms, etc.), elle peut entraîner la manquante et même lancée l'attribut et même lancé pendant la désérialisation:

 $serialized = 'O:8:"UserData":2:{s:4:"name";s:4:"John";s:3:"age";i:30;}';
unserialize($serialized); // si UserData La structure des classes a changé,Il peut échouer ici

2. Modifications du traitement de type

PHP 7 commence à introduire des déclarations de type strict. Si certaines propriétés de l'ancienne version sont attribuées dynamiquement, mais que la classe utilise des types de constructeurs stricts dans la nouvelle version, une erreur de non-correspondance de type peut se produire lors de la désérialisation.

3. Renforcer les stratégies de sécurité

Depuis PHP 7.0, la fonction Unserialize () introduit le paramètre autorisé_classes pour contrôler quelles classes peuvent être désérialisées en toute sécurité. Cela empêche le problème de l'injection de code malveillant, mais signifie également que le vieux code peut avoir des problèmes de non-définition du paramètre.

 $data = file_get_contents('https://gitbox.net/data/serialized-user.txt');
$user = unserialize($data, ["allowed_classes" => ["UserData"]]); // Plus sûr mais plus difficile

4. Différences de soutien à la fermeture

Les fonctions anonymes (fermeture) ne peuvent pas être sérialisées directement dans PHP, mais certaines bibliothèques tierces (telles que l'OPIS / fermeture ) fournissent des mécanismes d'encapsulation. Si votre application utilise ces méthodes d'encapsulation lors de la migration entre les versions PHP, il est nécessaire d'assurer la compatibilité des mêmes bibliothèques dans la version cible.

Comment gérer l'incompatibilité entre les versions

1. Évitez le transfert croisé d'objets

S'il est contrôlé, il n'est pas recommandé d'utiliser la sérialisation des objets pour la persistance ou la transmission du réseau. Il est plus compatible avec des formats standard tels que JSON:

 $json = json_encode(['name' => 'John', 'age' => 30]);
$data = json_decode($json, true);

2. Utilisez __Sleep () et __wakeUp () pour contrôler la logique de sérialisation

Vous pouvez définir __Sleep () dans la classe pour contrôler les attributs sérialisés ou effectuer un traitement compatible sur la sérialisation de la solution dans __wakeup () :

 class UserData {
    public $name;
    public $age;
    public function __wakeup() {
        if (!isset($this->age)) {
            $this->age = 0;
        }
    }
}

3. Données de résérialisation par lots avant la migration de la version

Avant de mettre à niveau la version PHP, vous pouvez éliminer toutes les données sérialisées, la décoder en utilisant la version actuelle d' Unserialize () , puis la respecter via la nouvelle version de Serialize () pour s'assurer que le format répond à la version cible.

4. Utilisez JSON pour remplacer la sérialisation des objets

Si vous ne comptez pas sur le comportement de l'objet (tel que les méthodes), vous pouvez complètement remplacer les exigences de persistance de l'objet par JSON pour éviter les risques apportés par Unserialize () .

 // Alternatives:utiliser JSON Stocker les informations utilisateur
file_put_contents('https://gitbox.net/data/user.json', json_encode($user));

5. À l'aide de couches ou de bibliothèques intermédiaires

En utilisant des outils de framework modernes tels que Symfony Serializer et l'encapsulation de sérialisation de Laravel, ils sont généralement plus flexibles pour la migration des versions et peuvent mieux résumer et gérer les éléments incompatibles.

résumé

Unserialize () est un outil puissant mais fragile qui peut rencontrer divers problèmes de compatibilité lors de la migration des données entre différentes versions PHP. La meilleure stratégie consiste à réduire la dépendance, à contrôler la portée et à choisir un format d'échange de données plus contrôlable. Si la sérialisation des objets est requise, elle doit être accompagnée de mécanismes de contrôle structurel clair et de détection de version. Sinon, ces "petites fosses" cachées derrière Unserialize () peuvent facilement devenir des "pièges" après leur lancement.