J'ai une corde brute. Je veux juste valider si la chaîne est JSON valide ou non. J'utilise JSON.NET.
J'ai une corde brute. Je veux juste valider si la chaîne est JSON valide ou non. J'utilise JSON.NET.
Réponses:
Par code:
Votre meilleur pari est d'utiliser parse dans une try-catch
exception et catch en cas d'échec de l'analyse. (Je ne connais aucune TryParse
méthode) .
(Utilisation de JSON.Net)
Le moyen le plus simple serait d'utiliser Parse
la chaîne JToken.Parse
, et également de vérifier si la chaîne commence par {
ou [
et se termine par }
ou ]
respectivement (ajouté à partir de cette réponse ) :
private static bool IsValidJson(string strInput)
{
if (string.IsNullOrWhiteSpace(stringValue)) { return false;}
strInput = strInput.Trim();
if ((strInput.StartsWith("{") && strInput.EndsWith("}")) || //For object
(strInput.StartsWith("[") && strInput.EndsWith("]"))) //For array
{
try
{
var obj = JToken.Parse(strInput);
return true;
}
catch (JsonReaderException jex)
{
//Exception in parsing json
Console.WriteLine(jex.Message);
return false;
}
catch (Exception ex) //some other exception
{
Console.WriteLine(ex.ToString());
return false;
}
}
else
{
return false;
}
}
La raison pour laquelle ajouter des vérifications pour {
ou [
etc était basée sur le fait que JToken.Parse
l'analyse des valeurs telles que "1234"
ou "'a string'"
comme un jeton valide. L'autre option pourrait être d'utiliser à la fois JObject.Parse
et JArray.Parse
dans l' analyse syntaxique et voir si quelqu'un d'entre eux réussit, mais je crois que la vérification des {}
et []
devrait être plus facile. (Merci @RhinoDevel de l'avoir signalé )
Sans JSON.Net
Vous pouvez utiliser l' espace de noms .Net Framework 4.5 System.Json , comme:
string jsonString = "someString";
try
{
var tmpObj = JsonValue.Parse(jsonString);
}
catch (FormatException fex)
{
//Invalid json format
Console.WriteLine(fex);
}
catch (Exception ex) //some other exception
{
Console.WriteLine(ex.ToString());
}
(Mais, vous devez installer System.Json
via le gestionnaire de packages Nuget en utilisant la commande: PM> Install-Package System.Json -Version 4.0.20126.16343
sur la console du gestionnaire de packages) (pris à partir d' ici )
Manière non-code:
Habituellement, quand il y a une petite chaîne json et que vous essayez de trouver une erreur dans la chaîne json, je préfère personnellement utiliser les outils en ligne disponibles. Ce que je fais habituellement, c'est:
JToken.Parse("1234")
! Cela peut être une bonne idée de vérifier d'abord si la chaîne commence par [
ou {
. Une autre alternative est l'utilisation JObject.Parse()
et JArray.Parse()
.
JToken.Parse("{a:1}")
ne lève pas d' exception même s'il s'agit d'un JSON invalide - a
doit être cité ( stackoverflow.com/q/949449/3116322 )
Utilisez la JContainer.Parse(str)
méthode pour vérifier si le str est un Json valide. Si cela lève une exception, ce n'est pas un Json valide.
JObject.Parse
- Peut être utilisé pour vérifier si la chaîne est un objet Json valide
JArray.Parse
- Peut être utilisé pour vérifier si la chaîne est un tableau Json valide
JContainer.Parse
- Peut être utilisé pour vérifier à la fois l'objet Json et le tableau
JContainer.Parse("1234");
.
En vous basant sur la réponse d'Habib, vous pouvez écrire une méthode d'extension:
public static bool ValidateJSON(this string s)
{
try
{
JToken.Parse(s);
return true;
}
catch (JsonReaderException ex)
{
Trace.WriteLine(ex);
return false;
}
}
Qui peut ensuite être utilisé comme ceci:
if(stringObject.ValidateJSON())
{
// Valid JSON!
}
JToken.Parse(s);
retourne true
même siJToken.Parse(123);
true
pour cet invalide JSON
:{A:{"B": 1}}
Juste pour ajouter quelque chose à la réponse de @ Habib, vous pouvez également vérifier si le JSON donné est d'un type valide:
public static bool IsValidJson<T>(this string strInput)
{
strInput = strInput.Trim();
if ((strInput.StartsWith("{") && strInput.EndsWith("}")) || //For object
(strInput.StartsWith("[") && strInput.EndsWith("]"))) //For array
{
try
{
var obj = JsonConvert.DeserializeObject<T>(strInput);
return true;
}
catch // not valid
{
return false;
}
}
else
{
return false;
}
}
J'ai trouvé que JToken.Parse analyse de manière incorrecte le JSON invalide tel que le suivant:
{
"Id" : ,
"Status" : 2
}
Collez la chaîne JSON dans http://jsonlint.com/ - elle n'est pas valide.
J'utilise donc:
public static bool IsValidJson(this string input)
{
input = input.Trim();
if ((input.StartsWith("{") && input.EndsWith("}")) || //For object
(input.StartsWith("[") && input.EndsWith("]"))) //For array
{
try
{
//parse the input into a JObject
var jObject = JObject.Parse(input);
foreach(var jo in jObject)
{
string name = jo.Key;
JToken value = jo.Value;
//if the element has a missing value, it will be Undefined - this is invalid
if (value.Type == JTokenType.Undefined)
{
return false;
}
}
}
catch (JsonReaderException jex)
{
//Exception in parsing json
Console.WriteLine(jex.Message);
return false;
}
catch (Exception ex) //some other exception
{
Console.WriteLine(ex.ToString());
return false;
}
}
else
{
return false;
}
return true;
}
{ name : "l am invalid JSON" }
⚠️ Option alternative n'utilisant pas JSON.Net ⚠️
Pour .Net Core / .Net 5 ( en préversion au moment de la rédaction de cet article ), on peut également utiliser l' System.Text.Json
espace de noms et analyser en utilisant le JsonDocument
. L'exemple est une méthode d'extension basée sur les opérations d'espace de noms:
public static bool IsJsonValid(this string txt)
{
try { return JsonDocument.Parse(txt) != null; } catch {}
return false;
}
Concernant la réponse de Tom Beech; J'ai plutôt proposé ce qui suit:
public bool ValidateJSON(string s)
{
try
{
JToken.Parse(s);
return true;
}
catch (JsonReaderException ex)
{
Trace.WriteLine(ex);
return false;
}
}
Avec une utilisation des éléments suivants:
if (ValidateJSON(strMsg))
{
var newGroup = DeserializeGroup(strMsg);
}
string
, mais cette réponse devrait vraiment soit a) ne pas être ici ou b) dire "j'ai utilisé la réponse de Tom Beech " sans le this
, c'est-à-dire sans en faire un élément d'extension) - tant cette réponse que celle référencée ont une brièveté et des faiblesses identiques. Si vous devez faire valoir ce point, mettez simplement un commentaire sur l'autre réponse.
JToken.Type
est disponible après une analyse réussie. Cela peut être utilisé pour éliminer une partie du préambule dans les réponses ci-dessus et fournir un aperçu pour un contrôle plus précis du résultat. Entrée totalement invalide (par exemple, "{----}".IsValidJson();
lancera toujours une exception).
public static bool IsValidJson(this string src)
{
try
{
var asToken = JToken.Parse(src);
return asToken.Type == JTokenType.Object || asToken.Type == JTokenType.Array;
}
catch (Exception) // Typically a JsonReaderException exception if you want to specify.
{
return false;
}
}
Référence Json.Net pour JToken.Type
: https://www.newtonsoft.com/json/help/html/T_Newtonsoft_Json_Linq_JTokenType.htm
Voici une méthode d'extension TryParse basée sur la réponse de Habib:
public static bool TryParse(this string strInput, out JToken output)
{
if (String.IsNullOrWhiteSpace(strInput))
{
output = null;
return false;
}
strInput = strInput.Trim();
if ((strInput.StartsWith("{") && strInput.EndsWith("}")) || //For object
(strInput.StartsWith("[") && strInput.EndsWith("]"))) //For array
{
try
{
output = JToken.Parse(strInput);
return true;
}
catch (JsonReaderException jex)
{
//Exception in parsing json
//optional: LogError(jex);
output = null;
return false;
}
catch (Exception ex) //some other exception
{
//optional: LogError(ex);
output = null;
return false;
}
}
else
{
output = null;
return false;
}
}
Usage:
JToken jToken;
if (strJson.TryParse(out jToken))
{
// work with jToken
}
else
{
// not valid json
}
J'utilise celui-ci:
internal static bool IsValidJson(string data)
{
data = data.Trim();
try
{
if (data.StartsWith("{") && data.EndsWith("}"))
{
JToken.Parse(data);
}
else if (data.StartsWith("[") && data.EndsWith("]"))
{
JArray.Parse(data);
}
else
{
return false;
}
return true;
}
catch
{
return false;
}
}