Структурное встраивание с использованием sqlx, не возвращающего значение из БД
У меня есть структура с полем времени, которое может быть ноль:
type Order struct {
...
PickupTime *time.Time `json:"-"`
}
Я хочу сохранить это в БД с sqlx
так что я думаю, мне нужно использовать pq.NullTime
как предложено здесь.
Вместо обновления Order
объект (я не хочу просачивать код БД в слой модели), я подумал, что мог бы встроить порядок в PgOrder
и изменить PickupTime
тип:
type PgOrder struct {
Order
PickupTime pq.NullTime
}
Проблема в том, что когда я просто обновляю Order
в БД, а затем развернуться и получить этот порядок, возвращенный PickupTime
пустой.
// update
func (pg Postgres) UpdateOrderPickupTime(order *Order, pickupTime time.Time) error {
_, err := pg.Exec(`UPDATE orders SET pickup_time = $1 WHERE id = $2`, pickupTime, order.ID)
return err
}
// retrieve
func (pg Postgres) GetOrder(orderID DatabaseID) (*Order, error) {
pgOrder := PgOrder{}
err := pg.Get(&pgOrder, `SELECT * FROM orders WHERE id = $1`, orderID)
if err == sql.ErrNoRows {
return nil, nil
}
... // at this point pgOrder.PickupTime is 0001-01-01 00:00:00 +0000 UTC
}
Если я ставлю точку останова между обновлением и извлечением, я могу проверить БД и увидеть, что значение сохраняется как 2017-04-20 12:05:37-04
, Таким образом, проблема должна быть в части извлечения. Если я правильно понял из документации, sqlx должен уметь обрабатывать встроенные структуры.
2 ответа
Если ваше поле является указателем на что-то, например *time.Time
, или же *string
вам не нужно использовать NullXxx
типы. Эти типы должны использоваться, когда у вас есть поле не ноль, например time.Time
, или же string
в то время как соответствующий столбец может быть NULL
,
Если вы все равно хотите добавить свой тип, чтобы избежать потенциального затенения, уже упомянутого @Dmitri Goldring, вы можете сказать sqlx
чтобы пропустить поле, в которое вы не хотите сканировать столбец. Так же, как вы сделали с json
тег, вы можете сделать это с db
тег:
type Order struct {
...
PickupTime *time.Time `json:"-" db:"-"`
}
type PgOrder struct {
Order
PickupTime pq.NullTime
}
Похоже, вы следите за PickupTime. Если я правильно читаю документацию sqlx, это означает, что он будет хранить значение в первом найденном им значении (в порядке), а затем, когда вы читаете значение в PgOrder, это неинициализированное время. Время. Вы можете проверить поле Valid в PgOrder.PickupTime, чтобы подтвердить это (оно должно быть недействительным).