Convierta objetos de cualquier tipo a JObject con Json.NET

89

A menudo necesito ampliar mi modelo de dominio con información adicional antes de devolverlo al cliente con WebAPI. Para evitar la creación de ViewModel, pensé que podría devolver JObject con propiedades adicionales. Sin embargo, no pude encontrar una forma directa de convertir un objeto de cualquier tipo a JObject con una sola llamada a la biblioteca Newtonsoft JSON. Se me ocurrió algo como esto:

  1. primer SerializeObject
  2. luego Parse
  3. y extender JObject

P.ej.:

var cycles = cycleSource.AllCycles();

var settings = new JsonSerializerSettings
{
    ContractResolver = new CamelCasePropertyNamesContractResolver()
};

var vm = new JArray();

foreach (var cycle in cycles)
{
    var cycleJson = JObject.Parse(JsonConvert.SerializeObject(cycle, settings));
    // extend cycleJson ......
    vm.Add(cycleJson);
}

return vm;

Yo de esta manera correcta?

libélula
fuente
17
JObject.FromObject(your_domain_object)es lo que estas buscando. Vea la respuesta de @ LB.
Brian Rogers

Respuestas:

123

JObject implementa IDictionary, por lo que puede usarlo de esa manera. Por ex,

var cycleJson  = JObject.Parse(@"{""name"":""john""}");

//add surname
cycleJson["surname"] = "doe";

//add a complex object
cycleJson["complexObj"] = JObject.FromObject(new { id = 1, name = "test" });

Entonces el json final será

{
  "name": "john",
  "surname": "doe",
  "complexObj": {
    "id": 1,
    "name": "test"
  }
}

También puede utilizar dynamicpalabras clave

dynamic cycleJson  = JObject.Parse(@"{""name"":""john""}");
cycleJson.surname = "doe";
cycleJson.complexObj = JObject.FromObject(new { id = 1, name = "test" });
LB
fuente
Gracias por tu respuesta Pero obtengo el siguiente json mientras evalúo cycleJson, con llaves adicionales. ¿Cómo puedo quitar esos tirantes adicionales? {{"name": "john", "surname": "doe", "complexObj": {"id": 1, "name": "test"}}}
remya thekkuvettil
@remyathekkuvettil no es un json válido. Necesita algunas manipulaciones de cadenas ad-hoc.
LB
28

Si tiene un objeto y desea convertirse en JObject, puede usar:

JObject o = (JObject)JToken.FromObject(miObjetoEspecial);

Me gusta esto :

Pocion pocionDeVida = new Pocion{
tipo = "vida",
duracion = 32,
};

JObject o = (JObject)JToken.FromObject(pocionDeVida);
Console.WriteLine(o.ToString());
// {"tipo": "vida", "duracion": 32,}
Condemateguadua
fuente
9
¿Por qué no JObject.FromObject () en lugar de (JObject) JToken.FromObject () directamente?
tomexou
me dio unaSystem.InvalidCastException
superninja
1

Esto funcionará:

var cycles = cycleSource.AllCycles();

var settings = new JsonSerializerSettings
{
    ContractResolver = new CamelCasePropertyNamesContractResolver()
};

var vm = new JArray();

foreach (var cycle in cycles)
{
    var cycleJson = JObject.FromObject(cycle);
    // extend cycleJson ......
    vm.Add(cycleJson);
}

return vm;
TheEmirOfGroofunkistan
fuente