1

I'm working with an API that has json values that can be a number or string and can sometimes be an empty string. For example:

[
    {
        "Description": "Doorknob",
        "Amount": 3.25
    },
    {
        "Description": "Light bulb",
        "Amount": "4.70"
    },
    {
        "Description": "Screwdriver",
        "Amount": ""
    }
]

I've learned I can use json.Number to deal with cases where the value can be a number or a string. But how do I deal with the cases where it's an empty string?

I need to insert these values into a postgres database so I'd like cases where it's an empty string to show as null and I'm thinking sql.NullFloat64 would be best suited to handle it.

Here's a function I'm using that works on the first 2 cases (Doorknob and Light bulb), but fails to unmarshal the last ("Screwdriver").

Here is an unmarshaling function I'm trying to use, but I can't figure out why it's not working:

type NullNumber struct{ sql.NullFloat64 }

func (nn *NullNumber) UnmarshalJSON(data []byte) error {
    var x *json.Number
    if err := json.Unmarshal(data, &x); err != nil {
        return err
    }
    if len(*x) == 0 {
        nn.Valid = false // This doesn't seem to be working. Why?
    }
    this, err := x.Float64()
    if err != nil {
        return err
    }
    nn.Valid = true
    nn.Float64 = this
    return nil
}

Is this a case where I should be using an open interface for the amount?

Any help is very appreciated.

playground: https://play.golang.org/p/QYQRq94OtV3

1 Answer 1

0

You're almost there! json.Unmarshal call errors when a json.Number is given an empty string.

Add this check beforehand:

// edge case: json.Number is given an empty string
if bytes.Equal(data, []byte(`""`)) {
    nn.Valid = false
    return nil
}

https://play.golang.org/p/ILxC8tjYI_G

Sign up to request clarification or add additional context in comments.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.