1
votes

Impossible de désérialiser JSON en C # en utilisant la même classe aux deux extrémités

Je cherche quelqu'un pour signaler l'erreur évidente ici.

Une application .NET Core en C # effectue un appel HTTP vers une autre application de ce type. Un certain traitement est effectué et une réponse est envoyée ainsi:

Response returned = new Response();
var response = await client.SendAsync(request);
                if (response.IsSuccessStatusCode)
                {
                    var json = await response.Content.ReadAsStringAsync();
                    returned = JsonConvert.DeserializeObject<Response>(json);
                }

Tout cela semble bon et responseMessage contient du JSON valide (selon un vérificateur JSON en ligne J'ai trouvé).

À l'autre extrémité, ceci est reçu ainsi:

 Response response = new Response(input)
        {
            stuff = processedStuff;
        };
        responseMessage = JsonConvert.SerializeObject(response);
        return new OkObjectResult(responseMessage);

Cela échoue avec une Erreur lors de la conversion de la valeur * la chaîne JSON * à "Réponse" à la ligne 1

Réponse est le même fichier de classe dans les deux applications. Quelle erreur jamais évidente et apparemment invisible suis-je en train de faire ici?


2 commentaires

À quoi ressemble json ?


Étroitement lié: L'analyseur JSON.NET semble sérialiser deux fois mes objets .


4 Réponses :


0
votes

vérifier si la chaîne retournée n'est pas encapsulée dans l'objet OkObjectResult .


0 commentaires

0
votes

Autant que je sache, vous n'avez pas besoin de la sérialisation et de la désérialisation, le framework s'occupe déjà de tout. Si vous en avez besoin, vous pouvez toujours désérialiser en un type anonyme ou le transtyper à partir d'un objet. https://www.newtonsoft.com/json/help/html/DeserializeAnonymousType. htm

Je vous aiderais également si vous pouviez partager la classe de réponse, car cela fait probablement partie du problème.


0 commentaires

2
votes

L'erreur invisible que vous faites est la double sérialisation du résultat. Le contrat de OkObjectResult est qu'il sérialisera automatiquement l'objet de résultat dans le type de contenu négocié (par exemple JSON ou XML) et retournera un statut OK . Vous sérialisez d'abord l'objet, puis passez la chaîne sérialisée à OkObjectResult afin qu'il finisse par être sérialisé deux fois.

var doubleSerializedJson = await response.Content.ReadAsStringAsync();
var json = JsonConvert.DeserializeObject<string>(doubleSerializedJson);
returned = JsonConvert.DeserializeObject<Response>(json);

Solutions possibles:

  1. Autoriser la sérialisation implicite à faire son travail (recommandé):

    responseMessage = JsonConvert.SerializeObject(response);   // serialize to JSON
    return new ContentResult()
    {
        Content = responseMessage,
        ContentType = "application/json",
        StatusCode = 200
    };
    
  2. Utilisez un ContentResult à la place (idéal si vous avez besoin d'une gestion de sérialisation spéciale):

    return new OkObjectResult(response);   // implicit serialization of response object
    
  3. Désérialiser deux fois du côté récepteur (à utiliser en dernier recours, c'est-à-dire que vous ne contrôlez pas le serveur):

    responseMessage = JsonConvert.SerializeObject(response);   // serialize to JSON
    return new OkObjectResult(responseMessage);                // implicit serialization here
    


0 commentaires

0
votes

En tant que personne assez âgée pour me souvenir du début des Simpsons, je ne peux répondre que de manière traditionnelle:

L'utilisation de la sérialisation implicite telle que décrite par le répondant kind ci-dessus a résolu le problème.


0 commentaires