sql.NullString || sql.NullInt64转换为正常格式json null?

时间:2017-10-26 19:33:10

标签: go

通常在关系数据库中发生,当从数据库中选择记录时,将返回该字段。 Go不会将字符串和数字处理为nil,在这种情况下有一个辅助类型的sql.Null {type} 但是如果以json格式返回数据,则不需要使用此类型,因为在javascript中,存在null。

现在我将sql.NullString转换为手动。 sql本身还有一个变量返回,而不是null,还有一个空行(如果是一行), 但由于某些原因,将来很难调试。

你如何解决这个问题?

1 个答案:

答案 0 :(得分:2)

你的问题有点令人困惑,但我想我明白你在问什么。受到另一篇我无法找到的帖子的启发,我在sql.Null类型周围编写了包装器,将JSON编码为基本类型。见下面的例子:

import (
    "database/sql"
    "encoding/json"
)

type JsonNullInt64 struct {
    sql.NullInt64
}

type JsonNullFloat64 struct {
    sql.NullFloat64
}

type JsonNullString struct {
    sql.NullString
}

type JsonNullBool struct {
    sql.NullBool
}

func (v *JsonNullBool) MarshalJSON() ([]byte, error) {
    if v.Valid {
        return json.Marshal(v.Bool)
    } else {
        return json.Marshal(nil)
    }
}

func (v *JsonNullBool) UnmarshalJSON(data []byte) error {
    var b *bool
    if err := json.Unmarshal(data, &b); err != nil {
        return err
    }

    if b != nil {
        v.Valid = true
        v.Bool = *b
    } else {
        v.Valid = false
    }

    return nil
}

func (v *JsonNullString) MarshalJSON() ([]byte, error) {
    if v.Valid {
        return json.Marshal(v.String)
    } else {
        return json.Marshal(nil)
    }
}

func (v *JsonNullString) UnmarshalJSON(data []byte) error {
    var str *string
    if err := json.Unmarshal(data, &str); err != nil {
        return err
    }

    if str != nil {
        v.Valid = true
        v.String = *str
    } else {
        v.Valid = false
    }

    return nil
}

func (v JsonNullFloat64) MarshalJSON() ([]byte, error) {
    if v.Valid {
        return json.Marshal(v.Float64)
    } else {
        return json.Marshal(0)
    }
}

func (v *JsonNullFloat64) UnmarshalJSON(data []byte) error {
    // Unmarshalling into a pointer will let us detect null

    var x *float64
    err := json.Unmarshal(data, &x)
    if err != nil {
        return err
    }
    if x != nil {
        v.Valid = true
        v.Float64 = *x
    } else {
        v.Valid = false
    }
    return nil
}

func (v JsonNullInt64) MarshalJSON() ([]byte, error) {
    if v.Valid {
        return json.Marshal(v.Int64)
    } else {
        return json.Marshal(0)
    }
}

func (v JsonNullInt64) UnmarshalJSON(data []byte) error {
    // Unmarshalling into a pointer will let us detect null
    var x *int64
    if err := json.Unmarshal(data, &x); err != nil {
        return err
    }
    if x != nil {
        v.Valid = true
        v.Int64 = *x
    } else {
        v.Valid = false
    }
    return nil
}