// ------------------------------------------------------------------------ // 🚀 Project active3 // 🔗 Active Thing (activething.com) git.activething.com/go // // File name gfield.go // ✍️ Created by DEV // 📅 Modified 09/05/2024 // // 🔒 Copyright 2024 activething.com // // 📜 LICENSE -------------------------------------------------------------- // Licensed under the Apache License, Version 2.0 (the "License"); // you may not use this file except in compliance with the License. // You may obtain a copy of the License at // // http://www.apache.org/licenses/LICENSE-2.0 // // Unless required by applicable law or agreed to in writing, software // distributed under the License is distributed on an "AS IS" BASIS, // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. // See the License for the specific language governing permissions and // limitations under the License. // ------------------------------------------------------------------------ package flds import ( "blds" "encoding/base64" "fmt" "reflect" "strconv" "time" ) type ( GField [T any] struct { valuer[T] kind Kind name string } ) func NewGField [T any] (name string, kind Kind, value T) *GField[T] { return &GField[T]{ name : name, kind : kind, valuer: makeValueValuer[T](value) }} func NewGDField[T any] (name string, kind Kind, valueFn func() T) *GField[T] { return &GField[T]{ name : name, kind : kind|KindDefer, valuer: makeDeferValuer[T](valueFn) }} func NewGDOField [T any] (name string, kind Kind, valueFn func() T) *GField[T] { return &GField[T]{ name : name, kind : kind|KindDeferOnce, valuer: newOnceValuer[T](valueFn) }} func (f GField[T]) Name() string { return f.name } func (f GField[T]) Kind() Kind { return f.kind } func (f GField[T]) ValueBool() bool { if f.kind.IsBool() { return (f.Value()).(bool) } if f.kind.IsAny() { if v,ok := (f.Value()).(bool); ok { return v } } panic(G.ErrInvalidRequest) } func (f GField[T]) ValueString() string { if f.kind.IsString() { return (f.Value()).(string) } if f.kind.IsAny() { if v,ok := (f.Value()).(string); ok { return v } } panic(G.ErrInvalidRequest) } func (f GField[T]) ValueBinary() []byte { if f.kind.IsBinary() { return (f.Value()).([]byte) } if f.kind.IsAny() { if v,ok := (f.Value()).([]byte); ok { return v } } panic(G.ErrInvalidRequest) } func (f GField[T]) ValueInt() int { if f.kind.IsInt() { return (f.Value()).(int) } if f.kind.IsAny() { switch t := f.Value().(type) { case int : return t case int8 : return int(t) case int16: return int(t) case int32: return int(t) case int64: return int(t) } } panic(G.ErrInvalidRequest) } func (f GField[T]) ValueUint() uint { if f.kind.IsUint() { return (f.Value()).(uint) } if f.kind.IsAny() { switch t := f.Value().(type) { case uint : return t case uint8 : return uint(t) case uint16 : return uint(t) case uint32 : return uint(t) case uint64 : return uint(t) case uintptr: return uint(t) } } panic(G.ErrInvalidRequest) } func (f GField[T]) ValueFloat() float64 { if f.kind.IsFloat() { return f.Value().(float64) } if f.kind.IsAny() { if v,ok := f.Value().(float32); ok { return float64(v) } } panic(G.ErrInvalidRequest) } func (f GField[T]) ValueTime() time.Time { if f.kind.IsTime() { return f.Value().(time.Time) } if f.kind.IsAny() { if v,ok := (f.Value()).(time.Time); ok { return v } } panic(G.ErrInvalidRequest) } func (f GField[T]) ValueDuration() time.Duration { if f.kind.IsDuration() { return f.Value().(time.Duration) } if f.kind.IsAny() { if v,ok := f.Value().(time.Duration); ok { return v } } panic(G.ErrInvalidRequest) } func (f GField[T]) ValueError() error { if f.kind.IsError() { return f.Value().(error) } if f.kind.IsAny() { if v,ok := f.Value().(error); ok { return v } } panic(G.ErrInvalidRequest) } func (f GField[T]) ValueReflect() reflect.Value { if f.kind.IsReflect() { return f.Value().(reflect.Value) } if f.kind.IsAny() { if v,ok := f.Value().(reflect.Value); ok { return v } } panic(G.ErrInvalidRequest) } func (f GField[T]) Append(dest []byte) []byte { v := f.Value() switch f.Kind() { case KindString : return append (dest,[]byte(v.(string))...) case KindBool : return strconv.AppendBool (dest,v.(bool)) case KindInt : return strconv.AppendInt (dest,int64(v.(int)),10) case KindUint : return strconv.AppendUint (dest,uint64(v.(uint)),10) case KindFloat : return strconv.AppendFloat(dest,v.(float64),'f',-1,64) case KindDuration: return strconv.AppendInt (dest,(f.Value()).(int64),10) case KindTime : return append (dest,[]byte((v.(time.Time)).String())...) case KindError : return append (dest,[]byte(v.(error).Error())...) case KindBinary : return append (dest,[]byte(base64.StdEncoding.EncodeToString(v.([]byte)))...) case KindReflect : return append (dest,fmt.Sprintf("%#v",v)...) default: if ap,is := v.(interface{ Append([]byte) []byte }); is { return ap.Append(dest) } return append (dest,fmt.Sprintf("%#v",v)...) } } func (f GField[T]) Build (builder blds.Builder) { builder.Object(func(obuilder blds.ObjectBuilder){ f.BuildField(obuilder) }) } func (f GField[T]) BuildField (obuilder blds.ObjectBuilder) { vb := obuilder.field(f.name) switch f.Kind() { case KindAny : case KindBool : vb.Bool (f.Value().(bool)) case KindBinary : vb.Binary (f.Value().([]byte)) case KindString : vb.String (f.Value().(string)) case KindInt : vb.Int (f.Value().(int)) case KindUint : vb.Uint (f.Value().(uint)) case KindFloat : vb.Float64 (f.Value().(float64)) case KindTime : vb.Time (f.Value().(time.Time)) case KindDuration: vb.Duration(f.Value().(time.Duration)) case KindError : vb.Error (f.Value().(error)) case KindReflect : vb.Reflect (f.Value().(reflect.Value)) default: vb.Any(f.Value()) } }