gf/g/encoding/gjson/gjson.go

232 lines
6.1 KiB
Go
Raw Normal View History

2017-11-23 10:21:28 +08:00
package gjson
import (
"fmt"
2017-11-23 10:21:28 +08:00
"strings"
"strconv"
"io/ioutil"
"encoding/json"
2017-11-23 10:21:28 +08:00
)
// json解析结果存放数组
type Json struct {
// 注意这是一个指针
value *interface{}
}
// 一个json变量
type JsonVar interface{}
// 编码go变量为json字符串并返回json字符串指针
func Encode (v interface{}) ([]byte, error) {
return json.Marshal(v)
2017-11-23 10:21:28 +08:00
}
// 解码字符串为interface{}变量
func Decode (b []byte) (interface{}, error) {
2017-11-23 10:21:28 +08:00
var v interface{}
if err := DecodeTo(b, &v); err == nil {
2017-12-13 17:35:43 +08:00
return nil, err
} else {
return v, nil
2017-11-23 10:21:28 +08:00
}
}
// 解析json字符串为go变量注意第二个参数为指针
func DecodeTo (b []byte, v interface{}) error {
return json.Unmarshal(b, v)
2017-11-23 10:21:28 +08:00
}
// 解析json字符串为gjson.Json对象并返回操作对象指针
func DecodeToJson (b []byte) (*Json, error) {
if v, err := Decode(b); err != nil {
return &Json{&v}, nil
} else {
2017-12-13 17:35:43 +08:00
return nil, err
2017-11-23 10:21:28 +08:00
}
}
// 加载json文件内容并转换为json对象
func Load (path string) (*Json, error) {
data, err := ioutil.ReadFile(path)
if err != nil {
return nil, err
}
var result interface{}
if err := json.Unmarshal(data, &result); err != nil {
return nil, err
}
return &Json{ &result }, nil
}
2017-11-23 10:21:28 +08:00
// 将变量转换为Json对象进行处理该变量至少应当是一个map或者array否者转换没有意义
func NewJson(v *interface{}) *Json {
return &Json{ v }
}
// 将指定的json内容转换为指定结构返回查找失败或者转换失败目标对象转换为nil
// 注意第二个参数需要给的是变量地址
func (p *Json) GetToVar(pattern string, v interface{}) error {
r := p.Get(pattern)
if r != nil {
2017-12-13 17:35:43 +08:00
if t, err := Encode(r); err == nil {
return DecodeTo(t, v)
} else {
return err
}
2017-11-23 10:21:28 +08:00
} else {
v = nil
}
return nil
}
// 获得一个键值对关联数组/哈希表,方便操作,不需要自己做类型转换
// 注意如果获取的值不存在或者类型与json类型不匹配那么将会返回nil
func (p *Json) GetMap(pattern string) map[string]interface{} {
result := p.Get(pattern)
if result != nil {
if r, ok := result.(map[string]interface{}); ok {
return r
}
}
return nil
}
// 将检索值转换为Json对象指针返回
func (p *Json) GetJson(pattern string) *Json {
result := p.Get(pattern)
if result != nil {
return &Json{&result}
}
return nil
}
2017-11-23 10:21:28 +08:00
// 获得一个数组[]interface{},方便操作,不需要自己做类型转换
// 注意如果获取的值不存在或者类型与json类型不匹配那么将会返回nil
func (p *Json) GetArray(pattern string) []interface{} {
result := p.Get(pattern)
if result != nil {
if r, ok := result.([]interface{}); ok {
return r
}
}
return nil
}
// 返回指定json中的string
func (p *Json) GetString(pattern string) string {
result := p.Get(pattern)
if result != nil {
if r, ok := result.(string); ok {
return r
}
}
return ""
}
// 返回指定json中的bool
func (p *Json) GetBool(pattern string) bool {
result := p.Get(pattern)
if result != nil {
str := fmt.Sprintf("%v", result)
if str != "" && str != "0" && str != "false" {
return true
}
}
return false
}
// 返回指定json中的float64
func (p *Json) GetFloat64(pattern string) float64 {
result := p.Get(pattern)
if result != nil {
if r, ok := result.(float64); ok {
return r
}
}
return 0
}
// 返回指定json中的float64->int
func (p *Json) GetInt(pattern string) int {
return int(p.GetFloat64(pattern))
}
// 返回指定json中的float64->int64
func (p *Json) GetInt64(pattern string) int64 {
return int64(p.GetFloat64(pattern))
}
// 根据约定字符串方式访问json解析数据参数形如 "items.name.first", "list.0"
// 返回的结果类型的interface{},因此需要自己做类型转换
// 如果找不到对应节点的数据返回nil
func (p *Json) Get(pattern string) interface{} {
var result interface{}
pointer := p.value
array := strings.Split(pattern, ".")
length := len(array)
for i:= 0; i < length; i++ {
switch (*pointer).(type) {
case map[string]interface{}:
if v, ok := (*pointer).(map[string]interface{})[array[i]]; ok {
if i == length - 1 {
result = v
} else {
pointer = &v
}
} else {
return nil
}
case []interface{}:
if isNumeric(array[i]) {
n, err := strconv.Atoi(array[i])
if err == nil && len((*pointer).([]interface{})) > n {
if i == length - 1 {
result = (*pointer).([]interface{})[n]
break;
} else {
pointer = &(*pointer).([]interface{})[n]
}
}
} else {
return nil
}
default:
return nil
}
}
return result
}
// 转换为map[string]interface{}类型,如果转换失败返回nil
func (p *Json) ToMap() map[string]interface{} {
pointer := p.value
switch (*pointer).(type) {
case map[string]interface{}:
return (*pointer).(map[string]interface{})
default:
return nil
}
}
// 转换为[]interface{}类型,如果转换失败返回nil
func (p *Json) ToArray() []interface{} {
pointer := p.value
switch (*pointer).(type) {
case []interface{}:
return (*pointer).([]interface{})
default:
return nil
}
}
// 判断所给字符串是否为数字
func isNumeric(s string) bool {
for i := 0; i < len(s); i++ {
if s[i] < byte('0') || s[i] > byte('9') {
return false
}
}
return true
}