增加json数据过滤能力
This commit is contained in:
parent
df4a0a0a39
commit
657b9b21d8
25
define/filter.go
Normal file
25
define/filter.go
Normal file
@ -0,0 +1,25 @@
|
|||||||
|
// Package define ...
|
||||||
|
//
|
||||||
|
// Description : define ...
|
||||||
|
//
|
||||||
|
// Author : go_developer@163.com<白茶清欢>
|
||||||
|
//
|
||||||
|
// Date : 2024-04-07 21:43
|
||||||
|
package define
|
||||||
|
|
||||||
|
import "git.zhangdeman.cn/zhangdeman/data_mask"
|
||||||
|
|
||||||
|
// FilterRule ...
|
||||||
|
//
|
||||||
|
// Author : go_developer@163.com<白茶清欢>
|
||||||
|
//
|
||||||
|
// Date : 21:43 2024/4/7
|
||||||
|
type FilterRule struct {
|
||||||
|
SourceDataPath string `json:"source_data_path"` // 原始数据路径
|
||||||
|
TargetDataPath string `json:"target_data_path"` // 目标数据路径
|
||||||
|
IsRequired bool `json:"is_required"` // 要求字段必须存在
|
||||||
|
AllowNil bool `json:"allow_nil"` // 允许nil值
|
||||||
|
DefaultValue string `json:"default_value"` // 不存在时的默认值
|
||||||
|
Type string `json:"type"` // 数据类型
|
||||||
|
DataMask data_mask.IDataMask `json:"-"` // 数据脱敏策略
|
||||||
|
}
|
158
filter/filter.go
Normal file
158
filter/filter.go
Normal file
@ -0,0 +1,158 @@
|
|||||||
|
// Package filter ...
|
||||||
|
//
|
||||||
|
// Description : filter ...
|
||||||
|
//
|
||||||
|
// Author : go_developer@163.com<白茶清欢>
|
||||||
|
//
|
||||||
|
// Date : 2024-04-07 21:59
|
||||||
|
package filter
|
||||||
|
|
||||||
|
import (
|
||||||
|
"errors"
|
||||||
|
"fmt"
|
||||||
|
"git.zhangdeman.cn/zhangdeman/data_mask/define"
|
||||||
|
"github.com/tidwall/gjson"
|
||||||
|
"github.com/tidwall/sjson"
|
||||||
|
"strings"
|
||||||
|
)
|
||||||
|
|
||||||
|
// Execute 数据转换
|
||||||
|
//
|
||||||
|
// Author : go_developer@163.com<张德满>
|
||||||
|
//
|
||||||
|
// Date : 12:39 2024/3/26
|
||||||
|
func Execute(sourceData string, convertRule []*define.FilterRule) *Transform {
|
||||||
|
sourceData = strings.TrimSpace(sourceData)
|
||||||
|
t := &Transform{
|
||||||
|
sourceData: sourceData,
|
||||||
|
ruleList: convertRule,
|
||||||
|
result: "{}",
|
||||||
|
}
|
||||||
|
return t
|
||||||
|
}
|
||||||
|
|
||||||
|
// Transform 转换
|
||||||
|
//
|
||||||
|
// Author : go_developer@163.com<张德满>
|
||||||
|
//
|
||||||
|
// Date : 10:56 2024/3/27
|
||||||
|
type Transform struct {
|
||||||
|
sourceData string
|
||||||
|
ruleList []*define.FilterRule
|
||||||
|
result string
|
||||||
|
}
|
||||||
|
|
||||||
|
// Execute 执行
|
||||||
|
//
|
||||||
|
// Author : go_developer@163.com<张德满>
|
||||||
|
//
|
||||||
|
// Date : 10:57 2024/3/27
|
||||||
|
func (t *Transform) Execute() error {
|
||||||
|
sourceResult := gjson.Parse(t.sourceData)
|
||||||
|
if !sourceResult.IsObject() {
|
||||||
|
return errors.New("source data is not object")
|
||||||
|
}
|
||||||
|
if err := t.checkRule(); nil != err {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
for _, itemRule := range t.ruleList {
|
||||||
|
if err := t.rewrite(itemRule); nil != err {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
// GetResult 获取处理结果
|
||||||
|
//
|
||||||
|
// Author : go_developer@163.com<张德满>
|
||||||
|
//
|
||||||
|
// Date : 11:32 2024/3/27
|
||||||
|
func (t *Transform) GetResult() string {
|
||||||
|
return t.result
|
||||||
|
}
|
||||||
|
|
||||||
|
// checkRule 校验规则
|
||||||
|
//
|
||||||
|
// Author : go_developer@163.com<张德满>
|
||||||
|
//
|
||||||
|
// Date : 11:18 2024/3/27
|
||||||
|
func (t *Transform) checkRule() error {
|
||||||
|
for _, itemRule := range t.ruleList {
|
||||||
|
itemRule.SourceDataPath = strings.TrimRight(itemRule.SourceDataPath, ".[]")
|
||||||
|
itemRule.TargetDataPath = strings.TrimRight(itemRule.TargetDataPath, ".[]")
|
||||||
|
fromPathArr := strings.Split(itemRule.SourceDataPath, "[]")
|
||||||
|
targetPathArr := strings.Split(itemRule.TargetDataPath, "[]")
|
||||||
|
if len(targetPathArr) > len(fromPathArr) {
|
||||||
|
return errors.New("slice path config invalid : " + itemRule.SourceDataPath + " -> " + itemRule.TargetDataPath)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
// rewrite 数据重写
|
||||||
|
//
|
||||||
|
// Author : go_developer@163.com<张德满>
|
||||||
|
//
|
||||||
|
// Date : 11:25 2024/3/27
|
||||||
|
func (t *Transform) rewrite(rule *define.FilterRule) error {
|
||||||
|
var (
|
||||||
|
err error
|
||||||
|
)
|
||||||
|
|
||||||
|
sourceResult := gjson.Get(t.sourceData, rule.SourceDataPath)
|
||||||
|
if !sourceResult.Exists() {
|
||||||
|
if rule.IsRequired {
|
||||||
|
return errors.New(rule.SourceDataPath + " is not exist, but required")
|
||||||
|
}
|
||||||
|
if strings.Contains(rule.SourceDataPath, "[]") {
|
||||||
|
return t.rewriteForSlice(rule)
|
||||||
|
}
|
||||||
|
if t.result, err = sjson.Set(t.result, rule.TargetDataPath, rule.DefaultValue); nil != err {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
t.result, err = sjson.Set(t.result, rule.TargetDataPath, sourceResult.Value())
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
// rewriteForSlice 数组重写
|
||||||
|
//
|
||||||
|
// Author : go_developer@163.com<张德满>
|
||||||
|
//
|
||||||
|
// Date : 15:22 2024/3/27
|
||||||
|
func (t *Transform) rewriteForSlice(rule *define.FilterRule) error {
|
||||||
|
pathArr := strings.Split(rule.SourceDataPath, ".[].")
|
||||||
|
sliceUnfoldResult := t.unfoldSourceSliceData(t.sourceData, pathArr[0:len(pathArr)-1], nil)
|
||||||
|
targetArr := strings.Split(rule.TargetDataPath, ".[].")
|
||||||
|
for idx, itemRes := range sliceUnfoldResult {
|
||||||
|
t.result, _ = sjson.Set(t.result, fmt.Sprintf("%v.%v.%v", targetArr[0], idx, targetArr[1]), itemRes.Get(pathArr[len(pathArr)-1]).Value())
|
||||||
|
}
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
// unfoldSourceSliceData 展开元数据的数组, 平铺
|
||||||
|
//
|
||||||
|
// Author : go_developer@163.com<张德满>
|
||||||
|
//
|
||||||
|
// Date : 17:39 2024/3/27
|
||||||
|
func (t *Transform) unfoldSourceSliceData(sourceData string, pathList []string, res []gjson.Result) []gjson.Result {
|
||||||
|
if nil == res {
|
||||||
|
res = make([]gjson.Result, 0)
|
||||||
|
}
|
||||||
|
|
||||||
|
arrRes := gjson.Get(sourceData, pathList[0]).Array()
|
||||||
|
if len(pathList) == 1 {
|
||||||
|
for _, itemRes := range arrRes {
|
||||||
|
res = append(res, itemRes)
|
||||||
|
}
|
||||||
|
return res
|
||||||
|
}
|
||||||
|
|
||||||
|
for i := 0; i < len(arrRes)-1; i++ {
|
||||||
|
res = t.unfoldSourceSliceData(arrRes[i].String(), pathList[1:], res)
|
||||||
|
}
|
||||||
|
|
||||||
|
return t.unfoldSourceSliceData(arrRes[len(arrRes)-1].String(), pathList[1:], res)
|
||||||
|
}
|
7
go.mod
7
go.mod
@ -1,3 +1,10 @@
|
|||||||
module git.zhangdeman.cn/zhangdeman/data_mask
|
module git.zhangdeman.cn/zhangdeman/data_mask
|
||||||
|
|
||||||
go 1.21
|
go 1.21
|
||||||
|
|
||||||
|
require (
|
||||||
|
github.com/tidwall/gjson v1.17.1 // indirect
|
||||||
|
github.com/tidwall/match v1.1.1 // indirect
|
||||||
|
github.com/tidwall/pretty v1.2.1 // indirect
|
||||||
|
github.com/tidwall/sjson v1.2.5 // indirect
|
||||||
|
)
|
||||||
|
10
go.sum
Normal file
10
go.sum
Normal file
@ -0,0 +1,10 @@
|
|||||||
|
github.com/tidwall/gjson v1.14.2/go.mod h1:/wbyibRr2FHMks5tjHJ5F8dMZh3AcwJEMf5vlfC0lxk=
|
||||||
|
github.com/tidwall/gjson v1.17.1 h1:wlYEnwqAHgzmhNUFfw7Xalt2JzQvsMx2Se4PcoFCT/U=
|
||||||
|
github.com/tidwall/gjson v1.17.1/go.mod h1:/wbyibRr2FHMks5tjHJ5F8dMZh3AcwJEMf5vlfC0lxk=
|
||||||
|
github.com/tidwall/match v1.1.1 h1:+Ho715JplO36QYgwN9PGYNhgZvoUSc9X2c80KVTi+GA=
|
||||||
|
github.com/tidwall/match v1.1.1/go.mod h1:eRSPERbgtNPcGhD8UCthc6PmLEQXEWd3PRB5JTxsfmM=
|
||||||
|
github.com/tidwall/pretty v1.2.0/go.mod h1:ITEVvHYasfjBbM0u2Pg8T2nJnzm8xPwvNhhsoaGGjNU=
|
||||||
|
github.com/tidwall/pretty v1.2.1 h1:qjsOFOWWQl+N3RsoF5/ssm1pHmJJwhjlSbZ51I6wMl4=
|
||||||
|
github.com/tidwall/pretty v1.2.1/go.mod h1:ITEVvHYasfjBbM0u2Pg8T2nJnzm8xPwvNhhsoaGGjNU=
|
||||||
|
github.com/tidwall/sjson v1.2.5 h1:kLy8mja+1c9jlljvWTlSazM7cKDRfJuR/bOJhcY5NcY=
|
||||||
|
github.com/tidwall/sjson v1.2.5/go.mod h1:Fvgq9kS/6ociJEDnK0Fk1cpYF4FIW6ZF7LAe+6jwd28=
|
@ -1,4 +1,4 @@
|
|||||||
// Package data_mask ...
|
// Package strategy ...
|
||||||
//
|
//
|
||||||
// Description : data_mask ...
|
// Description : data_mask ...
|
||||||
//
|
//
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
// Package data_mask ...
|
// Package strategy ...
|
||||||
//
|
//
|
||||||
// Description : data_mask ...
|
// Description : data_mask ...
|
||||||
//
|
//
|
||||||
|
Loading…
Reference in New Issue
Block a user