Home > Article > Backend Development > Unmarshalling sql.NullTime structures in Go
php Editor Xiaoxin In the Go language, we often use the sql.NullTime structure to process the time field in the database. The NullTime structure can represent a nullable time value and is very suitable for handling null values in the database. In this article, we will explain how to unmarshal a sql.NullTime structure and how to correctly handle null situations that may exist within it. Whether you are a beginner or an experienced developer, this article will provide you with clear guidance to help you better understand and use the NullTime structure.
Given
type NullTime struct { Time time.Time Valid bool // Valid is true if Time is not NULL }
and
type PayinCount struct { DateShiftStart sql.NullTime `json:"dateShiftStart"` DateShiftEnd sql.NullTime `json:"dateShiftend"` }
When I process the following JSON
{ "dateShiftStart":"2023-10-16", "dateShiftEnd":"2023-10-23" }
and
var payinsCount PayinsCount err = json.Unmarshal(body, &payinsCount) if err != nil { sendErrorResponse(w, err.Error(), http.StatusBadRequest) return }
Where sendErrorResponse is the following auxiliary process
func sendErrorResponse(w http.ResponseWriter, err string, statusCode int) { messageStatusCode := MessageStatusCode{ Message: err, StatusCode: statusCode} w.WriteHeader(statusCode) json.NewEncoder(w).Encode(messageStatusCode) }
I received the following message
{ "message": "json: cannot unmarshal string into Go struct field PayinsCount.dateShiftStart of type sql.NullTime", "statusCode": 400 }
how to solve this problem?
I ended up using the following. I added the following types.
type NullDate sql.NullTime
Then I changed the PayinsCount to use NullDate
type PayinsCount struct { DateShiftStart NullDate `json:"dateShiftStart,omitempty"` DateShiftEnd NullDate `json:"dateShiftend,omitempty"` }
Then I created
// UnmarshalJSON for NullDate func (nd *NullDate) UnmarshalJSON(b []byte) error { s := string(b) s = strings.ReplaceAll(s, "\"", "") x, err := time.Parse(time.DateOnly, s) if err != nil { nd.Valid = false return err } nd.Time = x nd.Valid = true return nil }
Now when I process the following JSON
{ "dateShiftStart":"2023-10-16", "dateShiftEnd":"2023-10-23" }
and
var payinsCount PayinsCount err = json.Unmarshal(body, &payinsCount) if err != nil { sendErrorResponse(w, err.Error(), http.StatusBadRequest) return }
It works. I ended up with a valid PayinsCount instance.
For completeness, here is the MarshalJSON function for NullDate
// MarshalJSON for NullDate func (nd NullDate) MarshalJSON() ([]byte, error) { if !nd.Valid { return []byte("null"), nil } val := fmt.Sprintf("\"%s\"", nd.Time.Format(time.DateOnly)) return []byte(val), nil }
Note the escaped double quotes - without them the encoding/json marshaling code processes the date string in 3 chunks and I get the following error
error(*encoding/json.SyntaxError) *{msg: "invalid character '-' after top-level value", Offset: 0}
The above is the detailed content of Unmarshalling sql.NullTime structures in Go. For more information, please follow other related articles on the PHP Chinese website!