SoFunction
Updated on 2025-03-01

Detailed explanation of the structure codec artifact Mapstructure library in golang

1: Introduction

In short: mapstructure is a codec tool for converting between a GO dictionary (map[string]interface{}) and a Go structure.

Core method: (input interface{}, output interface{})

Two: Installation

go get /mitchellh/mapstructure

Source code address:/mitchellh/mapstructure

Official document address://mitchellh/mapstructure

Three: Use

3.1: Simple use cases

Case: parse a JSON string into a dictionary object, and then bind the dictionary to a structure object.

package main
import (
	"encoding/json"
	"fmt"
	"/mitchellh/mapstructure"
	"log"
)
type Person struct {
	Name string
	Age  int
	Job  string
}
func main() {
	// Define a JSON string	dataJson :=
		`{
		  "name":"renshanwen",
		  "age":18,
		  "job": "engineer"
		}`
	// Parsing JOSN strings into dictionary	var m map[string]interface{}
	err := ([]byte(dataJson), &m)
	if err != nil {
		(err)
	}
	//Bind structure m into structure object p	var p Person
	(m, &p)
	("name is %s, age is %d, job is %s.", , , )
}

Output result:

name is renshanwen, age is 18, job is engineer.

3.2: Field tags

Field tag function: defines the field mapping relationship between Go dictionary and GO structure.

Default: mapstruct uses the name of the field in the structure (case insensitive) to make this map.

Case: For example, our structure has a Name field. When mapstructure decodes, it will look for the key name in map[string]interface{}.

Specify the relationship map:

package main
import (
	"encoding/json"
	"fmt"
	"/mitchellh/mapstructure"
	"log"
)
type Person struct {
	Name string `mapstructure:"user_name"`
	Age  int    `mapstructure:"user_age"`
	Job  string `mapstructure:"user_job"`
}
func main() {
	// Define a JSON string	dataJson :=
		`{
		  "user_name":"renshanwen",
		  "user_age":18,
		  "user_job": "engineer"
		}`
	// Parses JSON string into structure	var m map[string]interface{}
	err := ([]byte(dataJson), &m)
	if err != nil {
		(err)
	}
	//Bind structure m into structure object p	var p Person
	(m, &p)
	("name is %s, age is %d, job is %s.", , , )
}

3.3: Structural nesting

If the JSON structure in the parameter is relatively complex, multiple structures can be defined, and mapstructure will automatically help us parse.

package main
import (
	"encoding/json"
	"fmt"
	"/mitchellh/mapstructure"
	"log"
)
type Person struct {
	Name string `mapstructure:"user_name"`
	Age  int    `mapstructure:"user_age"`
	Job  string `mapstructure:"user_job"`
}
// Worker structure nestingtype Worker struct {
	Person Person
	Work   string `mapstructure:"user_work"`
}
func main() {
	// Define a JSON string	dataJson := `{
					"person":{
						"user_name":"renshanwen",
						"user_age":18,
						"user_job":"engineer"
					},
					"user_work":"code"
				}`
	// Parses JSON string into structure	var m map[string]interface{}
	err := ([]byte(dataJson), &m)
	if err != nil {
		(err)
	}
	// Bind structure m to structure object w	var w Worker
	(m, &w)
	("name is %s, age is %d, job is %s ,work is %s.", , , , )
}

3.4: Unified storage of unmapped values

You can define a field to receive all unmapdated fields.

Case:

package main
import (
	"encoding/json"
	"fmt"
	"/mitchellh/mapstructure"
	"log"
)
type Person struct {
	Name string `mapstructure:"user_name"`
	Age  int    `mapstructure:"user_age"`
	Job  string `mapstructure:"user_job"`
}
// Worker structure nestingtype Worker struct {
	Person Person
	Work   string                 `mapstructure:"user_work"`
	Other  map[string]interface{} `mapstructure:",remain"` // Unparsed fields are assigned here by default}
func main() {
	// Define a JSON string	dataJson := `{
					"person":{
						"user_name":"renshanwen",
						"user_age":18,
						"user_job":"engineer"
					},
					"user_work":"code",
					"user_mather": "mather",
					"user_baby": "baby"
				}`
	// Parses JSON string into structure	var m map[string]interface{}
	err := ([]byte(dataJson), &m)
	if err != nil {
		(err)
	}
	// Bind structure m to structure object w	var w Worker
	(m, &w)
	("name is %s, age is %d, job is %s ,work is %s other is %s.", , , , , )
}

result:

name is renshanwen, age is 18, job is engineer ,work is code other is map[user_baby:baby user_mather:mather].

3.5: Reverse conversion

Structure—> Dictionary

In reverse decoding, we can set mapstructure: ",omitempty" for certain fields. This way, when these fields are default values, they will not appear in the map[string]interface{} of the structure.

package main
import (
	"encoding/json"
	"fmt"
	"/mitchellh/mapstructure"
)
type Person struct {
	Name string `mapstructure:"user_name"`
	Age  int    `mapstructure:"user_age"`
	Job  string `mapstructure:"user_job,omitempty"` // ,omitempty means that if the structure object does not exist, it will not be parsed into the dictionary.}
// Worker structure nestingtype Worker struct {
	Person Person
	Work   string                 `mapstructure:"user_work"`
	Other  map[string]interface{} `mapstructure:",remain"` // Unparsed fields are assigned here by default}
func main() {
	// Define a JSON string	worker := &Worker{
		Work: "code",
	}
	 = "renshanwen"
	 = 18
	var m map[string]interface{}
	(worker, &m)
	data, _ := (m)
	(string(data))
	// {"Other":null,"Person":{"user_age":18,"user_name":"renshanwen"},"user_work":"code"}
}

3.6: Collect binding information

It can be used to store binding information.

Keys: The binding was successful

Unused: No bound

Unset: Missing

package main
import (
	"fmt"
	"/mitchellh/mapstructure"
)
type Person struct {
	Name string `mapstructure:"user_name"`
	Age  int    `mapstructure:"user_age"`
	Job  string `mapstructure:"user_job,omitempty"` // ,omitempty means that if the structure object does not exist, it will not be parsed into the dictionary.}
func main() {
	m := map[string]interface{}{
		"user_name": "renshanwen",
		"age":       18,
		"job":       "engineer",
	}
	var p Person
	var metadata 
	(m, &p, &metadata)
	("keys:%#v unused:%#v Unset:%#v \n", , , )
	// 	keys:[]string{"user_name"} unused:[]string{"age", "job"} Unset:[]string{"user_age", "user_job"} 
}

The above is a detailed explanation of the detailed content of the Mapstructure library, a structure codec artifact in golang. For more information about go Mapstructure, please follow my other related articles!