Neu bei Ruby und ROR und ich liebe es jeden Tag. Hier ist meine Frage, da ich keine Ahnung habe, wie ich es googeln soll (und ich habe es versucht :)).
Wir haben Methode
def foo(first_name, last_name, age, sex, is_plumber)
# some code
# error happens here
logger.error "Method has failed, here are all method arguments #{SOMETHING}"
end
Also, was ich suche, um alle Argumente an die Methode zu übergeben, ohne jedes einzelne aufzulisten. Da dies Ruby ist, nehme ich an, dass es einen Weg gibt :) Wenn es Java wäre, würde ich sie einfach auflisten :)
Ausgabe wäre:
Method has failed, here are all method arguments {"Mario", "Super", 40, true, true}
ruby-on-rails
ruby
Haris Krajina
quelle
quelle
method(__method__).parameters.map { |_, v| [v, binding.local_variable_get(v)] }
Antworten:
In Ruby 1.9.2 und höher können Sie die
parameters
Methode für eine Methode verwenden, um die Liste der Parameter für diese Methode abzurufen. Dies gibt eine Liste von Paaren zurück, die den Namen des Parameters angeben und angeben, ob er erforderlich ist.z.B
Wenn Sie tun
dann
Sie können die spezielle Variable verwenden
__method__
, um den Namen der aktuellen Methode abzurufen. Innerhalb einer Methode können also die Namen ihrer Parameter über abgerufen werdenSie können dann den Namen und den Wert jedes Parameters mit anzeigen
Hinweis: Da diese Antwort ursprünglich geschrieben wurde,
eval
kann Ruby in aktuellen Versionen nicht mehr mit einem Symbol aufgerufen werden. Um dies zu beheben,to_s
wurde beim Erstellen der Liste der Parameternamen eine explizite hinzugefügt, d. H.parameters.map { |arg| arg[1].to_s }
quelle
Seit Ruby 2.1 können Sie binding.local_variable_get verwenden , um den Wert jeder lokalen Variablen einschließlich der Methodenparameter (Argumente) zu lesen. Dank dessen können Sie die akzeptierte Antwort verbessern , um dies zu vermeiden
böseeval.quelle
Hash[method(__method__).parameters.map.collect { |_, name| [name, binding.local_variable_get(name)] }]
Eine Möglichkeit, damit umzugehen, ist:
quelle
Dies ist eine interessante Frage. Vielleicht mit local_variables ? Aber es muss einen anderen Weg geben als die Verwendung von eval. Ich suche in Kernel doc
quelle
eval var.to_s
. Eine Einschränkung ist auch, dass lokale Variablen, die vor dem Ausführen dieser Schleife definiert wurden, zusätzlich zu den Methodenparametern enthalten sind.local_variables
, werden Methodenargumente + alle lokalen Variablen zurückgegeben. Dies kann zu Fehlern bei Ihrem Code führen.Dies kann hilfreich sein ...
quelle
callers_name
Implementierung könnten Sie auch__method__
die weitergebenbinding
.Sie können eine Konstante definieren wie:
Und verwenden Sie es in Ihrem Code wie:
quelle
Bevor ich weiter gehe, geben Sie zu viele Argumente an foo weiter. Es sieht so aus, als wären alle diese Argumente Attribute in einem Modell, richtig? Sie sollten das Objekt selbst wirklich übergeben. Ende der Rede.
Sie könnten ein "splat" -Argument verwenden. Es verschiebt alles in ein Array. Es würde so aussehen:
quelle
Wenn Sie die Methodensignatur ändern würden, können Sie Folgendes tun:
Oder:
In diesem Fall interpoliert
args
oderopts.values
wird ein Array, aber Sie können,join
wenn auf Komma. Prostquelle
Es scheint, als könnte das, was mit dieser Frage erreicht werden soll, mit einem Juwel geschehen, das ich gerade veröffentlicht habe: https://github.com/ericbeland/exception_details . Es werden lokale Variablen und Werte (und Instanzvariablen) aus geretteten Ausnahmen aufgelistet. Könnte einen Blick wert sein ...
quelle
better_errors
Juwel empfehlen .Wenn Sie Argumente als Hash benötigen und den Körper der Methode nicht mit einer schwierigen Extraktion von Parametern verschmutzen möchten, verwenden Sie Folgendes:
Fügen Sie diese Klasse einfach Ihrem Projekt hinzu:
quelle
Wenn sich die Funktion in einer Klasse befindet, können Sie Folgendes tun:
quelle