golang 处理json
当心日期时间标准!!
Golang取自Google图片搜索
因此,今天的故事是关于在Golang中从JSON解组DateTime时发生的怪异行为。 我并不是说这是一个错误,但这只是我的故事,因为我在Golang中处理DateTime和时区时缺乏经验
当我想在Golang中创建CRUD API系统时,就会发生这种情况。 因此,我有一个端点说: /event
将接收来自JSON的事件对象。
{"title" : "title here in string" ,
"place" : "place name here in string" ,
"start_time" : "date time here in string"
}
我使用labstack / echo作为路由库来简化我的请求处理。 通过echo,可以接收响应主体并将其解组到我的结构中,我可以使用以下简单代码来完成它:
package mainimport (
"log"
"net/http"
"time"
"github.com/labstack/echo"
)
type Event struct {
Title string `json:"title"`
Place string `json:"place"`
StartTime time.Time `json:"start_time"`
CreatedAt time.Time `json:"created_at"`
UpdatedAt time.Time `json:"updated_at"`
}
func CreateEvent(c echo.Context) error {
e := new (Event)
err := c.Bind(&e)
if err != nil {
return err
}
now := time.Now()
e.CreatedAt = now
e.UpdatedAt = now
// Other code here
// ....
// Store to DB
// ...
return c.JSON(http.StatusCreated, e)
}
func main() {
e := echo.New()
e.POST( "/event" , CreateEvent)
if err := e.Start( ":9090" ); err != nil {
log.Fatal(err)
}
}
因此,当我想对其进行测试时,我按如下所示制作了请求正文,我只是从我们的API文档示例中将其复制粘贴。 因为起初,我什至不认为这很重要。
{"title" : "Core i13 Anniversarry" ,
"place" : "Ancol Beach" ,
"start_time" : "2018-09-22T12:42:31Z"
}
该API已经部署到登台服务器,因此我直接从Postman到登台服务器对其进行测试。 但是在获取所有存储的事件项之后,start_time与我在请求正文中发布的内容不同。 如下所示。
{"id" : "1" , // auto increment from database
"title" : "Core i13 Anniversarry" ,
"place" : "Ancol Beach" ,
"start_time" : "2018-09-22T19:42:31+07:00" ,
"created_at" : "2018-09-22T16:35:08+07:00" ,
"updated_at" : "2018-09-22T16:35:08+07:00"
}
并在数据库中存储如下:
查看start_time
字段。 它与我发布的内容有所不同。 我想要的是,存储的数据与我从Postman发布的数据相同 。
我发现问题显然是由于时区造成的。 所以我只需要照顾时区。 那是我的第一个念头。 我认为我的系统对此有一个错误。
解决问题
为了解决这个问题,我在下面执行所有此操作。
在连接驱动程序中寻找连接字符串
因为我将MySQL用作数据库存储,所以我需要一个驱动程序来将应用程序与MySQL连接。 我正在使用github.com/go-sql-driver/mysql作为连接驱动程序。 因此,在查找文档并检查了我的连接字符串之后,没有发生任何错误。 我做对了。
dsn := root:root@tcp(127.0 .0 .1 : 3306 )/event?parseTime= true &loc=Asia% 2 FJakarta&charset=utf8mb4&collation=utf8mb4_unicode_ci
手动重建日期时间
仍然很好奇,为什么会这样。 然后,我试图在StackOverflow甚至GitHub中找到与此有关的任何Q / A或问题。
老实说,尝试修复此问题最多需要2个小时。me
在那之前,我感到沮丧。 所以我有两个选择如何解决这个问题。
我将重建start_time,然后再存储到数据库中。向我的队友提问(*即使这样询问也是如此愚蠢🤦)
但是,只是想付出更多努力,我通过重建DateTime来解决此问题。
startTime := e.StartTime
loc,_ := time.LoadLocation( "Asia/Jakarta" )
localStartTime := time.Date(startTime.Year(), startTime.Month(), startTime.Day(), startTime.Hour(), startTime.Minute(), startTime.Second(), startTime.Nanosecond(), loc)
然后,出于好奇,我问我的团队有关此问题的信息。 然后他们和我一样看着我如何复制它,他们也好奇为什么会这样。 仅仅几分钟,我的一个团队就找到了发生这种情况的原因。
发生这种情况是因为我在请求正文中输入了错误的时区偏移。
{"title" : "Core i13 Anniversarry" ,
"place" : "Ancol Beach" ,
"start_time" : "2018-09-22T12:42:31Z" // look for the `Z` indicator
}
由于我居住在+7.00时区(亚洲/雅加达),因此应将其包含在我的JSON中。
因此,当我从以下位置更改start_time
时:
2018 -09 -22 T12: 42 : 31 <strong>Z</strong>
进入
2018 -09 -22 T12: 42 : 31 <strong>+ 07 : 00 </strong>
它解决了我的问题。 我的系统没有发生任何错误。 一切正常。
当我意识到这一点时,我感到so哑。 我一生都花了两个小时nothing。
经验教训
- 请务必先询问您的队友(如果有空的话)
-
2018–09–22T12:42:31+07:00
是RFC 3339格式,每个字符都很重要。
如果您认为本文值得一读,请向您的社交圈鼓掌或分享,以便每个人也可以阅读。 跟随更多类似的故事!
golang 处理json