• Home
  • History
  • Annotate
Name Date Size #Lines LOC

..03-May-2022-

testdata/H26-Jan-2018-1210

.gitignoreH A D26-Jan-2018492 3426

.travis.ymlH A D26-Jan-2018200 87

CODE_OF_CONDUCT.mdH A D26-Jan-20183.1 KiB4728

LICENSEH A D26-Jan-20181.5 KiB2925

README.mdH A D26-Jan-20187.9 KiB220170

doc.goH A D26-Jan-2018978 451

issue17_test.goH A D26-Jan-2018556 2622

issue23_test.goH A D26-Jan-2018541 2824

issue33_test.goH A D26-Jan-2018911 3427

issue38_test.goH A D26-Jan-20181.4 KiB6051

issue50_test.goH A D26-Jan-2018227 1915

issue52_test.goH A D26-Jan-20182.3 KiB10090

map.goH A D26-Jan-20185.2 KiB175134

merge.goH A D26-Jan-20186 KiB220179

merge_test.goH A D26-Jan-20181 KiB5143

mergo.goH A D26-Jan-20182.7 KiB9367

mergo_test.goH A D26-Jan-201815.8 KiB728652

README.md

1# Mergo
2
3A helper to merge structs and maps in Golang. Useful for configuration default values, avoiding messy if-statements.
4
5Also a lovely [comune](http://en.wikipedia.org/wiki/Mergo) (municipality) in the Province of Ancona in the Italian region of Marche.
6
7## Status
8
9It is ready for production use. [It is used in several projects by Docker, Google, The Linux Foundation, VMWare, Shopify, etc](https://github.com/imdario/mergo#mergo-in-the-wild).
10
11[![GoDoc][3]][4]
12[![GoCard][5]][6]
13[![Build Status][1]][2]
14[![Coverage Status][7]][8]
15[![Sourcegraph][9]][10]
16
17[1]: https://travis-ci.org/imdario/mergo.png
18[2]: https://travis-ci.org/imdario/mergo
19[3]: https://godoc.org/github.com/imdario/mergo?status.svg
20[4]: https://godoc.org/github.com/imdario/mergo
21[5]: https://goreportcard.com/badge/imdario/mergo
22[6]: https://goreportcard.com/report/github.com/imdario/mergo
23[7]: https://coveralls.io/repos/github/imdario/mergo/badge.svg?branch=master
24[8]: https://coveralls.io/github/imdario/mergo?branch=master
25[9]: https://sourcegraph.com/github.com/imdario/mergo/-/badge.svg
26[10]: https://sourcegraph.com/github.com/imdario/mergo?badge
27
28### Latest release
29
30[Release 0.3.2](https://github.com/imdario/mergo/releases/tag/0.3.2) is an important release because it changes `Merge()`and `Map()` signatures to support [transformers](#transformers). An optional/variadic argument has been added, so it won't break existing code.
31
32### Important note
33
34If you were using Mergo **before** April 6th 2015, please check your project works as intended after updating your local copy with ```go get -u github.com/imdario/mergo```. I apologize for any issue caused by its previous behavior and any future bug that Mergo could cause (I hope it won't!) in existing projects after the change (release 0.2.0).
35
36### Donations
37
38If Mergo is useful to you, consider buying me a coffe, a beer or making a monthly donation so I can keep building great free software. :heart_eyes:
39
40<a href='https://ko-fi.com/B0B58839' target='_blank'><img height='36' style='border:0px;height:36px;' src='https://az743702.vo.msecnd.net/cdn/kofi1.png?v=0' border='0' alt='Buy Me a Coffee at ko-fi.com' /></a>
41[![Beerpay](https://beerpay.io/imdario/mergo/badge.svg)](https://beerpay.io/imdario/mergo)
42[![Beerpay](https://beerpay.io/imdario/mergo/make-wish.svg)](https://beerpay.io/imdario/mergo)
43<a href="https://liberapay.com/dario/donate"><img alt="Donate using Liberapay" src="https://liberapay.com/assets/widgets/donate.svg"></a>
44
45### Mergo in the wild
46
47- [moby/moby](https://github.com/moby/moby)
48- [kubernetes/kubernetes](https://github.com/kubernetes/kubernetes)
49- [vmware/dispatch](https://github.com/vmware/dispatch)
50- [Shopify/themekit](https://github.com/Shopify/themekit)
51- [imdario/zas](https://github.com/imdario/zas)
52- [matcornic/hermes](https://github.com/matcornic/hermes)
53- [OpenBazaar/openbazaar-go](https://github.com/OpenBazaar/openbazaar-go)
54- [kataras/iris](https://github.com/kataras/iris)
55- [michaelsauter/crane](https://github.com/michaelsauter/crane)
56- [go-task/task](https://github.com/go-task/task)
57- [sensu/uchiwa](https://github.com/sensu/uchiwa)
58- [ory/hydra](https://github.com/ory/hydra)
59- [sisatech/vcli](https://github.com/sisatech/vcli)
60- [dairycart/dairycart](https://github.com/dairycart/dairycart)
61- [projectcalico/felix](https://github.com/projectcalico/felix)
62- [resin-os/balena](https://github.com/resin-os/balena)
63- [go-kivik/kivik](https://github.com/go-kivik/kivik)
64- [Telefonica/govice](https://github.com/Telefonica/govice)
65- [supergiant/supergiant](supergiant/supergiant)
66- [SergeyTsalkov/brooce](https://github.com/SergeyTsalkov/brooce)
67- [soniah/dnsmadeeasy](https://github.com/soniah/dnsmadeeasy)
68- [ohsu-comp-bio/funnel](https://github.com/ohsu-comp-bio/funnel)
69- [EagerIO/Stout](https://github.com/EagerIO/Stout)
70- [lynndylanhurley/defsynth-api](https://github.com/lynndylanhurley/defsynth-api)
71- [russross/canvasassignments](https://github.com/russross/canvasassignments)
72- [rdegges/cryptly-api](https://github.com/rdegges/cryptly-api)
73- [casualjim/exeggutor](https://github.com/casualjim/exeggutor)
74- [divshot/gitling](https://github.com/divshot/gitling)
75- [RWJMurphy/gorl](https://github.com/RWJMurphy/gorl)
76- [andrerocker/deploy42](https://github.com/andrerocker/deploy42)
77- [elwinar/rambler](https://github.com/elwinar/rambler)
78- [tmaiaroto/gopartman](https://github.com/tmaiaroto/gopartman)
79- [jfbus/impressionist](https://github.com/jfbus/impressionist)
80- [Jmeyering/zealot](https://github.com/Jmeyering/zealot)
81- [godep-migrator/rigger-host](https://github.com/godep-migrator/rigger-host)
82- [Dronevery/MultiwaySwitch-Go](https://github.com/Dronevery/MultiwaySwitch-Go)
83- [thoas/picfit](https://github.com/thoas/picfit)
84- [mantasmatelis/whooplist-server](https://github.com/mantasmatelis/whooplist-server)
85- [jnuthong/item_search](https://github.com/jnuthong/item_search)
86- [bukalapak/snowboard](https://github.com/bukalapak/snowboard)
87
88## Installation
89
90    go get github.com/imdario/mergo
91
92    // use in your .go code
93    import (
94        "github.com/imdario/mergo"
95    )
96
97## Usage
98
99You can only merge same-type structs with exported fields initialized as zero value of their type and same-types maps. Mergo won't merge unexported (private) fields but will do recursively any exported one. Also maps will be merged recursively except for structs inside maps (because they are not addressable using Go reflection).
100
101```go
102if err := mergo.Merge(&dst, src); err != nil {
103    // ...
104}
105```
106
107Also, you can merge overwriting values using the transformer `WithOverride`.
108
109```go
110if err := mergo.Merge(&dst, src, WithOverride); err != nil {
111    // ...
112}
113```
114
115Additionally, you can map a `map[string]interface{}` to a struct (and otherwise, from struct to map), following the same restrictions as in `Merge()`. Keys are capitalized to find each corresponding exported field.
116
117```go
118if err := mergo.Map(&dst, srcMap); err != nil {
119    // ...
120}
121```
122
123Warning: if you map a struct to map, it won't do it recursively. Don't expect Mergo to map struct members of your struct as `map[string]interface{}`. They will be just assigned as values.
124
125More information and examples in [godoc documentation](http://godoc.org/github.com/imdario/mergo).
126
127### Nice example
128
129```go
130package main
131
132import (
133	"fmt"
134	"github.com/imdario/mergo"
135)
136
137type Foo struct {
138	A string
139	B int64
140}
141
142func main() {
143	src := Foo{
144		A: "one",
145		B: 2,
146	}
147	dest := Foo{
148		A: "two",
149	}
150	mergo.Merge(&dest, src)
151	fmt.Println(dest)
152	// Will print
153	// {two 2}
154}
155```
156
157Note: if test are failing due missing package, please execute:
158
159    go get gopkg.in/yaml.v2
160
161### Transformers
162
163Transformers allow to merge specific types differently than in the default behavior. In other words, now you can customize how some types are merged. For example, `time.Time` is a struct; it doesn't have zero value but IsZero can return true because it has fields with zero value. How can we merge a non-zero `time.Time`?
164
165```go
166package main
167
168import (
169	"fmt"
170        "reflect"
171        "time"
172)
173
174type timeTransfomer struct {
175}
176
177func (t timeTransfomer) Transformer(typ reflect.Type) func(dst, src reflect.Value) error {
178	if typ == reflect.TypeOf(time.Time{}) {
179		return func(dst, src reflect.Value) error {
180			if dst.CanSet() {
181				isZero := dst.MethodByName("IsZero")
182				result := isZero.Call([]reflect.Value{})
183				if result[0].Bool() {
184					dst.Set(src)
185				}
186			}
187			return nil
188		}
189	}
190	return nil
191}
192
193type Snapshot struct {
194	Time time.Time
195	// ...
196}
197
198func main() {
199	src := Snapshot{time.Now()}
200	dest := Snapshot{}
201	mergo.Merge(&dest, src, WithTransformers(timeTransfomer{}))
202	fmt.Println(dest)
203	// Will print
204	// { 2018-01-12 01:15:00 +0000 UTC m=+0.000000001 }
205}
206```
207
208
209## Contact me
210
211If I can help you, you have an idea or you are using Mergo in your projects, don't hesitate to drop me a line (or a pull request): [@im_dario](https://twitter.com/im_dario)
212
213## About
214
215Written by [Dario Castañé](http://dario.im).
216
217## License
218
219[BSD 3-Clause](http://opensource.org/licenses/BSD-3-Clause) license, as [Go language](http://golang.org/LICENSE).
220