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
datastore: add omitempty support for time.Time - within isEmptyValue() + updated unit tests #131
Conversation
Thanks for your pull request. It looks like this may be your first contribution to a Google open source project (if not, look below for help). Before we can look at your pull request, you'll need to sign a Contributor License Agreement (CLA). 📝 Please visit https://cla.developers.google.com/ to sign. Once you've signed (or fixed any issues), please reply here (e.g. What to do if you already signed the CLAIndividual signers
Corporate signers
|
1 similar comment
Thanks for your pull request. It looks like this may be your first contribution to a Google open source project (if not, look below for help). Before we can look at your pull request, you'll need to sign a Contributor License Agreement (CLA). 📝 Please visit https://cla.developers.google.com/ to sign. Once you've signed (or fixed any issues), please reply here (e.g. What to do if you already signed the CLAIndividual signers
Corporate signers
|
I signed it! |
CLAs look good, thanks! |
1 similar comment
CLAs look good, thanks! |
@sbuss can you please take a look to this PR? For some reasons CI fails but seems the issue is not related to the change. Related tests are passing:
|
datastore/prop_test.go
Outdated
// }{ | ||
// NonEmptyValue: 1, | ||
// OmitEmptyWithValue: 2, | ||
// }) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Remove this and add a TODO or note in isEmptyValue
.
datastore/prop_test.go
Outdated
} else { | ||
expected := make([]string, len(expectedPropNames)) | ||
copy(expected, expectedPropNames) | ||
PROPS: |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think it would be more readable to sort expectedPropNames
and props
and then compare with a single loop.
sort.Slice(props, func(i, j int) bool {
return props[i].Name < props[j].Name
})
for i, _ := range props {
if props[i].Name != expectedPropNames[i] {
t.Errorf("Unexpected property: %v", props[i].Name)
}
}
datastore/prop_test.go
Outdated
func TestSaveStructOmitEmpty(t *testing.T) { | ||
expectedPropNames := []string{"EmptyValue", "NonEmptyValue", "OmitEmptyWithValue"} | ||
|
||
assert := func(src interface{}) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can this be more descriptive, e.g. testFieldsOmitted
?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
And by "this" I mean assert
. This snippet shows more lines than I selected.
Round tripping a time.Time can result in a different time.Location: Local instead of UTC.
@mtraver, I've addressed your comments, extended tests and fixed build - tests are passing. Let me know if I should squash commits or you can do it on merging the PR. |
datastore/prop_test.go
Outdated
for i := range props { | ||
actualPropNames[i] = props[i].Name | ||
} | ||
// and sort actuals for comparing with already sorted expected names |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
nit: // Sort actuals for comparing with already sorted expected names
datastore/save.go
Outdated
func isEmptyValue(v reflect.Value) bool { | ||
switch v.Kind() { | ||
case reflect.Array, reflect.Map, reflect.Slice, reflect.String: | ||
// TODO(perfomance): Only relect.String needed, other property types are not supported (copy/paste from json package) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
nit: relect
-> reflect
datastore/save.go
Outdated
return v.Len() == 0 | ||
case reflect.Bool: | ||
return !v.Bool() | ||
case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64: | ||
return v.Int() == 0 | ||
case reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Uintptr: | ||
// TODO(perfomance): Uint* are unsuported property types - should be removed (copy/paste from json package) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
nit: unsuported
-> unsupported
@adams-sarah Can you take a look at this, please? |
Done |
@jba, would you mind taking a look? This change probably also needs to be cherry picked into datastore for GoogleCloudPlatform/google-cloud-go. |
Thanks for the heads-up. Done in https://code-review.googlesource.com/#/c/gocloud/+/26910. |
time.Time fields now support the omitempty tag. A zero time.Time will not be saved. Mirrors the corresponding change in the AppEngine datastore client, from golang/appengine#131. Change-Id: I3ca875ecff865f3b533305091b86bfaec9a135fc Reviewed-on: https://code-review.googlesource.com/26910 Reviewed-by: kokoro <noreply+kokoro@google.com> Reviewed-by: Jean de Klerk <deklerk@google.com>
The change was merged in https://code-review.googlesource.com/c/gocloud/+/26910 @jba, @zombiezen can we approve/merge here as well? |
There are 4 advantages of this change:
PropertyLoadSaver
to achieve the same.This change modifies
func isEmptyValue()
. This requires additional type assertion but only fortime.Time
fields withomitempty
label. IdeallyisEmptyValue()
should be removed completely as it is called just in 1 place insidefunc saveStructProperty()
and it can be a bit optimized. But that would be a too big change and pros are not too big so I believe this can/should be done as a separate PR if desired.Closes #98
Alternative to PR #101 that seems to get abandoned and has no unit tests.