Un texte JSON doit au moins contenir deux octets
j'ai reçu cette erreur, et je ne pouvais trouver aucune réponse raisonnable à cette question, donc j'ai pensé que je voudrais écrire un résumé du problème.
si vous exécutez cet extrait dans irb:
JSON.parse( nil )
vous verrez l'erreur suivante:
TypeError: can't convert nil into String
Je m'attendais en quelque sorte à ce que la fonction renvoie nil
, et pas un TypeError
. Si vous convertissez toutes les entrées en utilisant to_s
, alors vous verrez l'erreur d'octet:
JSON::ParserError: A JSON text must at least contain two octets!
c'est très bien. Si vous ne savez pas ce qu'est un octet, lisez ce post pour un résumé et une solution: Qu'est-ce qu'un JSON octet et pourquoi deux sont-ils nécessaires?
Solution
la variable que vous passez est une chaîne vide. Ne tentez pas d'utiliser une chaîne vide dans la méthode JSON.parse
.
Question
donc, maintenant que je connais la cause de l'erreur, quel modèle devrais-je utiliser pour gérer cela? Je suis un peu dégouté de Monkey patch la bibliothèque JSON pour autoriser les valeurs nil
. Toute suggestion serait grandement appréciée.
4 réponses
parsed = json && json.length >= 2 ? JSON.parse(json) : nil
mais en réalité la bibliothèque devrait être capable de gérer cette affaire et de retourner zéro. Les navigateurs Web avec prise en charge JSON intégrée semblent fonctionner exactement comme vous l'attendez après tout.
ou pour le faire avec un seul mini patch légèrement intrusif:
module JSON
def self.parse_nil(json)
JSON.parse(json) if json && json.length >= 2
end
end
parsed = JSON.parse_nil(json)
selon json.org
JSON est construit sur deux structures:
-
Une collection de paires nom/valeur. Dans plusieurs langues, Ceci est réalisé comme un objet, un enregistrement, une structure, un dictionnaire, une table de hachage, une liste de touches, ou un tableau associatif.
-
Une liste ordonnée de valeurs. Dans la plupart des langues, ceci est réalisé comme un tableau, vecteur, une liste ou une séquence.
ainsi, au moins deux octets(8 bits) requis au niveau supérieur seraient {}
ou []
IMO, la meilleure solution serait de s'assurer que l'argument à JSON.parse
est soit un objet strigifié ou un tableau strigifié. :- )
data.presence && JSON.parse(data)
JSON.parse(data.presence || '{}')
hash = JSON.parse(json) rescue {}
array = JSON.parse(json) rescue []
string = JSON.parse(json) rescue ''