## Les changements de rétrocompatibilités

### PHP Core

#### Restrictions d'acceès $GLOBALS

L'accès au tableau $GLOBALS est maintenant soumis à un certain nombre de restrictions. L'accès en lecture et en écriture aux éléments individuels du tableau tel que `$GLOBALS['var']` continue de fonctionner tel quel. L'accès en lecture seule à l'ensemble du tableau $GLOBALS continue également d'être supporté. Cependant, l'accès en écriture à l'ensemble du tableau $GLOBALS n'est plus supporté. Par exemple, `array_pop($GLOBALS)` générera une erreur.

#### L'utilisation de variables static dans les méthods héritées.

Lorsqu'une méthode utilisant des variables static est héritée (mais non surchargée), la méthode héritée partagera désormais les variables.

`<?php
class A {
public static function counter() {
static $counter = 0;
$counter++;
return $counter;
}
}
class B extends A {}
var_dump(A::counter()); // int(1)
var_dump(A::counter()); // int(2)
var_dump(B::counter()); // int(3), précédemment int(1)
var_dump(B::counter()); // int(4), précédemment int(2)
?>`
Cela signifie que les variables statiques dans les méthodes se comportent désormais de la même manière que les propriétés statiques.

#### Les paramètres optionnels spécifié avant les paramètres requis

Un paramètre optionnel spécifié avant les paramètres requis est maintenant toujours traité comme requis, même lorsqu'il est appelé en utilisant les arguments nommés. À partir de PHP 8.0.0, mais avant PHP 8.1.0, le code ci-dessous émet une note de dépréciation sur la définition, mais s'exécute avec succès lorsqu'il est appelé. À partir de PHP 8.1.0, une erreur de la classe ArgumentCountError est lancée, comme ce serait le cas lorsqu'il est appelé avec des arguments positionnels.

`<?php
function makeyogurt($container = "bowl", $flavour)
{
return "Making a $container of $flavour yogurt.\n";
}
try
{
echo makeyogurt(flavour: "raspberry");
}
catch (Error $e)
{
echo get_class($e), ' - ', $e->getMessage(), "\n";
}
?>`

Résultat de l'exemple ci-dessus en PHP 8.0 :

    Deprecated: Required parameter $flavour follows optional parameter $container
     in example.php on line 3
    Making a bowl of raspberry yogurt.

Résultat de l'exemple ci-dessus en PHP 8.1 :

    Deprecated: Optional parameter $container declared before required parameter
     $flavour is implicitly treated as a required parameter in example.php on line 3
    ArgumentCountError - makeyogurt(): Argument #1 ($container) not passed

Notez qu'une valeur par défaut de `null` peut être utilisée avant les paramètres requis pour spécifier un type nullable, mais le paramètre sera toujours requis.

#### La compatibilité des types de retour avec les classes internes

La plupart des méthodes internes non finales nécessitent désormais que les méthodes de surcharge déclarent un type de retour compatible, sinon une note de dépréciation est émise lors de la validation de l'héritage. Dans le cas où le type de retour ne peut pas être déclaré pour une méthode de surcharge en raison de préoccupations de compatibilité inter-version de PHP, un attribut ReturnTypeWillChange peut être ajouté pour supprimer la note de dépréciation.

#### Nouveau mots-clés

`readonly` est désormais un mot-clé. Cependant, il peut toujours être utilisé comme nom de fonction.

`never` est désormais un mot réservé, donc il ne peut pas être utilisé pour nommer une classe, une interface ou un trait, et est également interdit d'être utilisé dans les namespaces.

### Migration de ressource vers objet

Plusieurs resources ont été migrées vers des objets. Les vérifications de valeur de retour utilisant is_resource() doivent être remplacées par des vérifications de `false`.

- Les fonctions FileInfo acceptent et retournent désormais des objets finfo au lieu de resources `fileinfo`.

- Les fonctions FTP acceptent et retournent désormais des objets FTP\Connection au lieu de resources `ftp`.

- Les fonctions IMAP acceptent et retournent désormais des objets IMAP\Connection au lieu de resources `imap`.

- Les fonctions LDAP acceptent et retournent désormais des objets LDAP\Connection au lieu de resources `ldap`.

- Les fonctions LDAP acceptent et retournent désormais des objets LDAP\Result au lieu de resources `ldap result`.

- Les fonctions LDAP acceptent et retournent désormais des objets LDAP\ResultEntry au lieu de resources `ldap result entry`.

- Les fonctions PgSQL acceptent et retournent désormais des objets PgSql\Connection au lieu de resources `pgsql link`.

- Les fonctions PgSQL acceptent et retournent désormais des objets PgSql\Result au lieu de resources `pgsql result`.

- Les fonctions PgSQL acceptent et retournent désormais des objets PgSql\Lob au lieu de resources `pgsql large object`.

- Les fonctions PSpell acceptent et retournent désormais des objets PSpell\Dictionary au lieu de resources `pspell`.

- Les fonctions PSpell acceptent et retournent désormais des objets PSpell\Config au lieu de resources `pspell config`.

### MySQLi

mysqli_fetch_fields(), et mysqli_fetch_field_direct() retourneront désormais `0` pour la max_length. Cette information peut être calculée en itérant sur le jeu de résultats, et en prenant la longueur maximale. C'est ce que PHP faisait précédemment en interne.

L'option `MYSQLI_STMT_ATTR_UPDATE_MAX_LENGTH` n'a plus aucun effet.

L'option `MYSQLI_STORE_RESULT_COPY_DATA` n'a plus aucun effet. Passer une valeur au paramètre `mode` de mysqli::store_result() n'a plus aucun effet.

mysqli::connect() retourne maintenant `true` au lieu de `null` en cas de succès.

Le mode de gestion des erreurs par défaut a été changé de "silencieux" à "exceptions". Voir la page Mode de rapport MySQLi pour plus de détails sur ce que cela implique, et comment définir explicitement cet attribut. Pour restaurer le comportement précédent, utilisez : `mysqli_report(MYSQLI_REPORT_OFF);`

Les classes étendant mysqli_stmt::execute() doivent désormais spécifier le paramètre optionnel supplémentaire.

### MySQLnd

La directive INIT mysqlnd.fetch_data_copy a été enlèvée. Cela ne devrait pas entraîner de changements de comportement visibles pour l'utilisateur.

### OpenSSL

Les clés privées EC seront désormais exportées au format PKCS#8 plutôt que le format traditionnel, tout comme toutes les autres clés.

openssl_pkcs7_encrypt() et openssl_cms_encrypt() utiliseront désormais par défaut AES-128-CBC plutôt que RC2-40. Le chiffrement RC2-40 est considéré comme non sécurisé et n'est pas activé par défaut par OpenSSL 3.

### Les objets de données PHP

`PDO::ATTR_STRINGIFY_FETCHES` tranforme désormais les valeurs de type booléen en `"0"` ou `"1"`. Précédemment, les booléen n'étaient pas transformés en chaînes.

Appeller PDOStatement::bindColumn() avec `PDO::PARAM_LOB` liera désormais constamment un stream de résultat lorsqu'`PDO::ATTR_STRINGIFY_FETCHES` n'est pas activé. Précédemment, le résultat était soit un stream, soit une chaîne en fonction du pilote de base de données utilisé et du moment où la liaison est effectuée.

#### Driver MySQL

Les entiers et les flottants dans les ensembles de résultats seront désormais retournés en utilisant les types natifs PHP au lieu de chaîne de caractèress lors de l'utilisation des déclarations préparées émulées. Cela correspond au comportement des déclarations préparées natives. Le comportement précédent peut être restauré en activant l'option `PDO::ATTR_STRINGIFY_FETCHES`.

#### Driver SQLite

Les entiers et les flottants dans les ensembles de résultats seront désormais retournés en utilisant les types PHP. Le comportement précédent peut être restauré en activant l'option `PDO::ATTR_STRINGIFY_FETCHES`.

### Phar

Pour se conformer à l'interface ArrayAccess, Phar::offsetUnset() et PharData::offsetUnset() ne retournent plus un booléen.

### Standard

version_compare() n'accepte plus les abréviations d'opérateurs non documentées.

htmlspecialchars(), htmlentities(), htmlspecialchars_decode(), html_entity_decode(), et get_html_translation_table() utilisent désormais `ENT_QUOTES | ENT_SUBSTITUTE` plutôt que `ENT_COMPAT` par défaut. Cela signifie que `'` est échappé en `&#039;` alors qu'auparavant rien n'était fait. De plus, l'UTF-8 mal formé sera remplacé par un caractère de substitution Unicode, au lieu de résulter en une chaîne vide.

debug_zval_dump() affiche désormais le refcount des références avec leur refcount, au lieu de simplement préfixer `&` à la valeur. Cela modélise plus précisément la représentation de référence depuis PHP 7.0.

debug_zval_dump() affiche désormais `interned` au lieu d'un refcount factice pour les chaînes internées et les tableaux immuables.

### Librairie Standard de PHP (Standard PHP Library ou SPL)

SplFixedArray, sera désormais encodé en JSON comme un tableau.