summaryrefslogtreecommitdiff
path: root/vendor/codeberg.org/gruf/go-structr
diff options
context:
space:
mode:
authorLibravatar kim <grufwub@gmail.com>2025-08-22 16:04:22 +0200
committerLibravatar kim <gruf@noreply.codeberg.org>2025-08-22 16:04:22 +0200
commit383e41e3e50f3cab3a0772ab59525707ad2c63da (patch)
treeda4a535b0329e9efd92c942039db420f05107c65 /vendor/codeberg.org/gruf/go-structr
parent[chore] update dependencies (#4386) (diff)
downloadgotosocial-383e41e3e50f3cab3a0772ab59525707ad2c63da.tar.xz
[chore] bump go-structr to v0.9.9 (#4390)
this improves handling of zero value keys. not something we bump into often, but a useful fix to have in place. Reviewed-on: https://codeberg.org/superseriousbusiness/gotosocial/pulls/4390 Co-authored-by: kim <grufwub@gmail.com> Co-committed-by: kim <grufwub@gmail.com>
Diffstat (limited to 'vendor/codeberg.org/gruf/go-structr')
-rw-r--r--vendor/codeberg.org/gruf/go-structr/README.md2
-rw-r--r--vendor/codeberg.org/gruf/go-structr/index.go9
-rw-r--r--vendor/codeberg.org/gruf/go-structr/runtime.go45
3 files changed, 38 insertions, 18 deletions
diff --git a/vendor/codeberg.org/gruf/go-structr/README.md b/vendor/codeberg.org/gruf/go-structr/README.md
index 922dc1a58..2ea88faef 100644
--- a/vendor/codeberg.org/gruf/go-structr/README.md
+++ b/vendor/codeberg.org/gruf/go-structr/README.md
@@ -2,7 +2,7 @@
A library with a series of performant data types with automated struct value indexing. Indexing is supported via arbitrary combinations of fields, and in the case of the cache type, negative results (errors!) are also supported.
-Under the hood, go-structr maintains a hashmap per index, where each hashmap is a hashmap keyed by serialized input key type. This is handled by the incredibly performant serialization library [go-mangler/v2](https://codeberg.org/gruf/go-mangler), which at this point in time supports *most* arbitrary types (other than channels, functions), so feel free to index by by almost *anything*!
+Under the hood, go-structr maintains a hashmap per index, where each hashmap is keyed by serialized input key. This is handled by the incredibly performant serialization library [go-mangler/v2](https://codeberg.org/gruf/go-mangler), which at this point in time supports all concrete types, so feel free to index by by *almost* anything!
See the [docs](https://pkg.go.dev/codeberg.org/gruf/go-structr) for more API information.
diff --git a/vendor/codeberg.org/gruf/go-structr/index.go b/vendor/codeberg.org/gruf/go-structr/index.go
index 9fbdcf112..d5bd5562e 100644
--- a/vendor/codeberg.org/gruf/go-structr/index.go
+++ b/vendor/codeberg.org/gruf/go-structr/index.go
@@ -21,12 +21,9 @@ type IndexConfig struct {
// be specified using periods. An example:
// "Username,Favorites.Color"
//
- // Note that nested fields where the nested
- // struct field is a ptr are supported, but
- // nil ptr values in nesting will result in
- // that particular value NOT being indexed.
- // e.g. with "Favorites.Color" if *Favorites
- // is nil then it will not be indexed.
+ // If a nested field encounters a nil pointer
+ // along the way, e.g. "Favourites == nil", then
+ // a zero value for "Favorites.Color" is used.
//
// Field types supported include any of those
// supported by the `go-mangler/v2` library.
diff --git a/vendor/codeberg.org/gruf/go-structr/runtime.go b/vendor/codeberg.org/gruf/go-structr/runtime.go
index c1a883462..8a8d53ede 100644
--- a/vendor/codeberg.org/gruf/go-structr/runtime.go
+++ b/vendor/codeberg.org/gruf/go-structr/runtime.go
@@ -18,7 +18,8 @@ import (
// including memory offset and hash function.
type struct_field struct {
- // mangle ...
+ // struct field type mangling
+ // (i.e. fast serializing) fn.
mangle mangler.Mangler
// zero value data, used when
@@ -81,6 +82,10 @@ func find_field(t xunsafe.TypeIter, names []string) (sfield struct_field, ftype
field reflect.StructField
)
+ // Take reference
+ // of parent iter.
+ o := t
+
for len(names) > 0 {
// Pop next name.
name := pop_name()
@@ -140,23 +145,41 @@ func find_field(t xunsafe.TypeIter, names []string) (sfield struct_field, ftype
// Get mangler from type info.
sfield.mangle = mangler.Get(t)
- // Get field type as zero interface.
- v := reflect.New(t.Type).Elem()
- vi := v.Interface()
-
- // Get argument mangler from iface.
- ti := xunsafe.TypeIterFrom(vi)
- mangleArg := mangler.Get(ti)
-
// Calculate zero value string.
- zptr := xunsafe.UnpackEface(vi)
- zstr := string(mangleArg(nil, zptr))
+ zptr := zero_value_field(o, sfield.offsets)
+ zstr := string(sfield.mangle(nil, zptr))
sfield.zerostr = zstr
sfield.zero = zptr
return
}
+// zero_value ...
+func zero_value(t xunsafe.TypeIter, offsets []next_offset) reflect.Value {
+ v := reflect.New(t.Type).Elem()
+ for _, offset := range offsets {
+ for range offset.derefs {
+ if v.IsNil() {
+ new := reflect.New(v.Type().Elem())
+ v.Set(new)
+ }
+ v = v.Elem()
+ }
+ for i := 0; i < v.NumField(); i++ {
+ if v.Type().Field(i).Offset == offset.offset {
+ v = v.Field(i)
+ break
+ }
+ }
+ }
+ return v
+}
+
+// zero_value_field ...
+func zero_value_field(t xunsafe.TypeIter, offsets []next_offset) unsafe.Pointer {
+ return zero_value(t, offsets).Addr().UnsafePointer()
+}
+
// extract_fields extracts given structfields from the provided value type,
// this is done using predetermined struct field memory offset locations.
func extract_fields(ptr unsafe.Pointer, fields []struct_field) []unsafe.Pointer {