How do I decode the following JSON? - json

I have a JSON object of the format
{
"results": [
{
"hits": [
{
"title": "Juliette DELAUNAY",
"author:url": "abc.com"
}
]
}
]
}
To decode in my go program, I have made the following structs
type results struct{
Result []result `json:"results"`
}
type result struct{
Hits []hit `json:"hits"`
}
type hit struct{
Name string `json:"title"`
Url string `json:"author:url"`
}
var m =make(map[string]string)
var t results
But when I try to do the following,
decoder := json.NewDecoder(resp.Body)
err = decoder.Decode(&t)
if err != nil {
fmt.Println(err)
}
for _,x := range t.Result[0].Hits{
m[x.Name] = x.Url
fmt.Println(x.Name,x.Url)
}
It gives a runtime error saying index is out of range. What am I doing wrong? Are my structs incorrect for the given json?
EDIT : The JSON file I need to decode
var jsonStr = []byte(`{"requests":[{"indexName":"recherchepepitesAtoZ","params":"query=x&hitsPerPage=2817&maxValuesPerFacet=42&page=0&facets=%5B%22field_frenchtech_hub_pepite%22%2C%22field_categorie%22%2C%22field_frenchtech_hub_pepite%22%5D&tagFilters="}]}`)
req, err := http.NewRequest("POST", "http://6y0slgl8yj-dsn.algolia.net/1/indexes/*/queries?x-algolia-agent=Algolia%20for%20vanilla%20JavaScript%20(lite)%203.20.4%3Binstantsearch.js%201.10.4%3BJS%20Helper%202.18.0&x-algolia-application-id=6Y0SLGL8YJ&x-algolia-api-key=6832a361e1e1628f8ddb2483623104c6", bytes.NewBuffer(jsonStr))
//req.Header.Set("X-Custom-Header", "application/x-www-form-urlencoded")
req.Header.Set("Content-Type", "application/json")
client := &http.Client{}
resp, err := client.Do(req)
if err != nil {
panic(err)
}
defer resp.Body.Close()

Here is a slightly modified version that works on my machine and go playground:
GoPlayground
package main
import (
"encoding/json"
"fmt"
"strings"
)
type results struct {
Result []result `json:"results"`
}
type result struct {
Hits []hit `json:"hits"`
}
type hit struct {
Name string `json:"title"`
Url string `json:"author:url"`
}
var m = make(map[string]string)
func main() {
jsonSample := `{
"results": [
{
"hits": [
{
"title": "Juliette DELAUNAY",
"author:url": "abc.com"
}
]
}
]
}`
var t results
decoder := json.NewDecoder(strings.NewReader(jsonSample))
err := decoder.Decode(&t)
if err != nil {
fmt.Println(err)
}
for _, x := range t.Result[0].Hits {
m[x.Name] = x.Url
fmt.Println(x.Name, x.Url)
}
}

Related

Parse json data in golang

I am trying to print out a json value that I am getting from a public API.
my json response:
[
{
"address": "0x6679eb24f59dfe111864aec72b443d1da666b360",
"name": "ARIVA",
"symbol": "ARV",
"logo": null,
"logo_hash": null,
"thumbnail": null,
"decimals": "8",
"block_number": "8242108",
"validated": 1
}
]
the code:
type TokenNamingInfo struct {
TokenName string `json:"name"`
TokenAddress string `json:"address"`
TokenSymbol string `json:"symbol"`
}
reqmeta, err := http.NewRequest("GET", "https://somesite.com", nil)
if err != nil {
// handle err
}
reqmeta.Header.Set("Accept", "application/json")
reqmeta.Header.Set("X-Api-Key", "api")
respmeta, err := http.DefaultClient.Do(reqmeta)
if err != nil {
// handle err
}
defer respmeta.Body.Close()
var responseTokenSymbol TokenNamingInfo
json.Unmarshal(tokensymbol, &responseTokenPrice)
However, this is not working and does not print.
fmt.Println(responseTokenSymbol.name)
this is working if my json and struct looks like the below, with the same above procedure.
{
"nativePrice": {
"value": "1906303859440",
"decimals": 18,
"name": "Binance Coin",
"symbol": "BNB"
},
"usdPrice": 0.000875604424294528,
"exchangeAddress": "0xcA143Ce32Fe78f1f7019d7d551a6402fC5350c73",
"exchangeName": "PancakeSwap v2"
}
type TokenPriceInfo struct {
Price float64 `json:"usdPrice"`
ExchangeName string `json:"exchangeName"`
ExchangeAddress string `json:"exchangeAddress"`
}
You want something like that:
import (
"io/ioutil"
"net/http"
"fmt"
"encoding/json"
)
type TokenNamingInfo struct {
TokenName string `json:"name"`
TokenAddress string `json:"address"`
TokenSymbol string `json:"symbol"`
Logo string `json:"logo"`
LogoHash string `json:"logo_hash"`
Thumbnail string `json:"thumbnail"`
Decimals int `json:"decimals"`
BlockNumber string `json:"block_number"`
Validated string `json:"validated"`
}
reqmeta, err := http.NewRequest("GET", "https://somesite.com", nil)
if err != nil {
// handle err
}
reqmeta.Header.Set("Accept", "application/json")
reqmeta.Header.Set("X-Api-Key", "api")
respmeta, err := http.DefaultClient.Do(reqmeta)
if err != nil {
// handle err
}
defer respmeta.Body.Close()
body, err := ioutil.ReadAll(respmeta.Body)
if err != nil {
// handle err
}
fmt.Println(string(body)) // Print result
responseTokenSymbol := &TokenNamingInfo{}
err = json.Unmarshal(body, responseTokenSymbol)
if err != nil {
// handle error
}
fmt.Println(responseTokenSymbol.TokenName) // Print name

How to parse json without a defined stucture?

I want to parse this JSON :
{
"error": null,
"id": "tutu",
"result": {
"param1": 559,
"param2": "yo",
"param3": {"tab":["a", "b"], "param4":"hello"},
}
}
The problem is that I want a flexible solution if the JSON structure changes: I want to be able to access each field with a key system (like in Javascript) without knowing in advance the JSON structure:
fmt.Println(jsonObj["result"]["param3"]["tab"][1])
Is it possible to do it ?
First, in your case unmarshall directly into map[string]interface{} to save an assertion.
var jsonObj map[string]interface{}
err := json.Unmarshal(b, &jsonObj)
Second, remember to check the assertion
result, ok := jsonObj["result"].(map[string]interface{})
if !ok {
panic("not json obj")
}
param3, ok := result["param3"].(map[string]interface{})
if !ok {
panic("not json obj")
}
tab, ok := param3["tab"].([]interface{})
if !ok {
panic("not json arr")
}
Lastly, you can declare a new type and "hide" the assertions in its methods
type AnyObj map[string]interface{}
func (obj AnyObj) MustObject(name string) AnyObj {
v, ok := obj[name].(map[string]interface{})
if !ok {
panic("not json obj")
}
return AnyObj(v)
}
func (obj AnyObj) MustArray(name string) []interface{} {
v, ok := obj[name].([]interface{})
if !ok {
panic("not json arr")
}
return v
}
Then use like this:
func main() {
var jsonObj AnyObj
err := json.Unmarshal(b, &jsonObj)
if (err != nil) {
panic(err);
}
tab := jsonObj.MustObject("result").MustObject("param3").MustArray("tab")
fmt.Println(tab[1])
}
check it here https://play.golang.org/p/ucdMZ0VEKcr
Yes, it is possible, although the fact that you need to assert the types makes it a bit unwieldy:
package main
import (
"encoding/json"
"fmt"
)
func main() {
b := []byte(`
{
"error": null,
"id": "tutu",
"result": {
"param1": 559,
"param2": "yo",
"param3": {"tab":["a", "b"], "param4": "hello"}
}
}
`)
var jsonObj interface{}
err := json.Unmarshal(b, &jsonObj)
if err != nil {
panic(err)
}
msg := jsonObj.(map[string]interface{})
result := msg["result"].(map[string]interface{})
param3 := result["param3"].(map[string]interface{})
tab := param3["tab"].([]interface{})
fmt.Println(tab[1])
}
This prints
b
like you would expect.
Note that this program will panic: not just if the JSON fails to parse, but also if the JSON does not exactly match the program's expectations: missing keys, different types and so on.
The Generic JSON with interface section of the JSON and Go article on The Go Blog has an example of checking the actual type of the thing at runtime; as was suggested in the comments, it's easy to forget.
this is mine used fastjson:
package main
import (
"fmt"
"github.com/valyala/fastjson"
)
type ParseValue struct {
*fastjson.Value
}
func Parse(b []byte) (*ParseValue, error) {
var p fastjson.Parser
v, err := p.ParseBytes(b)
if err != nil {
return nil, err
}
return &ParseValue{v}, nil
}
func (p *ParseValue) GetString(keys ...string) string {
return string(p.GetStringBytes(keys...))
}
func main() {
b := []byte(`
{
"error": null,
"id": "tutu",
"result": {
"param1": 559,
"param2": "yo",
"param3": {"tab":["a", "b"], "param4": "hello"}
}
}
`)
v, err := Parse(b)
if err != nil {
panic(err)
}
r := v.GetString("result", "param3", "tab", "1")
fmt.Println(r)
rr := v.GetUint("result", "param1")
fmt.Println(rr)
// output:
// b
// 559
}

Custom UnmarshalJSON: array object to map

I have json files like this:
{
"Systems":[
{
"ID":74,
"Data1":0.1,
"Data2":4
},
{
"ID":50,
"Data1":31,
"Data2":3
}
],
"Error":false
}
I would like to unmarshal in Go to something like this (note map):
type Info struct {
Systems map[int]System `json:"Systems"` // key should be ID json field
Error bool `json:"Error"`
}
type System struct {
Data1 float32 `json:"Data1"`
Data2 int `json:"Data2"`
}
Here is my (wrong) code:
package main
import (
"encoding/json"
"fmt"
)
type Info struct {
Systems map[int]System `json:"Systems"` // key should be ID json field
Error bool `json:"Error"`
}
type System struct {
ID int `json:"ID"`
Data1 float32 `json:"Data"`
Data2 int `json:"Data2"`
}
func main() {
file := "{\"Systems\":[{\"ID\":74,\"Data1\":0.1,\"Data2\":4},{\"ID\":50,\"Data1\":31,\"Data2\":3}],\"Error\":true}"
info := Info{}
bytes := []byte(file)
err := json.Unmarshal(bytes, &info)
if err != nil {
fmt.Printf("=> %v\n", err)
}
fmt.Printf("INFO: %+v\n", info)
}
func (d *Info) UnmarshalJSON(buf []byte) error {
var tmp interface{}
if err := json.Unmarshal(buf, &tmp); err != nil {
return err
}
d.Error = tmp.(map[string]interface{})["Error"].(bool)
d.Systems = make(map[int]System)
for _, v := range tmp.(map[string]interface{})["Systems"].([]interface{}) {
d.Systems[v.(map[string]interface{})["ID"].(int)] = v.(map[string]interface{}).(System)
}
return nil
}
https://play.golang.org/p/L_Gx-f9ycjW
You can try this
package main
import (
"encoding/json"
"fmt"
)
func main() {
var str = `{
"Systems":[
{
"ID":74,
"Data1":0.1,
"Data2":4
},
{
"ID":50,
"Data1":31,
"Data2":3
}
],
"Error":false
}`
var t Info
err := json.Unmarshal([]byte(str), &t)
if err != nil {
panic(err)
}
bts, err := json.MarshalIndent(t, "", " ")
if err != nil {
panic(err)
}
fmt.Println(string(bts))
}
type Info struct {
Systems map[int]System `json:"Systems"`
Error bool `json:"Error"`
}
type System struct {
ID int `json:"ID,omitempty"`
Data1 float32 `json:"Data1"`
Data2 int `json:"Data2"`
}
func (info *Info) UnmarshalJSON(data []byte) error {
var t struct {
Systems []System `json:"Systems"`
Error bool `json:"Error"`
}
err := json.Unmarshal(data, &t)
if err != nil {
return err
}
info.Systems = make(map[int]System, 0)
for _, v := range t.Systems {
info.Systems[v.ID] = v
}
return nil
}
https://play.golang.org/p/qB3vF08cmW8
Output:
{
"Systems": {
"50": {
"ID": 50,
"Data1": 31,
"Data2": 3
},
"74": {
"ID": 74,
"Data1": 0.1,
"Data2": 4
}
},
"Error": false
}
You can't decode json directly in the struct you proposed because it doesn't match the json structure.
What you can do is decoding the json into this:
type Info struct {
Systems []*System `json:"Systems"` // array here
Error bool `json:"Error"`
Index map[int]*System // not json mapped
}
type System struct {
ID int `json:"ID"`
Data1 float32 `json:"Data1"`
Data2 int `json:"Data2"`
}
and populate the Index field in postprocessing with something like this:
var info Info
json.Unmarshal(dataIn, &info)
info.Index = map[int]*System{} // initialize an empty map
for _, s := range info.Systems {
info.Index[s.ID] = s
}
fmt.Println(info.Index[50].Data1)
you can find a full example here https://play.golang.org/p/B8O6nfI258-

How do I json unmarshal slice inside a slice

I am trying to unmarshal some pretty ugly json but can't figure out how. I have:
package main
import "fmt"
import "encoding/json"
type PublicKey struct {
ID int `json:"id"`
Key string `json:"key"`
MyData []struct {
ID string `json:"id"`
Value int `json:"value"`
}
}
func main() {
b := `[
{
"id": 1,
"key": "my_key"
},
[
{
"id": "some_id",
"value": 12
},
{
"id": "anorther_id",
"value": 13
}
]
]`
var pk []PublicKey
err := json.Unmarshal([]byte(b), &pk)
if err != nil {
fmt.Println(err)
}
fmt.Println(pk)
}
For the result I am getting:
[{1 my_key []} {0 []}]
The second slice is empty when it shouldn't be.
EDIT:
The error I get is:
json: cannot unmarshal array into Go struct field PublicKey.key of type main.PublicKey
https://play.golang.org/p/cztXOchiiS5
That is some truly hideous JSON! I have two approaches to handling the mixed array elements and I like the 2nd one better. Here's the first approach using interface and a type switch:
package main
import (
"encoding/json"
"errors"
"fmt"
)
type PublicKey struct {
ID int `json:"id"`
Key string `json:"key"`
}
type MyData struct {
ID string `json:"id"`
Value int `json:"value"`
}
type MixedData struct {
Key []PublicKey
MyData [][]MyData
}
func (md *MixedData) UnmarshalJSON(b []byte) error {
md.Key = []PublicKey{}
md.MyData = [][]MyData{}
var obj []interface{}
err := json.Unmarshal([]byte(b), &obj)
if err != nil {
return err
}
for _, o := range obj {
switch o.(type) {
case map[string]interface{}:
m := o.(map[string]interface{})
id, ok := m["id"].(float64)
if !ok {
return errors.New("public key id must be an int")
}
pk := PublicKey{}
pk.ID = int(id)
pk.Key, ok = m["key"].(string)
if !ok {
return errors.New("public key key must be a string")
}
md.Key = append(md.Key, pk)
case []interface{}:
a := o.([]interface{})
myData := make([]MyData, len(a))
for i, x := range a {
m, ok := x.(map[string]interface{})
if !ok {
return errors.New("data array contains unexpected object")
}
val, ok := m["value"].(float64)
if !ok {
return errors.New("data value must be an int")
}
myData[i].Value = int(val)
myData[i].ID, ok = m["id"].(string)
if !ok {
return errors.New("data id must be a string")
}
md.MyData = append(md.MyData, myData)
}
default:
// got something unexpected, handle somehow
}
}
return nil
}
func main() {
b := `[
{
"id": 1,
"key": "my_key"
},
[
{
"id": "some_id",
"value": 12
},
{
"id": "another_id",
"value": 13
}
]
]`
m := MixedData{}
err := json.Unmarshal([]byte(b), &m)
if err != nil {
fmt.Println(err)
}
fmt.Println(m)
}
https://play.golang.org/p/g8d_AsH-pYY
Hopefully there aren't any unexpected other elements, but they can be handled similarly.
Here is the second that relies more on Go's internal JSON parsing with the help of json.RawMessage. It makes the same assumptions about the contents of the array. It assumes that any objects will Unmarshal into PublicKey instances and any arrays consist of only MyData instances. I also added how to marshal back into the target JSON for symmetry:
package main
import (
"encoding/json"
"fmt"
"os"
)
type PublicKey struct {
ID int `json:"id"`
Key string `json:"key"`
}
type MyData struct {
ID string `json:"id"`
Value int `json:"value"`
}
type MixedData struct {
Keys []PublicKey
MyData [][]MyData
}
func (md *MixedData) UnmarshalJSON(b []byte) error {
md.Keys = []PublicKey{}
md.MyData = [][]MyData{}
obj := []json.RawMessage{}
err := json.Unmarshal([]byte(b), &obj)
if err != nil {
return err
}
for _, o := range obj {
switch o[0] {
case '{':
pk := PublicKey{}
err := json.Unmarshal(o, &pk)
if err != nil {
return err
}
md.Keys = append(md.Keys, pk)
case '[':
myData := []MyData{}
err := json.Unmarshal(o, &myData)
if err != nil {
return err
}
md.MyData = append(md.MyData, myData)
default:
// got something unexpected, handle somehow
}
}
return nil
}
func (md *MixedData) MarshalJSON() ([]byte, error) {
out := make([]interface{}, len(md.Keys)+len(md.MyData))
i := 0
for _, x := range md.Keys {
out[i] = x
i++
}
for _, x := range md.MyData {
out[i] = x
i++
}
return json.Marshal(out)
}
func main() {
b := `[
{
"id": 1,
"key": "my_key"
},
[
{
"id": "some_id",
"value": 12
},
{
"id": "another_id",
"value": 13
}
]
]`
m := MixedData{}
err := json.Unmarshal([]byte(b), &m)
if err != nil {
fmt.Println(err)
os.Exit(1)
}
fmt.Println(m)
enc := json.NewEncoder(os.Stdout)
enc.SetIndent("", " ")
if err := enc.Encode(m); err != nil {
fmt.Println(err)
os.Exit(1)
}
}
https://play.golang.org/p/ryZzaWKNcN0
Here's an approach that combines json.RawMessage with the trick of using the default unmarshaler in a type that implements json.Unmarshaler by creating a new temporary type that aliases the target type.
The idea is that we unmarshal the incoming array into a raw message and ensure that the array length is what we expect. Then we unmarshal the individual array elements into the custom struct types using their JSON tag annotations. The end result is that we can unmarshal the PublicKey type in the usual way and the UnmarshalJSON code is not terribly difficult to follow once you understand the tricks.
For example (Go Playground):
type PublicKey struct {
ID int `json:"id"`
Key string `json:"key"`
Data []MyData
}
type MyData struct {
ID string `json:"id"`
Value int `json:"value"`
}
func (pk *PublicKey) UnmarshalJSON(bs []byte) error {
// Unmarshal into a RawMessage so we can inspect the array length.
var rawMessage []json.RawMessage
err := json.Unmarshal(bs, &rawMessage)
if err != nil {
return err
}
if len(rawMessage) != 2 {
return fmt.Errorf("expected array of length 2, got %d", len(rawMessage))
}
// Parse the first object as PublicKey using the default unmarshaler
// using a temporary type that is an alias for the target type.
type PublicKey2 PublicKey
var pk2 PublicKey2
err = json.Unmarshal(rawMessage[0], &pk2)
if err != nil {
return err
}
// Parse the second object as []MyData in the usual way.
err = json.Unmarshal(rawMessage[1], &pk2.Data)
if err != nil {
return err
}
// Finally, assign the aliased object to the target object.
*pk = PublicKey(pk2)
return nil
}
func main() {
var pk PublicKey
err := json.Unmarshal([]byte(jsonstr), &pk)
if err != nil {
panic(err)
}
fmt.Printf("%#v\n", pk)
// main.PublicKey{ID:1, Key:"my_key", Data:[]main.MyData{main.MyData{ID:"some_id", Value:12}, main.MyData{ID:"anorther_id", Value:13}}}
}

got an error when i tried to call the value with go lang

I just starting learn this Go Lang programming, and now i'm stuck with the [] things, I tried to create a blog using the Go Lang and i'm using a template, there's no problem with the template, it just I want to append a data that I got from json file.
If I just take the data and send it through the file it's already done, but the problem is when I tried to append the slug to the data (because the json file i got no slug url in it.
That's why I want to get the title of the post then make a slug with it, then
package main
import (
"encoding/json"
"fmt"
"github.com/gosimple/slug"
"html/template"
"io/ioutil"
"net/http"
"os"
)
type Blog struct {
Title string
Author string
Header string
}
type Posts struct {
Posts []Post `json:"posts"`
}
type Post struct {
Title string `json:"title"`
Author string `json:"author"`
Content string `json:"content"`
PublishDate string `json:"publishdate"`
Image string `json:"image"`
}
type BlogViewModel struct {
Blog Blog
Posts []Post
}
func loadFile(fileName string) (string, error) {
bytes, err := ioutil.ReadFile(fileName)
if err != nil {
return "", err
}
return string(bytes), nil
}
func loadPosts() []Post {
jsonFile, err := os.Open("source/posts.json")
if err != nil {
fmt.Println(err)
}
fmt.Println("Successfully open the json file")
defer jsonFile.Close()
bytes, _ := ioutil.ReadAll(jsonFile)
var post []Post
json.Unmarshal(bytes, &post)
return post
}
func handler(w http.ResponseWriter, r *http.Request) {
blog := Blog{Title: "asd", Author: "qwe", Header: "zxc"}
posts := loadPosts()
viewModel := BlogViewModel{Blog: blog, Posts: posts}
t, _ := template.ParseFiles("template/blog.html")
t.Execute(w, viewModel)
}
The error is show in the main function
func main() {
posts := loadPosts()
for i := 0; i < len(posts.Post); i++ { // it gives me this error posts.Post undefined (type []Post has no field or method Post)
fmt.Println("Title: " + posts.Post[i].Title)
}
// http.HandleFunc("/", handler)
// fs := http.FileServer(http.Dir("template"))
// http.Handle("/assets/css/", fs)
// http.Handle("/assets/js/", fs)
// http.Handle("/assets/fonts/", fs)
// http.Handle("/assets/images/", fs)
// http.Handle("/assets/media/", fs)
// fmt.Println(http.ListenAndServe(":9000", nil))
}
I already try to solved it a couple of hours but I hit the wall, I think it's possible but I just don't find the way, I don't know what is the good keyword to solve the problem.
And I don't if I already explain good enough or not. Please help me, thank you
This is the JSON file format
{
"posts": [
{
"title": "sapien ut nunc",
"author": "Jeni",
"content": "jgwilt0#mapquest.com",
"publishdate": "26.04.2017",
"image": "http://dummyimage.com/188x199.png/cc0000/ffffff"
},
{
"title": "mus vivamus vestibulum sagittis",
"author": "Analise",
"content": "adonnellan1#biblegateway.com",
"publishdate": "13.03.2017",
"image": "http://dummyimage.com/182x113.bmp/ff4444/ffffff"
}
]
}
You're loadPost method returns []Post. Your definition of Post does not contain the attribute Post. Your Posts struct does.
Here is a modified working example. I didn't define your other structures for brevity.
package main
import (
"encoding/json"
"fmt"
"io/ioutil"
)
var rawJson = `{
"posts": [
{
"title": "sapien ut nunc",
"author": "Jeni",
"content": "jgwilt0#mapquest.com",
"publishdate": "26.04.2017",
"image": "http://dummyimage.com/188x199.png/cc0000/ffffff"
},
{
"title": "mus vivamus vestibulum sagittis",
"author": "Analise",
"content": "adonnellan1#biblegateway.com",
"publishdate": "13.03.2017",
"image": "http://dummyimage.com/182x113.bmp/ff4444/ffffff"
}
]
}`
type Data struct {
Posts []struct {
Title string `json:"title"`
Author string `json:"author"`
Content string `json:"content"`
Publishdate string `json:"publishdate"`
Image string `json:"image"`
} `json:"posts"`
}
func loadFile(fileName string) (string, error) {
bytes, err := ioutil.ReadFile(fileName)
if err != nil {
return "", err
}
return string(bytes), nil
}
func loadData() (Data, error) {
var d Data
// this is commented out so that i can load raw bytes as an example
/*
f, err := os.Open("source/posts.json")
if err != nil {
return d, err
}
defer f.Close()
bytes, _ := ioutil.ReadAll(f)
*/
// replace rawJson with bytes in prod
json.Unmarshal([]byte(rawJson), &d)
return d, nil
}
func main() {
data, err := loadData()
if err != nil {
log.Fatal(err)
}
for i := 0; i < len(data.Posts); i++ {
fmt.Println("Title: " + data.Posts[i].Title)
}
/*
// you can also range over the data.Posts if you are not modifying the data then using the index is not necessary.
for _, post := range data.Posts {
fmt.Println("Title: " + post.Title)
}
*/
}
modified just for files
package main
import (
"encoding/json"
"fmt"
"io/ioutil"
)
type Data struct {
Posts []struct {
Title string `json:"title"`
Author string `json:"author"`
Content string `json:"content"`
Publishdate string `json:"publishdate"`
Image string `json:"image"`
} `json:"posts"`
}
func loadData() (Data, error) {
var d Data
b, err := ioutil.ReadFile("source/posts.json")
if err != nil {
return d, err
}
err = json.Unmarshal(b, &d)
if err != nil {
return d, err
}
return d, nil
}
func main() {
data, err := loadData()
if err != nil {
log.Fatal(err)
}
for _, post := range data.Posts {
fmt.Println("Title: " + post.Title)
}
}