J'ai du code qui doit sauver plusieurs types d'exceptions dans ruby:
begin
a = rand
if a > 0.5
raise FooException
else
raise BarException
end
rescue FooException, BarException
puts "rescued!"
end
Ce que je voudrais faire, c'est en quelque sorte stocker la liste des types d'exceptions que je veux sauver quelque part et passer ces types à la clause de sauvetage:
EXCEPTIONS = [FooException, BarException]
puis:
rescue EXCEPTIONS
Est-ce même possible, et est-ce possible sans quelques appels vraiment hack-y eval
? Je n'ai pas bon espoir étant donné que je vois TypeError: class or module required for rescue clause
quand je tente ce qui précède.
Réponses:
Vous pouvez utiliser un tableau avec l'opérateur splat
*
.Si vous allez utiliser une constante pour le tableau comme ci-dessus (avec
EXCEPTIONS
), notez que vous ne pouvez pas la définir dans une définition, et aussi si vous la définissez dans une autre classe, vous devez y faire référence avec son espace de noms. En fait, ce n'est pas forcément une constante.Opérateur Splat
L'opérateur splat
*
"décompresse" un tableau dans sa position de sorte quesignifie la même chose que
Vous pouvez également l'utiliser dans un tableau littéral comme
qui est le même que
ou en position d'argument
ce qui signifie
[]
s'étend à la vacuité:Une différence entre ruby 1.8 et ruby 1.9 est avec
nil
.Soyez prudent avec les objets sur lesquels
to_a
est défini, commeto_a
cela sera appliqué dans de tels cas:Avec d'autres types d'objets, il revient tout seul.
la source
EXCEPTIONS
dans ce cas? Voudrais en savoir un peu plus.rescue InvalidRequestError, CardError => e
(voir mikeferrier.com/2012/05/19/… )rescue *EXCEPTIONS => e
oùEXCEPTIONS
est un tableau de noms de classe d'exception.Bien que la réponse donnée par @sawa soit techniquement correcte, je pense qu'elle abuse du mécanisme de gestion des exceptions de Ruby.
Comme le suggère le commentaire de Peter Ehrlich (en pointant vers un ancien article de blog de Mike Ferrier ), Ruby est déjà équipé d'un mécanisme de gestionnaire d'exceptions DRY:
En utilisant cette technique, nous pouvons accéder à l'objet d'exception, qui contient généralement des informations précieuses.
la source
Je viens de rencontrer ce problème et j'ai trouvé une solution alternative. Dans le cas où votre
FooException
etBarException
allez tous être des classes d'exceptions personnalisées et en particulier si elles sont toutes liées thématiquement, vous pouvez structurer votre hiérarchie d'héritage de telle sorte qu'elles hériteront toutes de la même classe parente, puis ne sauveront que la classe parente.Par exemple , j'avais trois exceptions:
FileNamesMissingError
,InputFileMissingError
etOutputDirectoryError
que je voulais sauver avec une déclaration. J'ai créé une autre classe d'exception appeléeFileLoadError
, puis j'ai configuré les trois exceptions ci-dessus pour en hériter. J'ai alors sauvé seulementFileLoadError
.Comme ça:
la source