Je pense qu'il est impossible de donner une réponse définitive ici, car des choix comme celui-ci sont une préférence personnelle.
Considérez que ce qui suit est mon approche, et je n'ai aucune présomption que c'est la bonne .
Ce que je peux dire avec certitude, c'est que vous devriez éviter votre troisième option:
Il suffit de retourner null / false
C'est mauvais sous différents aspects:
- retour type de cohérence
- rend les fonctions plus difficiles à tester unitairement
- forcer une vérification conditionnelle sur le type de retour (
if (! is_null($thing))...
) rendant le code plus difficile à lire
J'utilise plus que souvent la POO pour coder les plugins, et mes méthodes d'objet lèvent souvent des exceptions en cas de problème.
Ce faisant, je:
- accomplir la cohérence du type de retour
- rendre le code simple au test unitaire
- pas besoin de vérification conditionnelle sur le type retourné
Cependant, lancer des exceptions dans un plugin WordPress signifie que rien ne les rattrapera , ce qui se terminera par une erreur fatale qui n'est absolument pas souhaitable, en particulier en production.
Pour éviter ce problème, j'ai normalement une "routine principale" située dans le fichier plugin principal, que j'enveloppe dans un bloc try
/ catch
. Cela me donne la chance d'attraper l'exception en production et d'éviter l'erreur fatale.
Un exemple grossier d'une classe:
# myplugin/src/Foo.php
namespace MyPlugin;
class Foo {
/**
* @return bool
*/
public function doSomething() {
if ( ! get_option('my_plugin_everything_ok') ) {
throw new SomethingWentWrongException('Something went wrong.');
}
// stuff here...
return true;
}
}
et en l'utilisant à partir du fichier plugin principal:
# myplugin/main-plugin-file.php
namespace MyPlugin;
function initialize() {
try {
$foo = new Foo();
$foo->doSomething();
} catch(SomethingWentWrongException $e) {
// on debug is better to notice when bad things happen
if (defined('WP_DEBUG') && WP_DEBUG) {
throw $e;
}
// on production just fire an action, making exception accessible e.g. for logging
do_action('my_plugin_error_shit_happened', $e);
}
}
add_action('wp_loaded', 'MyPlugin\\initialize');
Bien sûr, dans le monde réel, vous pouvez lancer et attraper différents types d'exceptions et vous comporter différemment selon l'exception, mais cela devrait vous donner une direction.
Une autre option que j'utilise souvent (et que vous n'avez pas mentionnée) est de renvoyer des objets qui contiennent un indicateur pour vérifier si aucune erreur ne se produit, mais en gardant la cohérence du type de retour.
Voici un exemple grossier d'un objet comme celui-ci:
namespace MyPlugin;
class Options {
private $options = [];
private $ok = false;
public function __construct($key)
{
$options = is_string($key) ? get_option($key) : false;
if (is_array($options) && $options) {
$this->options = $options;
$this->ok = true;
}
}
public function isOk()
{
return $this->ok;
}
}
Maintenant, depuis n'importe quel endroit de votre plugin, vous pouvez faire:
/**
* @return MyPlugin\Options
*/
function my_plugin_get_options() {
return new MyPlugin\Options('my_plugin_options');
}
$options = my_plugin_get_options();
if ($options->isOk()) {
// do stuff
}
Notez comment my_plugin_get_options()
ci-dessus retourne toujours une instance de Options
classe, de cette façon, vous pouvez toujours transmettre la valeur de retour, et même l'injecter à d'autres objets qui utilisent le type-hint avec maintenant le souci que le type soit différent.
Si la fonction était retournée null
/ false
en cas d'erreur, avant de la faire circuler, vous aviez été forcé de vérifier si la valeur retournée était valide.
En même temps, vous avez clairement un moyen de comprendre si quelque chose ne va pas avec l'instance d'option.
C'est une bonne solution au cas où l'erreur est quelque chose qui peut être facilement récupérée, en utilisant les valeurs par défaut ou tout ce qui convient.