An interesting go struct tag expression syntax for field validation, etc.

Overview

go-tagexpr report card GoDoc

An interesting go struct tag expression syntax for field validation, etc.

Usage

  • Validator: A powerful validator that supports struct tag expression

  • Binding: A powerful HTTP request parameters binder that supports struct tag expression

Feature

  • Support for a variety of common operator
  • Support for accessing arrays, slices, members of the dictionary
  • Support access to any field in the current structure
  • Support access to nested fields, non-exported fields, etc.
  • Support registers function expression
  • Built-in len, sprintf, regexp functions
  • Support single mode and multiple mode to define expression
  • Parameter check subpackage
  • Use offset pointers to directly take values, better performance
  • Required go version ≥1.9

Example

=100"` B string `tagexpr:"len($)>1 && regexp('^\\w*$')"` C bool `tagexpr:"expr1:(f.g)$>0 && $; expr2:'C must be true when T.f.g>0'"` d []string `tagexpr:"@:len($)>0 && $[0]=='D'; msg:sprintf('invalid d: %v',$)"` e map[string]int `tagexpr:"len($)==$['len']"` e2 map[string]*int `tagexpr:"len($)==$['len']"` f struct { g int `tagexpr:"$"` } } vm := tagexpr.New("tagexpr") t := &T{ A: 107, B: "abc", C: true, d: []string{"x", "y"}, e: map[string]int{"len": 1}, e2: map[string]*int{"len": new(int)}, f: struct { g int `tagexpr:"$"` }{1}, } tagExpr, err := vm.Run(t) if err != nil { panic(err) } fmt.Println(tagExpr.Eval("A")) fmt.Println(tagExpr.Eval("B")) fmt.Println(tagExpr.Eval("[email protected]")) fmt.Println(tagExpr.Eval("[email protected]")) if !tagExpr.Eval("d").(bool) { fmt.Println(tagExpr.Eval("[email protected]")) } fmt.Println(tagExpr.Eval("e")) fmt.Println(tagExpr.Eval("e2")) fmt.Println(tagExpr.Eval("f.g")) // Output: // true // true // true // C must be true when T.f.g>0 // invalid d: [x y] // true // false // 1 } ">
package tagexpr_test

import (
	"fmt"

	tagexpr "github.com/bytedance/go-tagexpr/v2"
)

func Example() {
	type T struct {
		A  int             `tagexpr:"$<0||$>=100"`
		B  string          `tagexpr:"len($)>1 && regexp('^\\w*$')"`
		C  bool            `tagexpr:"expr1:(f.g)$>0 && $; expr2:'C must be true when T.f.g>0'"`
		d  []string        `tagexpr:"@:len($)>0 && $[0]=='D'; msg:sprintf('invalid d: %v',$)"`
		e  map[string]int  `tagexpr:"len($)==$['len']"`
		e2 map[string]*int `tagexpr:"len($)==$['len']"`
		f  struct {
			g int `tagexpr:"$"`
		}
	}

	vm := tagexpr.New("tagexpr")
	t := &T{
		A:  107,
		B:  "abc",
		C:  true,
		d:  []string{"x", "y"},
		e:  map[string]int{"len": 1},
		e2: map[string]*int{"len": new(int)},
		f: struct {
			g int `tagexpr:"$"`
		}{1},
	}

	tagExpr, err := vm.Run(t)
	if err != nil {
		panic(err)
	}

	fmt.Println(tagExpr.Eval("A"))
	fmt.Println(tagExpr.Eval("B"))
	fmt.Println(tagExpr.Eval("[email protected]"))
	fmt.Println(tagExpr.Eval("[email protected]"))
	if !tagExpr.Eval("d").(bool) {
		fmt.Println(tagExpr.Eval("[email protected]"))
	}
	fmt.Println(tagExpr.Eval("e"))
	fmt.Println(tagExpr.Eval("e2"))
	fmt.Println(tagExpr.Eval("f.g"))

	// Output:
	// true
	// true
	// true
	// C must be true when T.f.g>0
	// invalid d: [x y]
	// true
	// false
	// 1
}

Syntax

Struct tag syntax spec:

type T struct {
	// Single model
    Field1 T1 `tagName:"expression"`
	// Multiple model
    Field2 T2 `tagName:"exprName:expression; [exprName2:expression2;]..."`
	// Omit it
    Field3 T3 `tagName:"-"`
    // Omit it when it is nil
    Field4 T4 `tagName:"?"`
    ...
}

NOTE: The exprName under the same struct field cannot be the same!

Operator or Operand Explain
true false boolean
0 0.0 float64 "0"
'' String
\\' Escape ' delims in string
\" Escape " delims in string
nil nil, undefined
! not
+ Digital addition or string splicing
- Digital subtraction or negative
* Digital multiplication
/ Digital division
% division remainder, as: float64(int64(a)%int64(b))
== eq
!= ne
> gt
>= ge
< lt
<= le
&& Logic and
|| Logic or
() Expression group
(X)$ Struct field value named X
(X.Y)$ Struct field value named X.Y
$ Shorthand for (X)$, omit (X) to indicate current struct field value
(X)$['A'] Map value with key A or struct A sub-field in the struct field X
(X)$[0] The 0th element or sub-field of the struct field X(type: map, slice, array, struct)
len((X)$) Built-in function len, the length of struct field X
mblen((X)$) the length of string field X (character number)
regexp('^\\w*$', (X)$) Regular match the struct field X, return boolean
regexp('^\\w*$') Regular match the current struct field, return boolean
sprintf('X value: %v', (X)$) fmt.Sprintf, format the value of struct field X
range(KvExpr, forEachExpr) Iterate over an array, slice, or dictionary
- #k is the element key var
- #v is the element value var
- ## is the number of elements
- e.g. example

Operator priority(high -> low):

  • () ! bool float64 string nil
  • * / %
  • + -
  • < <= > >=
  • == !=
  • &&
  • ||

Field Selector

field_lv1.field_lv2...field_lvn

Expression Selector

  • If expression is single model or exprName is @:
field_lv1.field_lv2...field_lvn
  • If expression is multiple model and exprName is not @:

Benchmark

goos: darwin
goarch: amd64
pkg: github.com/bytedance/go-tagexpr
BenchmarkTagExpr-4   	10000000	       148 ns/op	      32 B/op	       3 allocs/op
BenchmarkReflect-4   	10000000	       182 ns/op	      16 B/op	       2 allocs/op
PASS

Go to test code

Issues
  • query: 1. how to validate slice elements? 2.how to validate nested struct?

    query: 1. how to validate slice elements? 2.how to validate nested struct?

    I have one question and one improvement suggestion, the scenario is as below:

    AssetListRequestV1 is the request struct

    1. for AssetPlatform field, the validate rule is: all the elements in it should be "1" or "2" or "3" how do I write the validation tag?
    	// asset list request
    	AssetListRequestV1 struct {
    		AssetPlatform   []string
    		AmountLow       float64 `vd:"$>=0"`
    		AmountHigh      float64 `vd:"$>=(AmountLow)$"`
    		AprLow          int     `vd:"$>=0 && $<=100"`
    		AprHigh         int     `vd:"$>=0 && $<=100 && $>=(AprLow)$"`
    		RatingLow       int     `vd:"$>=0 && $<=100"`
    		RatingHigh      int     `vd:"$>=0 && $<=100 && $>=(RatingLow)$"`
    		TradeCreditLow  int     `vd:"$>=0 && $<=100"`
    		TradeCreditHigh int     `vd:"$>=0 && $<=100 && $>=(TradeCreditLow)$"`
    		OrderCond       []OrderCond
    		Page            int `vd:"$>=1"`
    		RowCount        int `vd:"$>=1"`
    	}
    
    	OrderCond struct {
    		OrderField string `vd:"$=='asset_platform' || $=='asset_identifier' || $=='update_ts' || $=='debtor' || $=='amount' || $=='apr' || $=='due_dt' || $=='rating' || $=='trade_credit'"`
    		Order      string `vd:"$=='desc' || $=='asc'"`
    	}
    
    1. OrderCond is the sub field of AssetListRequestV1, although I have write validation tag in its own struct, but it will not check if I wirte code like this
    var vd = validator.New("vd")
    func ListAssetDetail(c *gin.Context) {
    	// get req
    	req := new(AssetListRequestV1)
    	if err := c.Bind(req); err != nil {
    		ResponseErr(c, ErrInvalidParam, err.Error())
    		return
    	}
    
    	// input check
    	if err := vd.Validate(req); err != nil {
    		ResponseErr(c, ErrRequestValidationNotPass, err.Error())
    		return
    	}
    .........
    }
    

    actually, I need to range the nested struct by myself

    var vd = validator.New("vd")
    
    func ListAssetDetail(c *gin.Context) {
    	// get req
    	req := new(AssetListRequestV1)
    	if err := c.Bind(req); err != nil {
    		ResponseErr(c, ErrInvalidParam, err.Error())
    		return
    	}
    
    	// input check
    	if err := vd.Validate(req); err != nil {
    		ResponseErr(c, ErrRequestValidationNotPass, err.Error())
    		return
    	}
    
    	for _, cond := range req.OrderCond {
    		if err := vd.Validate(&cond); err != nil {
    			ResponseErr(c, ErrRequestValidationNotPass, err.Error())
    			return
    		}
    	}
    
    .......
    
    }
    

    I think it can be improved @henrylee2cn

    opened by huahuayu 4
  • 自定义函数的逻辑运算问题

    自定义函数的逻辑运算问题

    type TStruct struct {
    	TOk string `vd:"gt($,'0') && gt($, '1')" json:"t_ok"`
    	//TFail string `vd:"gt($,'0')" json:"t_fail"`
    }
    
    func TInit() {
    	validator.RegFunc("gt", func(args ...interface{}) error {
    		return errors.New("force error")
    	})
    }
    func Test_tagexpr(t *testing.T) {
    	TInit()
    	fmt.Printf("%+v\n", validator.Validate(&TStruct{TOk: "1" /*TFail: "1"*/}))
    }
    

    如上代码 自定义了“gt”函数,TFail字段单独使用gt函数,validate会报错,符合预期; 但是TOk字段,对两个gt函数执行了逻辑运算,validate会通过,不符合预期。

    opened by lileibuaa 3
  • chore(deps): bump github.com/tidwall/gjson from 1.6.0 to 1.9.3

    chore(deps): bump github.com/tidwall/gjson from 1.6.0 to 1.9.3

    ⚠️ Dependabot is rebasing this PR ⚠️

    Rebasing might not happen immediately, so don't worry if this takes some time.

    Note: if you make any changes to this PR yourself, they will take precedence over the rebase.


    Bumps github.com/tidwall/gjson from 1.6.0 to 1.9.3.

    Commits

    Dependabot compatibility score

    Dependabot will resolve any conflicts with this PR as long as you don't alter it yourself. You can also trigger a rebase manually by commenting @dependabot rebase.


    Dependabot commands and options

    You can trigger Dependabot actions by commenting on this PR:

    • @dependabot rebase will rebase this PR
    • @dependabot recreate will recreate this PR, overwriting any edits that have been made to it
    • @dependabot merge will merge this PR after your CI passes on it
    • @dependabot squash and merge will squash and merge this PR after your CI passes on it
    • @dependabot cancel merge will cancel a previously requested merge and block automerging
    • @dependabot reopen will reopen this PR if it is closed
    • @dependabot close will close this PR and stop Dependabot recreating it. You can achieve the same result by closing it manually
    • @dependabot ignore this major version will close this PR and stop Dependabot creating any more for this major version (unless you reopen the PR or upgrade to it yourself)
    • @dependabot ignore this minor version will close this PR and stop Dependabot creating any more for this minor version (unless you reopen the PR or upgrade to it yourself)
    • @dependabot ignore this dependency will close this PR and stop Dependabot creating any more for this dependency (unless you reopen the PR or upgrade to it yourself)
    • @dependabot use these labels will set the current labels as the default for future PRs for this repo and language
    • @dependabot use these reviewers will set the current reviewers as the default for future PRs for this repo and language
    • @dependabot use these assignees will set the current assignees as the default for future PRs for this repo and language
    • @dependabot use this milestone will set the current milestone as the default for future PRs for this repo and language

    You can disable automated security fix PRs for this repo from the Security Alerts page.

    dependencies 
    opened by dependabot[bot] 2
  • 在 vd 的时候 msg 里如果包含单引号会产生不可预料的错误

    在 vd 的时候 msg 里如果包含单引号会产生不可预料的错误

    如在

    `query:"profiling_id" vd:"@:len($)==32; msg:'profiling_id's length is invalid'"`
    

    这样的句子里,msg 里包含的单引号会使整个vd失效而无法产生正确结果; 如果将msg 里的单引号转义 ',会产生一个更奇葩的效果就是服务第一次的验证会成功,而之后的验证都会失效。 以及同学有没有内部的联系方式方便讨论呀?

    opened by zhaobenx 2
  • Custom type supported? Like decimal.

    Custom type supported? Like decimal.

    Test case

    import (
    	"fmt"
    	vd "github.com/bytedance/go-tagexpr/validator"
    	"github.com/shopspring/decimal"
    )
    
    func main() {
    		p := struct {
    			Price decimal.Decimal `vd:"$>0"`
    		}{
    			Price: decimal.NewFromFloat(1.00),
    		}
    		fmt.Println(vd.Validate(p))
    }
    

    would result

    invalid parameter: Price
    
    opened by leopku 2
  • go mod 问题

    go mod 问题

    我把demo copy到本地尝试运行,但是因为go mod 下载包的原因而不不能通过编译,

    我用的是go 12.4 GO111MODULE=on GOPROXY=https://athens.azurefd.net

    tagexpr 使用了包 github.com/henrylee2cn/goutil/tpack 这个包用 go mod tidy 下载不下来

    opened by alpha-baby 2
  • 建议新增CheckAll函数

    建议新增CheckAll函数

    想对一个结构体检查,只要有一个参数不在预期就返回false 伪代码如下

    
     type T struct {
            A  int             `tagexpr:"$<0||$>=100"`
            B  string          `tagexpr:"len($)>1 && regexp('^\\w*$')"`
            C  bool            `tagexpr:"{expr1:(f.g)$>0 && $}{expr2:'C must be true when T.f.g>0'}"`
            d  []string        `tagexpr:"{@:len($)>0 && $[0]=='D'} {msg:sprintf('invalid d: %v',$)}"`
            e  map[string]int  `tagexpr:"len($)==$['len']"`
            e2 map[string]*int `tagexpr:"len($)==$['len']"`
            f  struct {
                g int `tagexpr:"$"`
            }
        }   
    
        vm := tagexpr.New("tagexpr")
        err := vm.WarmUp(new(T))
        if err != nil {
            panic(err)
        }   
    
        t := &T{ 
            A:  107,
            B:  "abc",
            C:  true,
            d:  []string{"x", "y"},
            e:  map[string]int{"len": 1}, 
            e2: map[string]*int{"len": new(int)},
            f: struct {
                g int `tagexpr:"$"`
            }{1},
        }   
    
        tagExpr, err := vm.Run(t)
        if err != nil {
            panic(err)
        }   
    
        // 看我 
        b := tagExpr.CheckAll(t)
        if !b {
            fmt.Printf("invalid argument\n")
        }
    
    
    opened by guonaihong 2
  • 自定义 json-unmarshal 函数设置为实例级别

    自定义 json-unmarshal 函数设置为实例级别

    你好!

    var (
    	jsonUnmarshalFunc func(data []byte, v interface{}) error
    )
    
    // ResetJSONUnmarshaler reset the JSON Unmarshal function.
    // NOTE: verifyingRequired is true if the required tag is supported.
    func ResetJSONUnmarshaler(fn JSONUnmarshaler) {
    	jsonUnmarshalFunc = fn
    }
    

    现在 jsonUnmarshalFunc 是全局变量,ResetJSONUnmarshaler 是全局影响的函数。

    可否将 jsonUnmarshalFunc 绑定到 Binding 结构体上,然后 ResetJSONUnmarshaler 函数,去修改 defaultBinding 实例?

    这样的话,可以控制只影响一个实例的 unmarshal 效果。

    如果可以的话,我可以来提供这个修改。谢谢。

    opened by chyroc 1
  • feat: support stop semantics

    feat: support stop semantics

    close #34

    If a custom function returns ErrStop, the field checks after this field where in the same struct are stopped.

    Update: Use io.ErrUnexpectedEOF in the validator to indicate an error in the validation.

    Hi, since io.EOF is used in validator, I use io.EOF to represent stopping the validation of the current struct fields. Please help to see if this way is possible

    opened by sikasjc 1
  • The json body parameter does not take effect when default tag is set

    The json body parameter does not take effect when default tag is set

    当入参填写了 default tag 并且没有 json tag 的时候,无论 body 中填什么值,都会被 default 值覆盖。 body 入参的定义如下 type GetItemRequest struct { Content string thrift:"Content,1,required" default:"hello" } 此时,curl 请求 curl 'http://localhost:6791?Action=GetItem'
    --header 'Content-Type: application/json'
    --data-raw '{ "Content": "123", }' 后,Content 值依然为 hello

    猜测原因: https://github.com/bytedance/go-tagexpr/blob/873eca54c6826ba829b91e813a5b4681bdd9b41d/binding/bind.go#L169 这个地方先把 body unmarshal 到 Req 中,在没有打 json tag 而只打了 default tag 的情况下,就会执行 https://github.com/bytedance/go-tagexpr/blob/873eca54c6826ba829b91e813a5b4681bdd9b41d/binding/bind.go#L213 从而又把 default 值覆盖到了已有的值中

    opened by xpofei 1
  • panic when map contains nil value

    panic when map contains nil value

    reproduce as code below:

    type MyStruct struct {
    	Data map[string]interface{}
    }
    
    func main() {
    	ms := MyStruct{
    		Data: map[string]interface{}{
    			"a": "111",
    			"b": nil,
    		},
    	}
    	vd := validator.New("vd")
    	err := vd.Validate(ms)
    	fmt.Println(err)
    
    }
    

    stack info:

    panic: runtime error: invalid memory address or nil pointer dereference
    [signal SIGSEGV: segmentation violation code=0x1 addr=0x2 pc=0x101177a]
    
    goroutine 1 [running]:
    reflect.maplen(0x2, 0x15)
            /Users/qujianping/local/go/src/runtime/map.go:1371 +0xa
    reflect.Value.MapKeys(0x13b7ba0, 0xc0000aff20, 0x195, 0x14262ad, 0x1, 0x1426442)
            /Users/qujianping/local/go/src/reflect/value.go:1136 +0x208
    simple/vendor/github.com/bytedance/go-tagexpr.(*TagExpr).Range(0xc00033c0c0, 0xc0002ceb40, 0x5819e00, 0x0)
            /Users/qujianping/local/src/simple/vendor/github.com/bytedance/go-tagexpr/tagexpr.go:792 +0x95c
    simple/vendor/github.com/bytedance/go-tagexpr/validator.(*Validator).Validate.func1(0xc00033c0c0, 0x0, 0x0, 0x15e92e0, 0x13cefc0)
            /Users/qujianping/local/src/simple/vendor/github.com/bytedance/go-tagexpr/validator/validator.go:78 +0x18c
    simple/vendor/github.com/bytedance/go-tagexpr.(*VM).subRunAll(0xc0000aff80, 0x0, 0x0, 0x0, 0x13cefc0, 0xc0000aff20, 0x19, 0xc000163ed8, 0x80, 0x13c73a0)
            /Users/qujianping/local/src/simple/vendor/github.com/bytedance/go-tagexpr/tagexpr.go:160 +0xb46
    simple/vendor/github.com/bytedance/go-tagexpr.(*VM).RunAny(0xc0000aff80, 0x13cefc0, 0xc0000aff20, 0xc000163ed8, 0xc000163ec8, 0x100d509)
            /Users/qujianping/local/src/simple/vendor/github.com/bytedance/go-tagexpr/tagexpr.go:144 +0x82
    simple/vendor/github.com/bytedance/go-tagexpr/validator.(*Validator).Validate(0xc000163f68, 0x13cefc0, 0xc0000aff20, 0x0, 0x0, 0x0, 0xc000163f67, 0x1)
            /Users/qujianping/local/src/simple/vendor/github.com/bytedance/go-tagexpr/validator/validator.go:70 +0x197
    main.main()
            /Users/qujianping/local/src/simple/main.go:21 +0x1b0
    
    opened by qjpcpu 1
  • Supporting different JSON tag

    Supporting different JSON tag

    Hi

    Is it possible to support custom JSON tag for binding data? As sometime for the same data, we will want to support snake case and camel case for the same field.

    Example:

    type Person struct {
    	DateOfBirth string `json:"dateOfBirth" sjson:"date_of_birth"`
    }
    
    opened by odinmarks1988 0
  • binding.Error 和 validator.Error 行为不一致

    binding.Error 和 validator.Error 行为不一致

    当使用msg自定义错误信息时 validator的Error的行为是,如果有自定义错误信息就只返回自定义信息

    // Error implements error interface.
    func (e *Error) Error() string {
    	if e.Msg != "" {
    		return e.Msg
    	}
    	return "invalid parameter: " + e.FailPath
    }
    

    而binding的Error却会有其他附加信息

    func (e *Error) Error() string {
    	if e.Msg != "" {
    		return e.ErrType + ": expr_path=" + e.FailField + ", cause=" + e.Msg
    	}
    	return e.ErrType + ": expr_path=" + e.FailField + ", cause=invalid"
    }
    

    建议,

    1. 两者的行为应该一致。
    2. 可以考虑在e.Msg支持占位符,由用户自己决定想要的错误信息格式。如
    placeholders := map[string]string {"{{ ErrType }}":e.ErrType, "{{ FailField  }}":e..FailField }
    msg := e.Msg
    
    for k, v := range placeholders{
        msg = strings.Replace(msg, k, v)
    }
    
    return msg
    
    opened by XIELongDragon 2
  • Can not build at 32bit OS

    Can not build at 32bit OS

    caused by used package github.com/henrylee2cn/ameda

    15:36:40 # github.com/henrylee2cn/ameda 15:36:40 vendor/github.com/henrylee2cn/ameda/int.go:13:2: constant 9223372036854775807 overflows int 15:36:40 vendor/github.com/henrylee2cn/ameda/uint.go:13:2: constant 18446744073709551615 overflows uint

    opened by CCS-CloudServices 1
  • example improvement suggestion

    example improvement suggestion

    hi, tagexpr is powerful but the examples use so many variables like a b c d, which is not meaningful.
    I suggest using some true scenario of any kind, say: validate an amount, email, phoneno, etc, which is more interesting and demonstrate the idea.

    opened by huahuayu 3
Releases(v2.9.3)
Owner
Bytedance Inc.
Bytedance Inc.
Convert arbitrary formats to Go Struct (including json, toml, yaml, etc.)

go2struct Convert arbitrary formats to Go Struct (including json, toml, yaml, etc.) Installation Run the following command under your project: go get

Afeyer 33 Jun 9, 2022
A Go implementation of the core algorithm in paper

Boolean Expression Indexer Go library A Go implementation of the core algorithm in paper <Indexing Boolean Expression>, which already supports the fol

wangyi 48 May 22, 2022
Exp-tree: go library for parsing expression tree

Vinshop expression tree Exp-tree is go library for parsing expression tree Installation go get -u github.com/vinshop/exp-tree Quick start Format Expre

VinShop 6 May 11, 2022
Golang string comparison and edit distance algorithms library, featuring : Levenshtein, LCS, Hamming, Damerau levenshtein (OSA and Adjacent transpositions algorithms), Jaro-Winkler, Cosine, etc...

Go-edlib : Edit distance and string comparison library Golang string comparison and edit distance algorithms library featuring : Levenshtein, LCS, Ham

Hugo Bollon 331 Jun 29, 2022
Generic types that are missing from Go, including sets, trees, sorted lists, etc.

go-typ Generic types that are missing from Go, including sets, trees, sorted lists, etc. All code is implemented with 0 dependencies and in pure Go co

null 12 Jul 3, 2022
Converts PDF, DOC, DOCX, XML, HTML, RTF, etc to plain text

docconv A Go wrapper library to convert PDF, DOC, DOCX, XML, HTML, RTF, ODT, Pages documents and images (see optional dependencies below) to plain tex

Search.io 962 Jul 5, 2022
A faster method to get elements from an interface (Struct or Slice type) for Go.

A faster method to get elements from an interface (Struct or Slice type) for Go.

karminski-牙医 35 May 13, 2022
Convert json string to Golang struct

json-to-go-cli Convert json string to Golang struct How to install git clone https://github.com/tiancheng92/json-to-go-cli.git cd json-to-go-cli go bu

TianCheng 7 May 10, 2022
GoStruct2Table - format your struct like a table.

GoStruct2Table format your struct like a table. Installing $ go get -u -v github.com/runningzyp/GoStruct2Table Simple Example import parser "github.c

YunpengZhan 9 Jun 14, 2022
An interesting go struct tag expression syntax for field validation, etc.

An interesting go struct tag expression syntax for field validation, etc.

Bytedance Inc. 1.2k Jul 5, 2022
:100:Go Struct and Field validation, including Cross Field, Cross Struct, Map, Slice and Array diving

Package validator Package validator implements value validations for structs and individual fields based on tags. It has the following unique features

Go Playgound 10.8k Jul 6, 2022
💯 Go Struct and Field validation, including Cross Field, Cross Struct, Map, Slice and Array diving

Package validator implements value validations for structs and individual fields based on tags.

Flamego 12 Feb 16, 2022
Golang parameter validation, which can replace go-playground/validator, includes ncluding Cross Field, Map, Slice and Array diving, provides readable,flexible, configurable validation.

Checker 中文版本 Checker is a parameter validation package, can be use in struct/non-struct validation, including cross field validation in struct, elemen

Liang Yaopei 70 Jun 29, 2022
An idiomatic Go (golang) validation package. Supports configurable and extensible validation rules (validators) using normal language constructs instead of error-prone struct tags.

ozzo-validation Description ozzo-validation is a Go package that provides configurable and extensible data validation capabilities. It has the followi

Ozzo Framework 2.8k Jul 1, 2022
Just a playground with some interesting concepts like pipelines aka middleware, handleFuncs, request validations etc. Check it out.

Pipeline a.k.a middleware in Go Just a playground with some interesting concepts like pipelines aka middleware, handleFuncs, request validations etc.

null 0 Dec 9, 2021
Gin Middleware to extract json tag value from playground validator's errors validation

Json Tag Extractor for Go-Playground Validator This is Gin Middleware that aim to extract json tag and than store it to FieldError.Field() object. Ins

Muhamad Surya Iksanudin 0 Jan 14, 2022
☄ The golang convenient converter supports Database to Struct, SQL to Struct, and JSON to Struct.

Gormat - Cross platform gopher tool The golang convenient converter supports Database to Struct, SQL to Struct, and JSON to Struct. 中文说明 Features Data

永林 273 Jul 1, 2022
Go tool to modify struct field tags

Go tool to modify/update field tags in structs. gomodifytags makes it easy to update, add or delete the tags in a struct field. You can easily add new tags, update existing tags (such as appending a new key, i.e: db, xml, etc..) or remove existing tags

Fatih Arslan 1.8k Jul 1, 2022
structslop is a static analyzer for Go that recommends struct field rearrangements to provide for maximum space/allocation efficiency.

structslop Package structslop defines an Analyzer that checks struct can be re-arranged fields to get optimal struct size.

orijtech 653 Jun 24, 2022
Go linter to check the struct literal to use field name

Structfield Find struct literals using non-labeled fields. The structfield analysis reports the usage of struct literal using non-labeled fields more

Nuruddin Ashr 3 Aug 23, 2021
containedctx detects is a linter that detects struct contained context.Context field

containedctx containedctx detects is a linter that detects struct contained context.Context field Instruction go install github.com/sivchari/contained

sivchari 9 Jun 19, 2022
The Slick programming language is an s-expression surface syntax for Go.

The Slick programming language The Slick programming language is a Lisp/Scheme-style s-expression surface syntax for the Go programming language, with

null 124 Jul 5, 2022
Using NFP (Number Format Parser) you can get an Abstract Syntax Tree (AST) from Excel number format expression

NFP (Number Format Parser) Using NFP (Number Format Parser) you can get an Abstract Syntax Tree (AST) from Excel number format expression. Installatio

fossabot 0 Feb 4, 2022
A declarative struct-tag-based HTML unmarshaling or scraping package for Go built on top of the goquery library

goq Example import ( "log" "net/http" "astuart.co/goq" ) // Structured representation for github file name table type example struct { Title str

Andrew Stuart 217 May 30, 2022
dateparse time by struct tag

dateparse_tag dateparse time by struct tag intro&简介 WithTagName() // 自定义你想要使用的tag名称,默认为dateFormat WithDefaultTagValue() // 定义这个tag的默认值,默认为 default Wit

coward 1 Jan 13, 2022
This is a template project to help beginners learn, or to help developers develop some interesting small projects

This is a template project to help beginners learn, or to help developers develop some interesting small projects

null 6 May 24, 2022
Watch for interesting patterns in Caddy logs and send a Telegram notification.

Watch for interesting patterns in Caddy logs and send a Telegram notification.

Heyang Zhou 8 Jan 17, 2022
Struct validation using tags

Govalid Use Govalid to validate structs. Documentation For full documentation see pkg.go.dev. Example package main import ( "fmt" "log" "strings"

Travis Harmon 29 May 14, 2022
Gookit 721 Jun 29, 2022