Ruby on Rails fügt die "as_json"-Methode zu vielen gängigen Klassen hinzu, die ActiveRecord-Objekte in Hash-Objekte umwandelt, die dann an einen JSON-Serializer gesendet werden können. Kürzlich bin ich in meinem Code auf einen Fehler gestoßen, der mit dieser Methode und ihrer Behandlung von booleschen Werten zusammenhängt.
Ich kann den Fehler sehr knapp zusammenfassen:
{"foo" => true}.as_json
Ich würde erwarten, dass diese Methode einen identischen Hash zurückgibt. Stattdessen gibt sie
{"foo" => "true"}
Dies scheint Absicht zu sein, wie aus Zeile 157 in encoding.rb hervorgeht
AS_JSON = ActiveSupport::JSON::Variable.new('true').freeze
Darf ich fragen, warum Rails den String-Wert "true" zurückgibt, anstatt ihn als wahren booleschen Wert zu behalten?
Mein Fehler ist der folgende: Ich speichere JSON-serialisierte Objekte in einem Cache. Wenn ich sie aus dem Cache ziehe, lasse ich sie als Hashes, um eine unnötige Deserialisierung des Objekts zu vermeiden. Wenn ich es nicht im Cache finde, ziehe ich das Objekt aus der Datenbank und rufe as_json auf. Ich erwarte, dass das, was ich aus dem Cache ziehe, und das, was ich von as_json zurückbekomme, identisch sind. Das ist nicht der Fall, denn was aus dem Cache kommt, ist {"foo" => true} und was von as_json zurückkommt, ist {"foo" => "true"}.