json - 使用自定义格式将结构的 time.Time 字段编组为 JSON 的通用方法
问题描述
我的数据模型定义了多个结构,它们都有两个共同的字段: aStartDate
和 an EndDate
。我需要将这两个字段格式化为2018-09-21
编组 JSON 中的格式,因此结构实现了Marshaller
接口:
type Results struct {
Source string `json:"source"`
StartDate time.Time
EndDate time.Time
}
type WeightedResults struct {
Source string `json:"source"`
StartDate time.Time
EndDate time.Time
}
func (r Results) MarshalJSON() ([]byte, error) {
type Alias Results
if equalDate(r.StartDate, r.EndDate) {
return json.Marshal(&struct {
Date string `json:"date"`
Alias
}{
Date: r.StartDate.Format(dateFormat),
Alias: (Alias)(r),
})
}
return json.Marshal(&struct {
StartDate string `json:"start_date"`
EndDate string `json:"end_date"`
Alias
}{
StartDate: r.StartDate.Format("2006-01-02"),
EndDate: r.EndDate.Format("2006-01-02"),
Alias: (Alias)(r),
})
}
func (r WeightedResults) MarshalJSON() ([]byte, error) {
type Alias WeightedResults
if equalDate(r.StartDate, r.EndDate) {
return json.Marshal(&struct {
Date string `json:"date"`
Alias
}{
Date: r.StartDate.Format(dateFormat),
Alias: (Alias)(r),
})
}
return json.Marshal(&struct {
StartDate string `json:"start_date"`
EndDate string `json:"end_date"`
Alias
}{
StartDate: r.StartDate.Format("2006-01-02"),
EndDate: r.EndDate.Format("2006-01-02"),
Alias: (Alias)(r),
})
}
上面的解决方案工作正常,但会产生大量代码重复。有没有办法重构两个实现MarshalJSON
以使用相同的逻辑/代码?我很清楚 Go 不提供泛型(还),但必须有另一种方法来解决这个问题,对吧?
解决方案
您的自定义封送拆收器不应位于结构上,而应位于嵌入的自定义类型上time.Time
:
type MyTime struct {
time.Time
}
func (t MyTime) MarshalJSON() ([]byte, error) {
return json.Marshal(t.Format("2006-01-02"))
}
然后在任何你想要的地方使用这种类型。
type Results struct {
Source string `json:"source"`
StartDate MyTime
EndDate MyTime
}
推荐阅读
- javascript - 在异步函数中的 if 语句之后使用变量
- android - Wrapped Drawable 显示不正确
- modelica - 如何在 Dymola 中导出矢量图形?
- linux-kernel - sem_post/sem_wait 如何区分基于内存和基于内核的信号量
- python-3.x - 对于 Python 库 parsedatetime,尾随返回值是什么意思?
- java - Java:如何实现 SortedMap 即 TreeMap
- django - 列表视图中使用 ContentType 框架的 DRF 光标分页
- javascript - JQuery val() 仅在输入 2 个字符时为真
- javascript - 提取值
使用 javascript 将属性赋予变量 - swift - 将 SwiftUI 与自定义发布者结合使用 - 使用 .assign 订阅者时出现意外行为