Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

json.RawMessage does not support NULL #129

Closed
kyleconroy opened this issue Nov 11, 2019 · 13 comments · Fixed by #1145 · May be fixed by #3356
Closed

json.RawMessage does not support NULL #129

kyleconroy opened this issue Nov 11, 2019 · 13 comments · Fixed by #1145 · May be fixed by #3356
Labels
bug Something isn't working
Milestone

Comments

@kyleconroy
Copy link
Collaborator

sql: Scan error on column index 5, name "xxx": unsupported Scan, storing driver.Value type <nil> into type *json.RawMessage
@kyleconroy kyleconroy added the bug Something isn't working label Nov 11, 2019
@kyleconroy
Copy link
Collaborator Author

I believe we can generated the following type to fix this issue

// NullRawMessage represents a json.RawMessage that may be null.
// NullRawMessage implements the Scanner interface so
// it can be used as a scan destination, similar to NullString.
type NullRawMessage struct {
	RawMessage json.RawMessage
	Valid bool // Valid is true if JSON is not NULL
}

// Scan implements the Scanner interface.
func (n *NullRawMessage) Scan(value interface{}) error {
	n.RawMessage = json.RawMessage{}
	if value == nil {
		n.Valid = false
		return nil
	}
	n.Valid = true
	return n.RawMessage.Scan(value)
}

// Value implements the driver Valuer interface.
func (n NullRawMessage) Value() (driver.Value, error) {
	if !n.Valid {
		return nil, nil
	}
	return n.RawMessage.Value()
}

@kyleconroy
Copy link
Collaborator Author

It appears that json.RawMessage does not implement the Scanner interface.

# command-line-arguments
./foo.go:24:21: n.RawMessage.Scan undefined (type json.RawMessage has no field or method Scan)
./foo.go:32:2: not enough arguments to return
./foo.go:32:21: n.RawMessage.Value undefined (type json.RawMessage has no field or method Value

@mrcampbell
Copy link

mrcampbell commented Nov 14, 2019

We ran into this issue earlier, but this isn't really anything wrong with sqlc. We just added a null check in our code and if it was nil, we put in an empty array.

	if params.SalesforceProducts == nil {
		params.SalesforceProducts = json.RawMessage([]byte("[]"))
	}

Definitely not ideal, but like you said, no Scanner.

@mrcampbell
Copy link

But if you find a fix, I'd love to see it! I'll keep an eye out as well.

@zdunecki
Copy link

zdunecki commented Sep 30, 2020

@mrcampbell,@kyleconroy, you can do something like this:

func (n *NullRawMessage) Scan(value interface{}) error {
	if value == nil {
		n.RawMessage, n.Valid = json.RawMessage{}, false
		return nil
	}
	buf, ok := value.([]byte)

	if !ok {
		return errors.New("canot parse to bytes")
	}

	n.RawMessage, n.Valid = buf, true

	return nil
}

@duyker
Copy link

duyker commented Jan 28, 2021

Not sure if it is the best way, but I was able to work around the issue by adding a coalesce statement in the query.sql

// query.sql

-- name: GetSomething :one
select
  t."id",
  coalesce(t."data", '[]') as "data"
from
  "public"."something" t
where
  t.id = $1
limit 1;

@ludusrusso
Copy link
Contributor

Hi! Is someone working on this? I'm getting the same error when reading a jsonb value that can be null.

@eborst
Copy link

eborst commented Aug 11, 2021

Would also love to see a fix for this. I'm having this issue when reading json data from postgres.

@koolay
Copy link

koolay commented Sep 26, 2021

There is the same problem on mysql.

@idan-stripe
Copy link

@koolay I solved this for mysql using overrides in sqlc.yaml:

overrides:
  - db_type: "json"
    go_type:
      type: "[]byte"  # workaround sqlc bug when reading null json columns
    nullable: true

Note that the documentation is not up to date - go_type is a struct and not a string.

@GetPsyched
Copy link

GetPsyched commented Oct 14, 2022

Hey, @idan-stripe. I tried your fix but I still seem to be getting the same error as I was before. Have you changed anything else other than sqlc.yaml?

Edit: I'm using PostgreSQL

@ravayak
Copy link

ravayak commented Jul 13, 2023

Bug still not resolved in 08/13/2023.

@geertjanvdk
Copy link

I did try the main with #129 fix, but no luck. The override works nicely.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug Something isn't working
Projects
None yet