Записать Struct в файл Json с помощью полей структуры (не ключей json)
Как я могу прочитать json файл в struct, а затем Marshal обратно в строку json с полями Struct как ключи (а не оригинальные json-ключи)?
(см. ниже Desired Output to Json File
...)
код:
package main
import (
"encoding/json"
"fmt"
"io/ioutil"
)
type Rankings struct {
Keyword string `json:"keyword"`
GetCount uint32 `json:"get_count"`
Engine string `json:"engine"`
Locale string `json:"locale"`
Mobile bool `json:"mobile"`
}
func main() {
var jsonBlob = []byte(`
{"keyword":"hipaa compliance form", "get_count":157, "engine":"google", "locale":"en-us", "mobile":false}
`)
rankings := Rankings{}
err := json.Unmarshal(jsonBlob, &rankings)
if err != nil {
// nozzle.printError("opening config file", err.Error())
}
rankingsJson, _ := json.Marshal(rankings)
err = ioutil.WriteFile("output.json", rankingsJson, 0644)
fmt.Printf("%+v", rankings)
}
Вывод на экран:
{Keyword:hipaa compliance form GetCount:157 Engine:google Locale:en-us Mobile:false}
Выход в файл Json:
{"keyword":"hipaa compliance form","get_count":157,"engine":"google","locale":"en-us","mobile":false}
Желаемый вывод в файл Json:
{"Keyword":"hipaa compliance form","GetCount":157,"Engine":"google","Locale":"en-us","Mobile":false}
Ответы
Ответ 1
Если я правильно понял ваш вопрос, все, что вы хотите сделать, это удалить теги json из вашего определения структуры.
Итак:
package main
import (
"encoding/json"
"fmt"
"io/ioutil"
)
type Rankings struct {
Keyword string
GetCount uint32
Engine string
Locale string
Mobile bool
}
func main() {
var jsonBlob = []byte(`
{"keyword":"hipaa compliance form", "get_count":157, "engine":"google", "locale":"en-us", "mobile":false}
`)
rankings := Rankings{}
err := json.Unmarshal(jsonBlob, &rankings)
if err != nil {
// nozzle.printError("opening config file", err.Error())
}
rankingsJson, _ := json.Marshal(rankings)
err = ioutil.WriteFile("output.json", rankingsJson, 0644)
fmt.Printf("%+v", rankings)
}
Результаты в:
{Keyword:hipaa compliance form GetCount:0 Engine:google Locale:en-us Mobile:false}
И вывод файла:
{"Keyword":"hipaa compliance form","GetCount":0,"Engine":"google","Locale":" en-us","Mobile":false}
Пример выполнения http://play.golang.org/p/dC3s37HxvZ
Примечание. GetCount показывает 0, так как он был прочитан как "get_count"
. Если вы хотите читать в JSON, который имеет "get_count"
vs. "GetCount"
, но выводит "GetCount"
, вам нужно будет провести дополнительный синтаксический анализ.
См. Go- Скопируйте все общие поля между структурами для получения дополнительной информации об этой конкретной ситуации.
Ответ 2
Попробуйте изменить формат json в структуре
type Rankings struct {
Keyword string `json:"Keyword"`
GetCount uint32 `json:"Get_count"`
Engine string `json:"Engine"`
Locale string `json:"Locale"`
Mobile bool `json:"Mobile"`
}
Ответ 3
Акусация произошла благодаря использованию json.Marshal()/json.MarshalIndent(). Он перезаписывает существующий файл, который в моем случае был неоптимальным. Я просто хотел добавить контент в текущий файл и сохранить старый контент.
Это записывает данные через буфер с типом bytes.Buffer.
Это то, что я собрал до сих пор:
package srf
import (
"bytes"
"encoding/json"
"os"
)
func WriteDataToFileAsJSON(data interface{}, filedir string) (int, error) {
//write data as buffer to json encoder
buffer := new(bytes.Buffer)
encoder := json.NewEncoder(buffer)
encoder.SetIndent("", "\t")
err := encoder.Encode(data)
if err != nil {
return 0, err
}
file, err := os.OpenFile(filedir, os.O_RDWR|os.O_CREATE, 0755)
if err != nil {
return 0, err
}
n, err := file.Write(buffer.Bytes())
if err != nil {
return 0, err
}
return n, nil
}
Это выполнение функции вместе со стандартным json.Marshal() или json.MarshalIndent(), который перезаписывает файл.
package main
import (
"encoding/json"
"fmt"
"io/ioutil"
"log"
minerals "./minerals"
srf "./srf"
)
func main() {
//array of Test struct
var SomeType [10]minerals.Test
//Create 10 units of some random data to write
for a := 0; a < 10; a++ {
SomeType[a] = minerals.Test{
Name: "Rand",
Id: 123,
A: "desc",
Num: 999,
Link: "somelink",
People: []string{"John Doe", "Aby Daby"},
}
}
//writes aditional data to existing file, or creates a new file
n, err := srf.WriteDataToFileAsJSON(SomeType, "test2.json")
if err != nil {
log.Fatal(err)
}
fmt.Println("srf printed ", n, " bytes to ", "test2.json")
//overrides previous file
b, _ := json.MarshalIndent(SomeType, "", "\t")
ioutil.WriteFile("test.json", b, 0644)
}
Почему это полезно? File.Write()
возвращает байты, записанные в файл! Так что это идеально, если вы хотите управлять памятью или хранилищем.
WriteDataToFileAsJSON() (numberOfBytesWritten, error)