Descubra como criar e converter Structs em Go para JSON ou XML. Aprenda a manipular dados facilmente com exemplos práticos.
Tempo de Leitura: 5 minutos
Olá. Dando continuidade ao artigo anterior, hoje irei abordar a criação de Structs em Go e como podemos, facilmente, converter seus dados para saídas em JSON ou XML.
Para aqueles que já vem da linguagem C já está acostumado com esse tipo de abordagem.
Definição de Struct:
Em Go, uma "struct" (abreviação de structure) é um tipo de dados composto que agrupa campos de dados com tipos diferentes sob um único nome. As structs são uma maneira de criar tipos de dados personalizados e mais complexos, organizando dados relacionados em uma única unidade. Uma struct em Go envolve usar a palavra-chave type seguida pelo nome da struct, uma lista de campos e seus tipos associados. Aqui está um exemplo simples:
package main import "fmt" // Definição de uma struct chamada "Pessoa" type Pessoa struct { Nome string Idade int Sexo string } func main() { // Criando uma instância da struct "Pessoa" pessoa1 := Pessoa{ Nome: "João", Idade: 25, Sexo: "Masculino", } // Acessando os campos da struct fmt.Println("Nome:", pessoa1.Nome) fmt.Println("Idade:", pessoa1.Idade) fmt.Println("Sexo:", pessoa1.Sexo) }
Ao executar o retorno será:
- Nome: João
- Idade: 25
- Sexo: Masculino
Fácil né?
Vamos fazer nesse exemplo retornar um JSON e após um XML, para isso precisamos definir algumas modificações na nossa estrutura.
Agoram, vamos nomear cada propriedade da estrutura a nomenclatura que ficará o JSON, ex.:
// Definição de uma struct chamada "Pessoa" type Pessoa struct { Nome string `json:"nome"` Idade int `json:"idade"` Sexo string `json:"sexo"` }
Isso é importante para que o programa entenda qual os elementos que compõem o JSON tanto na entrada quanto na saída dos dados.
Finalizando vamos usar a biblioteca JSON, nativa no Go, importando a biblioteca "encoding/json" e usar o método Marshal.
O código ficará assim:
package main import ( "encoding/json" "fmt" ) // Definição de uma struct chamada "Pessoa" type Pessoa struct { Nome string `json:"nome"` Idade int `json:"idade"` Sexo string `json:"sexo"` } func main() { // Criando uma instância da struct "Pessoa" pessoa1 := Pessoa{ Nome: "João", Idade: 25, Sexo: "Masculino", } // Criando o arquivo JSON a partir de pessoa1 jsonData, err := json.Marshal(&pessoa1) if err != nil { fmt.Println(err.Error()) } // Acessando JSON da struct fmt.Println(string(jsonData)) }
Após executar você terá o retorno:
{"nome":"João","idade":25,"sexo":"Masculino"}
Com poucas linhas de código conseguimos retornar um JSON com os dados passados para a nossa estrutura.
Agora digamos que precisamos que seja retornado um XML desses dados, a maneira é bem similar.
Mas para definir um retorno em XML utilizaremos a biblioteca "encoding/xml" e criar algumas alterações em nossa estrutura para o XML receber um atributo e que as suas tags fiquem corretas:
// Definição de uma struct chamada "Pessoa" type Pessoa struct { XMLName xml.Name `xml:"pessoa"` Tipo string `xml:"tipo,attr"` Nome string `xml:"nome"` Idade int `xml:"idade"` Sexo string `xml:"sexo"` }
Então o código ficará assim:
package main import ( "encoding/xml" "fmt" ) // Definição de uma struct chamada "Pessoa" type Pessoa struct { XMLName xml.Name `xml:"pessoa"` Tipo string `xml:"tipo,attr"` Nome string `xml:"nome"` Idade int `xml:"idade"` Sexo string `xml:"sexo"` } func main() { // Criando uma instância da struct "Pessoa" pessoa1 := Pessoa{ Tipo: "Pessoa1", Nome: "João", Idade: 25, Sexo: "Masculino", } // Criando o arquivo XML a partir de pessoa1 xmlData, err := xml.Marshal(&pessoa1) if err != nil { fmt.Println(err.Error()) } // Acessando XML da struct fmt.Println(string(xmlData)) }
Ao executar terá o seguinte retorno:
<pessoa tipo="Pessoa1">
<nome>João</nome><idade>25</idade><sexo>Masculino</sexo>
</pessoa>
A diferença é que foram criadas uma tag para a entidade pessoa e mais um atributo para informar a Pessoa1.
Agora vamos fazer o contrário.
Enviaremos um JSON e depois enviar um XML, quando enviados eles terão que alimentar a nossa estrutura e ela irá devolver os atributos.
Para isso, tanto o JSON quanto o XML irão usar o método Unmarshal das suas respectivas bibliotecas.
Exemplo com o XML:
package main import ( "encoding/xml" "fmt" ) // Definição de uma struct chamada "Pessoa" type Pessoa struct { XMLName xml.Name `xml:"pessoa"` Tipo string `xml:"tipo,attr"` Nome string `xml:"nome"` Idade int `xml:"idade"` Sexo string `xml:"sexo"` } func main() { // Criando uma variavel pessoa1 da Struct Pessoa var pessoa1 Pessoa //Passando o XML em uma variavel; xmlData := `<pessoa tipo="Pessoa1"><nome>João</nome><idade>25</idade><sexo>Masculino</sexo></pessoa>` //passando os dados do XML para a pessoa1 if err := xml.Unmarshal([]byte(xmlData), &pessoa1); err != nil { fmt.Println(err.Error()) } // Acessando os campos da struct fmt.Println("Nome:", pessoa1.Nome) fmt.Println("Idade:", pessoa1.Idade) fmt.Println("Sexo:", pessoa1.Sexo) }
Ao executar terá o seguinte retorno:
- Nome: João
- Idade: 25
- Sexo: Masculino
Com os dados vindo de um XML, aqui passei via string, mas poderia vir de um arquivo, alimentou a nossa estrutura e alimentou as suas propriedades.
O mesmo com JSON, só devemos fazer algumas mudanças de biblioteca e a chamada na struct Pessoa:
package main import ( "encoding/json" "fmt" ) // Definição de uma struct chamada "Pessoa" type Pessoa struct { Nome string `json:"nome"` Idade int `json:"idade"` Sexo string `json:"sexo"` } func main() { // Criando uma variavel pessoa1 da Struct Pessoa var pessoa1 Pessoa //Passando o JSON em uma variavel; jsonData := `{"nome":"João","idade":25,"sexo":"Masculino"}` //passando os dados do JSON para a pessoa1 if err := json.Unmarshal([]byte(jsonData), &pessoa1); err != nil { fmt.Println(err.Error()) } // Acessando os campos da struct fmt.Println("Nome:", pessoa1.Nome) fmt.Println("Idade:", pessoa1.Idade) fmt.Println("Sexo:", pessoa1.Sexo) }
Novamente passei direto pela propriedade string, mas poderá ser enviada de um arquivo também. E no final teremos o mesmo resultado:
- Nome: João
- Idade: 25
- Sexo: Masculino
Para finalizar esse artigo, agora teremos a seguinte situação. Vamos passar um JSON e retornar um XML e depois passar um XML e retornar um JSON. Isso é interessante para quem precisar fazer conversões entre esses dois tipos de arquivos.
JSON para XML:
package main import ( "encoding/json" "encoding/xml" "fmt" ) // Definição de uma struct chamada "Pessoa" type Pessoa struct { xml.Name `json:"-" xml:"pessoa"` Tipo string `json:"tipo" xml:"tipo,attr"` Nome string `json:"nome" xml:"nome"` Idade int `json:"idade" xml:"idade"` Sexo string `json:"sexo" xml:"sexo"` } func main() { // Criando uma variavel pessoa1 da Struct Pessoa var pessoa1 Pessoa //Passando o JSON em uma variavel; jsonData := `{"tipo":"Pessoa1","nome":"João","idade":25,"sexo":"Masculino"}` //passando os dados do JSON para a pessoa1 if err := json.Unmarshal([]byte(jsonData), &pessoa1); err != nil { fmt.Println(err.Error()) } // Criando o arquivo XML a partir de pessoa1 xmlData, err := xml.Marshal(&pessoa1) if err != nil { fmt.Println(err.Error()) } // Acessando XML da struct fmt.Println(string(xmlData)) }
Retorno:
<pessoa tipo="Pessoa1">
<nome>João</nome><idade>25</idade><sexo>Masculino</sexo>
</pessoa>
XML para JSON:
package main import ( "encoding/json" "encoding/xml" "fmt" ) // Definição de uma struct chamada "Pessoa" type Pessoa struct { xml.Name `json:"-" xml:"pessoa"` Tipo string `json:"tipo" xml:"tipo,attr"` Nome string `json:"nome" xml:"nome"` Idade int `json:"idade" xml:"idade"` Sexo string `json:"sexo" xml:"sexo"` } func main() { // Criando uma variavel pessoa1 da Struct Pessoa var pessoa1 Pessoa //Passando o XML em uma variavel; xmlData := `<pessoa tipo="Pessoa1"><nome>João</nome><idade>25</idade><sexo>Masculino</sexo></pessoa>` //passando os dados do XML para a pessoa1 if err := xml.Unmarshal([]byte(xmlData), &pessoa1); err != nil { fmt.Println(err.Error()) } // Criando o arquivo JSON a partir de pessoa1 jsonData, err := json.Marshal(&pessoa1) if err != nil { fmt.Println(err.Error()) } // Acessando JSON da struct fmt.Println(string(jsonData)) }
Retorno:
{"tipo":"Pessoa1","nome":"João","idade":25,"sexo":"Masculino"}
Esse foi um exemplo bem simples de como utilizar, manipular dados de JSON e XML e de conversão de dados. Existem várias opções de utilizar essa abordagem, mas tentei criar uma maneira mais fácil de como entender a trabalhar com esses arquivos.
Fico por aqui, agradeço quem leu até o final e seguiu os exemplos, aguardem para mais próximos artigos.