Documentation
¶
Overview ¶
Package sheriff transforms structs into a map based on specific tags on the struct fields. A typical use is an API which marshals structs into JSON and maintains different API versions. Using sheriff, struct fields can be annotated with API version and group tags. By invoking sheriff with specific options, those tags determine whether a field will be added to the output map or not. It can then be marshalled using "encoding/json".
Example ¶
package main import ( "encoding/json" "fmt" "log" "github.com/hashicorp/go-version" "github.com/liip/sheriff/v2" ) type User struct { Username string `json:"username" groups:"api"` Email string `json:"email" groups:"personal"` Name string `json:"name" groups:"api"` Roles []string `json:"roles" groups:"api" since:"2"` } type UserList []User func MarshalUsers(version *version.Version, groups []string, users UserList) ([]byte, error) { o := &sheriff.Options{ Groups: groups, ApiVersion: version, } data, err := sheriff.Marshal(o, users) if err != nil { return nil, err } return json.MarshalIndent(data, "", " ") } func main() { users := UserList{ User{ Username: "alice", Email: "alice@example.org", Name: "Alice", Roles: []string{"user", "admin"}, }, User{ Username: "bob", Email: "bob@example.org", Name: "Bob", Roles: []string{"user"}, }, } v1, err := version.NewVersion("1.0.0") if err != nil { log.Panic(err) } v2, err := version.NewVersion("2.0.0") if err != nil { log.Panic(err) } output, err := MarshalUsers(v1, []string{"api"}, users) if err != nil { log.Panic(err) } fmt.Println("Version 1 output:") fmt.Printf("%s\n\n", output) output, err = MarshalUsers(v2, []string{"api"}, users) if err != nil { log.Panic(err) } fmt.Println("Version 2 output:") fmt.Printf("%s\n\n", output) output, err = MarshalUsers(v2, []string{"api", "personal"}, users) if err != nil { log.Panic(err) } fmt.Println("Version 2 output with personal group too:") fmt.Printf("%s\n\n", output) }
Output: Version 1 output: [ { "name": "Alice", "username": "alice" }, { "name": "Bob", "username": "bob" } ] Version 2 output: [ { "name": "Alice", "roles": [ "user", "admin" ], "username": "alice" }, { "name": "Bob", "roles": [ "user" ], "username": "bob" } ] Version 2 output with personal group too: [ { "email": "alice@example.org", "name": "Alice", "roles": [ "user", "admin" ], "username": "alice" }, { "email": "bob@example.org", "name": "Bob", "roles": [ "user" ], "username": "bob" } ]
Index ¶
Examples ¶
Constants ¶
This section is empty.
Variables ¶
This section is empty.
Functions ¶
func Marshal ¶
Marshal encodes the passed data into a map which can be used to pass to json.Marshal().
If the passed argument `data` is a struct, the return value will be of type `map[string]interface{}`. In all other cases we can't derive the type in a meaningful way and is therefore an `interface{}`.
Types ¶
type FieldFilter ¶
type FieldFilter func(field reflect.StructField) (bool, error)
A FieldFilter is a function that decides whether a field should be marshalled or not. If it returns true, the field will be marshalled, otherwise it will be skipped.
type KVStore ¶
A KVStore is a simple key-value store. The default implementation uses a map[string]interface{}. This is fast, however will lead to inconsistent ordering of the keys in the generated JSON. A custom implementation can be used to maintain the order of the keys.
type MarshalInvalidTypeError ¶
type MarshalInvalidTypeError struct {
// contains filtered or unexported fields
}
MarshalInvalidTypeError is an error returned to indicate the wrong type has been passed to Marshal.
func (MarshalInvalidTypeError) Error ¶
func (e MarshalInvalidTypeError) Error() string
type Marshaller ¶
Marshaller is the interface models have to implement in order to conform to marshalling.
type Options ¶
type Options struct { // The FieldFilter makes the decision whether a field should be marshalled or not. // It receives the reflect.StructField of the field and should return true if the field should be included. // If this is not set then the default FieldFilter will be used, which uses the Groups and ApiVersion fields. // Setting this value will result in the other options being ignored. FieldFilter FieldFilter // Groups determine which fields are getting marshalled based on the groups tag. // A field with multiple groups (comma-separated) will result in marshalling of that // field if one of their groups is specified. Groups []string // ApiVersion sets the API version to use when marshalling. // The tags `since` and `until` use the API version setting. // Specifying the API version as "1.0.0" and having an until setting of "2" // will result in the field being marshalled. // Specifying a since setting of "2" with the same API version specified, // will not marshal the field. ApiVersion *version.Version // IncludeEmptyTag determines whether a field without the // `groups` tag should be marshalled ot not. // This option is false by default. IncludeEmptyTag bool // The KVStoreFactory is a function that returns a new KVStore. // The default implementation uses a map[string]interface{}, which is fast but does not maintain the order of the // keys. // A custom implementation can be used to maintain the order of the keys, i.e. using github.com/wk8/go-ordered-map KVStoreFactory func() KVStore // contains filtered or unexported fields }
Options determine which struct fields are being added to the output map.