Home > other >  How do I bind a date string to a struct?
How do I bind a date string to a struct?

Time:09-27

type TestModel struct {
  Date     time.Time `json:"date" form:"date" gorm:"index"`
  gorm.Model
}

i'm using echo framwork, and I have a struct like the one above, and I get string data like '2021-09-27' , how can I bind it to the struct?

func CreateDiary(c echo.Context) error {
    var getData model.TestModel
    if err := (&echo.DefaultBinder{}).BindBody(c, &getData); err != nil {
        fmt.Print(err.Error())
    }
   return c.JSON(200, getData)
}

When I code like this, I get the following error:

code=400, message=parsing time "2021-09-27" as "2006-01-02T15:04:05Z07:00": cannot parse "" as "T", internal=parsing time "2021-09-27" as "2006-01-02T15:04:05Z07:00": cannot parse "" as "T"

I'm a golang beginner, can you show me a simple example??, please.

i'm using echo framwork

CodePudding user response:

Type CustomTime time.Time

func (ct *CustomTime) UnmarshalParam(param string) error {
    t, err := time.Parse(`2006-01-02`, param)
    if err != nil {
        return err
    }
    *ct = CustomTime(t)
    return nil
}

ref: https://github.com/labstack/echo/issues/1571

CodePudding user response:

You need to wrap time.Time into custom struct and then implement json.Marshaler and json.Unmarshaler interfaces

Example

package main

import (
    "encoding/json"
    "fmt"
    "strings"
    "time"
)

type jsonDate struct {
    time.Time
}

type TestModel struct {
    Date jsonDate `json:"date"`
}

func (t jsonDate) MarshalJSON() ([]byte, error) {
    date := t.Time.Format("2006-01-02")
    date = fmt.Sprintf(`"%s"`, date)
    return []byte(date), nil
}

func (t *jsonDate) UnmarshalJSON(b []byte) (err error) {
    s := strings.Trim(string(b), "\"")

    date, err := time.Parse("2006-01-02", s)
    if err != nil {
        return err
    }
    t.Time = date
    return
}

func main() {
    b := []byte(`{"date": "2021-09-27"}`)
    fmt.Println(string(b))

    var j TestModel
    json.Unmarshal(b, &j)
    fmt.Println(j.Date)

    b2, err := json.Marshal(j)
    fmt.Println(string(b2), err)
}
  • Related