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

Allocate struct pointers fields with "bind" tag #1165

Merged
merged 1 commit into from Dec 14, 2022

Conversation

eliaperantoni
Copy link
Contributor

Hello,
this is an attempt to fix #1164.

If I were to do something like:

var slice []*struct{
    User *models.User `boil:",bind"`
}
models.Users().BindG(nil, &slice)

It wouldn't have worked prior to this PR because bind would've created a zeroed instance of the struct and then attempted to get a reflect.Value by dereferencing the User field. But in a zeroed struct the pointer is nil, and so you get this panic:

panic: reflect: call of reflect.Value.Field on zero Value

A workaround would be to embed models.User without a pointer. But this is not always feasible or performant, depending on how the resulting slice is going to be used afterward.

This PR makes it so that bind also allocates any pointer field provided that the target is []*Struct and the bind tag is set.


Implementation wise, I simply enumerate the struct fields after the call to reflect.New and allocate any pointer with the bind tag.

When the bind target is []Struct (instead of []*Struct) the behavior remains unchanged as the structs are copied-by-value anyways and the documentation already warns about not using structs with references when binding like that.

@eliaperantoni
Copy link
Contributor Author

@stephenafamo

@stephenafamo stephenafamo merged commit 332721a into volatiletech:master Dec 14, 2022
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Call of reflect.Value.Field on zero Value
2 participants