Gestion des erreurs PHP: die () Vs trigger_error () Vs throw Exception

119

En ce qui concerne la gestion des erreurs en PHP - Pour autant que je sache, il existe 3 styles:

  1. die()ou exit()style:

    $con = mysql_connect("localhost","root","password");
    
    if (!$con) {
     die('Could not connect: ' . mysql_error());
    }
  2. throw Exception style:

     if (!function_exists('curl_init')) {
    
          throw new Exception('need the CURL PHP extension. 
                               Recomplie PHP with curl');
        }
  3. trigger_error() style:

    if(!is_array($config) && isset($config)) {
            trigger_error('Error: config is not an array or is not set', E_USER_ERROR);
        }

Maintenant, dans le manuel PHP, les trois méthodes sont utilisées.

  • Ce que je veux savoir, c'est quel style devrais-je préférer et pourquoi?

  • Ces 3 gouttes se remplacent-elles les unes les autres et peuvent donc être utilisées de manière interchangeable?

Légèrement OT: Est-ce juste moi ou tout le monde pense que les options de gestion des erreurs PHP sont trop nombreuses dans la mesure où cela déroute les développeurs PHP?

CuriousMind
la source
4
Ce ne sont pas des «styles». Ce sont des caractéristiques linguistiques différentes. À des fins différentes.
mario
11
@mario: quels sont les différents objectifs en retrait ? Please enlighten me :)
CuriousMind
Vous posez la question d'une excellente manière. merci d'avoir demandé
Accountant م

Réponses:

86

Le premier ne doit jamais être utilisé dans le code de production, car il transporte des informations non pertinentes pour les utilisateurs finaux (un utilisateur ne peut rien faire à propos de "Impossible de se connecter à la base de données" ).

Vous lancez des exceptions si vous savez qu'à un certain point de code critique, votre application peut échouer et que vous voulez que votre code récupère sur plusieurs niveaux d'appel.

trigger_error()vous permet de générer des rapports d'erreurs précis (en utilisant différents niveaux de messages d'erreur) et vous pouvez masquer ces erreurs aux utilisateurs finaux (à l'aide de set_error_handler()), tout en les affichant pendant les tests.

trigger_error()Peut également produire des messages non fatals importants pendant le développement qui peuvent être supprimés dans le code de production à l'aide d'un gestionnaire d'erreurs personnalisé. Vous pouvez également produire des erreurs fatales ( E_USER_ERROR) mais celles-ci ne sont pas récupérables. Si vous en déclenchez un, l'exécution du programme s'arrête à ce stade. C'est pourquoi, pour les erreurs fatales, des exceptions doivent être utilisées. De cette façon, vous aurez plus de contrôle sur le déroulement de votre programme:

// Example (pseudo-code for db queries):

$db->query('START TRANSACTION');

try {
    while ($row = gather_data()) {
       $db->query('INSERT INTO `table` (`foo`,`bar`) VALUES(?,?)', ...);
    }
    $db->query('COMMIT');
} catch(Exception $e) {
    $db->query('ROLLBACK');
}

Ici, si gather_data()juste croassaient brut ( en utilisant E_USER_ERRORou die()) il y a une chance, précédentes INSERTdéclarations auraient fait dans votre base de données, même si pas désiré et vous auriez aucun contrôle sur ce qui est à arriver.

Linus Kleen
la source
2
si hors de trigger_error()& lançant des exceptions: lequel dois-je utiliser et quand?
CuriousMind
@Gaurish Voir l'exemple ajouté à ce sujet.
Linus Kleen
2
Après avoir lu votre exemple, je pense que maintenant je comprends mieux le but de l'exception de jet. Merci :)
CuriousMind
1
@Pacerier Cela dépend de la configuration du serveur, en fait. Un système peut être configuré pour effectuer une validation automatique par défaut, d'où l'explicite ROLLBACK. Cet exemple de pseudo-code couvre les deux cas: les serveurs qui ne sont pas configurés pour l'autocommit (l' COMMITinstruction est obligatoire) et ceux qui le font.
Linus Kleen
1
@LinusKleen, l'autocommit n'est-il pas désactivé une fois que nous avons exécuté la ligne query('START TRANSACTION');?
Pacerier
10

J'utilise généralement la première méthode pour un débogage simple dans le code de développement. Il n'est pas recommandé pour la production. Le meilleur moyen est de lancer une exception, que vous pouvez intercepter dans d'autres parties du programme et effectuer une gestion des erreurs.

Les trois styles ne sont pas des substituts instantanés les uns pour les autres. Le premier n'est pas du tout une erreur, mais juste un moyen d'arrêter le script et de générer des informations de débogage que vous pourrez analyser manuellement. Le second n'est pas une erreur en soi, mais sera converti en une erreur si vous ne l'attrapez pas. Le dernier déclenche une véritable erreur dans le moteur PHP qui sera gérée en fonction de la configuration de votre environnement PHP (dans certains cas montré à l'utilisateur, dans d'autres cas simplement connecté à un fichier ou pas du tout sauvegardé).

Emil Vikström
la source
1
Que se passe-t-il lorsqu'une exception est levée mais pas interceptée? cela causera une erreur fatale, je suppose. Et avec la trigger_error()même chose se produit. alors quelle est la différence?
CuriousMind
4
La différence est que vous pouvez intercepter l'exception et la gérer comme vous le souhaitez.
Emil Vikström