Criação de JSON em tempo real com JObject


97

Para alguns de meus testes de unidade, desejo a capacidade de construir valores JSON específicos (álbuns de registro neste caso) que podem ser usados ​​como entrada para o sistema em teste.

Eu tenho o seguinte código:

var jsonObject = new JObject();
jsonObject.Add("Date", DateTime.Now);
jsonObject.Add("Album", "Me Against The World");
jsonObject.Add("Year", 1995);
jsonObject.Add("Artist", "2Pac");

Isso funciona bem, mas eu nunca gostei muito da sintaxe da "string mágica" e preferiria algo mais próximo da sintaxe expando-property em JavaScript como esta:

jsonObject.Date = DateTime.Now;
jsonObject.Album = "Me Against The World";
jsonObject.Year = 1995;
jsonObject.Artist = "2Pac";

5
Você deve receber o dobro de pontos pela seleção de artista / álbum!
spottedmahn

Respostas:


145

Bem, que tal:

dynamic jsonObject = new JObject();
jsonObject.Date = DateTime.Now;
jsonObject.Album = "Me Against the world";
jsonObject.Year = 1995;
jsonObject.Artist = "2Pac";

3
Perfeito! Exatamente o que eu estava procurando, esqueci completamente dynamic.
Karl Anderson

Recebo 'Newtonsoft.Json.Linq.JObject' não contém uma definição para o erro 'Data' quando tento executar seu código. A forma como eu poderia fazer isso funcionar é mudar a primeira linha para: dynamic jsonExpando = new ExpandoObject();e adicionar uma linha após o seu código:JObject jsonObject = JObject.FromObject(jsonExpando);
BornToCode

3
Se você deseja adicionar um List <> ao seu objeto Json, você precisa fazer algo como jsonObject.list = JToken.FromObject(mylist);.
Steve Smith

Você pode usar a combinação de índice e notação de propriedade caso acerte o nome do campo com um caractere especial, por exemplo, Create-Year ". Você não será capaz de escrever jsonObject.Create-Year = 1995, mas pode usar o seguinte. JsonObject [" Create-Year "] = 1995; jsonObject.Artist =" 2Pac ";
PAS

72

Você pode usar a JObject.Parseoperação e simplesmente fornecer texto JSON delimitado por aspas simples.

JObject  o = JObject.Parse(@"{
  'CPU': 'Intel',
  'Drives': [
    'DVD read/writer',
    '500 gigabyte hard drive'
  ]
}");

Isso tem a vantagem de ser realmente JSON e, portanto, é lido como JSON.

Ou você tem dados de teste que são dinâmicos, você pode usar a JObject.FromObjectoperação e fornecer um objeto embutido.

JObject o = JObject.FromObject(new
{
    channel = new
    {
        title = "James Newton-King",
        link = "http://james.newtonking.com",
        description = "James Newton-King's blog.",
        item =
            from p in posts
            orderby p.Title
            select new
            {
                title = p.Title,
                description = p.Description,
                link = p.Link,
                category = p.Categories
            }
    }
});

Documentação Json.net para serialização


10
JObject.FromObject deve ser marcado como a resposta correta. Obrigado.
Thomas

1
Acho que JObject.FromObjectnão funcionará se houver propriedades com caracteres especiais como -.
Jatin Sanghvi

40

Nem dynamic, nem a JObject.FromObjectsolução funciona quando você tem propriedades JSON que não são nomes de variáveis ​​C # válidos, por exemplo "@odata.etag". Eu prefiro a sintaxe do inicializador do indexador em meus casos de teste:

JObject jsonObject = new JObject
{
    ["Date"] = DateTime.Now,
    ["Album"] = "Me Against The World",
    ["Year"] = 1995,
    ["Artist"] = "2Pac"
};

Ter um conjunto separado de símbolos delimitadores para inicializar JObjecte adicionar propriedades torna os inicializadores de índice mais legíveis do que os inicializadores de objeto clássicos, especialmente no caso de objetos JSON compostos conforme abaixo:

JObject jsonObject = new JObject
{
    ["Date"] = DateTime.Now,
    ["Album"] = "Me Against The World",
    ["Year"] = 1995,
    ["Artist"] = new JObject
    {
        ["Name"] = "2Pac",
        ["Age"] = 28
    }
};

Com a sintaxe do inicializador de objetos, a inicialização acima seria:

JObject jsonObject = new JObject
{
    { "Date", DateTime.Now },
    { "Album", "Me Against The World" },
    { "Year", 1995 }, 
    { "Artist", new JObject
        {
            { "Name", "2Pac" },
            { "Age", 28 }
        }
    }
};

2
A última é definitivamente a melhor sintaxe para escrever json em c #.
Anthony Brenelière 01 de

consulte stackoverflow.com/questions/51015036/… para saber como fazer isso também com coleções
kofifus

30

Existem alguns ambientes onde você não pode usar dinâmico (por exemplo, Xamarin.iOS) ou casos em que você apenas procura uma alternativa para as respostas válidas anteriores.

Nestes casos, você pode fazer:

using Newtonsoft.Json.Linq;

JObject jsonObject =
     new JObject(
             new JProperty("Date", DateTime.Now),
             new JProperty("Album", "Me Against The World"),
             new JProperty("Year", "James 2Pac-King's blog."),
             new JProperty("Artist", "2Pac")
         )

Mais documentação aqui: http://www.newtonsoft.com/json/help/html/CreatingLINQtoJSON.htm


2

Maneira simples de criar newtonsoft JObject de Propriedades.

Este é um exemplo de propriedades do usuário

public class User
{
    public string Name;
    public string MobileNo;
    public string Address;
}

e eu quero esta propriedade em Newtonsoft JObject é:

JObject obj = JObject.FromObject(new User()
{
    Name = "Manjunath",
    MobileNo = "9876543210",
    Address = "Mumbai, Maharashtra, India",
});

A saída será assim:

{"Name":"Manjunath","MobileNo":"9876543210","Address":"Mumbai, Maharashtra, India"}

2

Mais cedo ou mais tarde você terá um imóvel com caráter especial. Você pode usar índice ou combinação de índice e propriedade.

dynamic jsonObject = new JObject();
jsonObject["Create-Date"] = DateTime.Now; //<-Index use
jsonObject.Album = "Me Against the world"; //<- Property use
jsonObject["Create-Year"] = 1995; //<-Index use
jsonObject.Artist = "2Pac"; //<-Property use

Como isso responde à pergunta?
Enigmativity

@Enigmativity, o que quero dizer é que você pode usar a notação de índice e a notação de propriedade juntas. ou seja, obj [x] = x1; obj.y = y1 pode ser usado no mesmo código. A combinação de palavra-chave dinâmica e notação de índice responde às perguntas. Nenhuma outra resposta menciona isso. Possivelmente, isso deve ser um comentário do que uma resposta.
PAS

Só acho que a questão é sobre não usar cordas mágicas, mas essa resposta está dando a ele isso.
Enigmativity

@Enigmativity, palavra-chave dinâmica apenas engana o compilador. Portanto, não é diferente de uma string arbitrária. o objeto do tipo dinâmico não é fortemente tipado. É apenas um açúcar sintático. Se o objeto subjacente não tiver propriedade, o tempo de execução falhará. mas você simplesmente não pode usar propriedades se o nome da propriedade contiver caracteres especiais, por exemplo, 99BottlesOfBeer, namespace, It's-All-Over. Então, nesses casos, podemos usar propriedades indexadas. Outra resposta faz você pensar que é uma ou outra, mas você pode misturar e combinar propriedade e índice.
PAS de

-3

Você pode usar a biblioteca Newtonsoft e usá-la da seguinte maneira

using Newtonsoft.Json;



public class jb
{
     public DateTime Date { set; get; }
     public string Artist { set; get; }
     public int Year { set; get; }
     public string album { set; get; }

}
var jsonObject = new jb();

jsonObject.Date = DateTime.Now;
jsonObject.Album = "Me Against The World";
jsonObject.Year = 1995;
jsonObject.Artist = "2Pac";


System.Web.Script.Serialization.JavaScriptSerializer oSerializer =
         new System.Web.Script.Serialization.JavaScriptSerializer();

string sJSON = oSerializer.Serialize(jsonObject );

5
você não está realmente usando a biblioteca newtonsoft aqui
Mickey Perlstein
Ao utilizar nosso site, você reconhece que leu e compreendeu nossa Política de Cookies e nossa Política de Privacidade.
Licensed under cc by-sa 3.0 with attribution required.