Meilleures pratiques: utilisation de @ throws en PHP-doc, et comment cela pourrait être géré

Disons que j'ai une classe avec une méthode comme ceci:

/*
 *
 * Loads the user from username.
 *
 * @param string $username The username
 *
 * @return UserInterface
 *
 * @throws userNotFoundException if the user is not found
 */
public function getUser($username)
{
    // someFunction return an UserInterface class if found, or null if not.
    $user = someFunction('SELECT ....', $username);
    if ($user === null) {
        throw new userNotFoundException();
    }

    return $user
}

Maintenant, disons que someFunction pourrait lancer un InvalidArgumentException / RuntimeException / PDOException pour des raisons XYZ. Que devrais-je faire? et quoi pas?

Numéro 1

Ajoutez toutes les exceptions possibles qui pourraient lancer someFunction dans PHP-docs.

/*
 *
 * Loads the user from username.
 *
 * @param string $username The username
 *
 * @return UserInterface
 *
 * @throws userNotFoundException if the user is not found
 * @throws InvalidArgumentException
 * @throws ...
 */

Numéro 2

Ajoutez un bloc try-catch pour vous assurer que la méthode doit lancer des exceptions uniquement documentées

/*
 *
 * Loads the user from username.
 *
 * @param string $username The username
 *
 * @return UserInterface
 *
 * @throws userNotFoundException if the user is not found
 * @throws RuntimeException 
 */
public function getUser($username)
{
    try {
        $user = someFunction('SELECT ....', $username);
    } catch (Exception $e) {
        throw new RuntimeException();
    }

    if ($user === null) {
        throw new userNotFoundException();
    }

    return $user
}

Numéro 3

Ne fais rien.

22
demandé sur Federkun 2013-03-23 17:50:08

3 réponses

Personnellement, je considérerais traiter @throws similaire aux exceptions vérifiées de Java

La façon dont cela fonctionne en Java est que fondamentalement les exceptions qui héritent de RuntimeException peuvent être levées et ne doivent pas être traitées. Tous les autres types d'exceptions doivent avoir un bloc try-catch pour les gérer. Ce code de gestion doit être dans l'appelant.

Fondamentalement en PHP un peu comme ceci:

Lorsqu'une méthode est un @throws annotation, vous ont ajouter du code pour gérer ses exception.

Toutes les exceptions qui ne sont pas mentionnées sont facultatives pour la gestion dans le code appelant.


Maintenant, je ne suis pas à 100% ce principe moi-même. Toute la chose des exceptions de gestion est en quelque sorte à la préférence du programmeur, mais ce ne sont que quelques réflexions sur la façon dont je pense qu'il pourrait être géré de manière raisonnable.

10
répondu Jani Hartikainen 2013-03-23 13:55:55

En ce qui concerne la documentation, si une fonction explicitement lève une exception, elle doit être incluse dans la documentation de la fonction. Ainsi, pour chaque instruction throw, Il devrait y avoir un @throws correspondant dans la documentation PHP.

en ce qui concerne la manipulation, s'il y a des opérations qui doivent être exécutées lorsque l'exception est levée, puis l'attraper. Sinon, laissez-le gonfler - à condition qu'il y ait une instruction catch qui va le gérer tard.

Mise à jour:

Quelques années plus tard, j'ai changé à l'opinion qu'on ne devrait laisser une exception "gonfler" non modifiée que lorsque l'exception est toujours pertinente au niveau d'abstraction du module. Des stratégies de capture et de relance devraient être utilisées pour rendre l'exception plus significative. Il devrait également rendre la gestion des erreurs plus sûre en évitant la divulgation inutile d'informations sur les modules sous-jacents à l'abstraction.

/**
 * @throws UserNotFoundException
 */
public function getUser($username)
{
    try {
        $user = someFunction('SELECT ....', $username);
    } catch (DatabaseException $dbe) {

        /* Re-throw since a database exception may no longer be
         * meaningful to the caller.
         */
        throw new UserNotFoundException();
    }

    return $user
}
8
répondu Czar Pino 2018-02-14 06:30:45

Du point de vue de la maintenance de la documentation, Je n'ajouterais que les lignes @throw pour les exceptions qui sont spécifiquement lancées sinon vous obtiendrez rapidement votre documentation à jour.

5
répondu acutesoftware 2013-03-23 13:56:04