// ------------------------------------------------------------------------ // 🚀 Project active3 // 🔗 Active Thing (activething.com) git.activething.com/go // // File name active.go // ✍️ Created by DEV // 📅 Modified 10/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 pkjson import ( "apack" "cdcs/cjson" "encoding" "encoding/json" "reflect" "strconv" "sync" "time" ) type stringify interface{ String() string } const ( sep byte = ',' fsep byte = ':' ) var ( g = struct { stringifyType reflect.Type jsonMarshalerType reflect.Type textMarshalerType reflect.Type keyStringer *keyStringer packersCache sync.Map } { stringifyType : reflect.TypeOf((*stringify)(nil)).Elem(), jsonMarshalerType: reflect.TypeOf((*json.Marshaler)(nil)).Elem(), textMarshalerType: reflect.TypeOf((*encoding.TextMarshaler)(nil)).Elem(), keyStringer : newKeyStringer(func(s *keyStringer){ // Registramos los tipos conocidos fnI := func(e *rMapEntry, k reflect.Value) error { e.k = strconv.FormatInt(k.Int(), 10) return nil } s.stringers[reflect.TypeOf(int (0))]=fnI s.stringers[reflect.TypeOf(int8 (0))]=fnI s.stringers[reflect.TypeOf(int16 (0))]=fnI s.stringers[reflect.TypeOf(int32 (0))]=fnI s.stringers[reflect.TypeOf(int64 (0))]=fnI fnU := func(e *rMapEntry, k reflect.Value) error { e.k = strconv.FormatUint(k.Uint(), 10) return nil } s.stringers[reflect.TypeOf(uint (0))]=fnU s.stringers[reflect.TypeOf(uint8 (0))]=fnU s.stringers[reflect.TypeOf(uint16 (0))]=fnU s.stringers[reflect.TypeOf(uint32 (0))]=fnU s.stringers[reflect.TypeOf(uint64 (0))]=fnU s.stringers[reflect.TypeOf(uintptr(0))]=fnU s.stringers[reflect.TypeOf(false)]= func(e *rMapEntry, k reflect.Value) error { e.k = strconv.FormatBool(k.Bool()) return nil } s.stringers[reflect.TypeOf(float64(0))]=func(e *rMapEntry, k reflect.Value) error { e.k = cjson.JSONFloat(k.Float(),64) return nil } s.stringers[reflect.TypeOf(float32(0))]=func(e *rMapEntry, k reflect.Value) error { e.k = cjson.JSONFloat(k.Float(), 32) return nil } s.stringers[reflect.TypeOf(time.Time{})]=func(e *rMapEntry, r reflect.Value) error { e.k = (r.Interface().(time.Time)).String() return nil } s.stringers[reflect.TypeOf(time.Duration(0))]=func(e *rMapEntry, r reflect.Value) error { e.k = strconv.FormatInt(r.Int(), 10) return nil } // Registramos los ifaceCheckers conocido que pueden convertir su valor en clave s.RegInterfaceChecker( // Stringify Check func(r reflect.Type) rMapEntryFnc { if r.Implements(reflect.TypeOf((*stringify)(nil)).Elem()) { return func(e *rMapEntry, v reflect.Value) error { if v.Kind() == reflect.Pointer && v.IsNil() { return nil } e.k = (v.Interface().(stringify)).String() e.f = apack.FlagScapeHTML return nil } } return nil }, // Text Marshaller func(r reflect.Type) rMapEntryFnc { if r.Implements(reflect.TypeOf((*encoding.TextMarshaler)(nil)).Elem()) { return func(e *rMapEntry, v reflect.Value) error { if v.Kind() == reflect.Pointer && v.IsNil() { return nil } bf, er := v.Interface().(encoding.TextMarshaler).MarshalText() if er != nil { return er } e.k = string(bf) e.f = apack.FlagScapeHTML return nil } } return nil }) }), } )