-
Notifications
You must be signed in to change notification settings - Fork 0
/
example_test.go
146 lines (123 loc) · 3.54 KB
/
example_test.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
package inject_test
import (
"fmt"
"github.com/theplant/inject"
)
// Define interfaces and implementations
type Printer interface {
Print() string
}
type SimplePrinter struct{}
func (p *SimplePrinter) Print() string {
return "Printing document"
}
// New type definition
type DocumentDescription string
type Document struct {
Injector *inject.Injector `inject:""` // Injector will be provided by default, so you can also get it if needed
ID string // Not injected
Description DocumentDescription `inject:""` // Exported non-optional field
Printer Printer `inject:""` // Exported non-optional field
Size int64 `inject:"optional"` // Exported optional field
page int `inject:""` // Unexported non-optional field
name string `inject:"optional"` // Unexported optional field
}
func ExampleInjector() {
inj := inject.New()
// Provide dependencies
if err := inj.Provide(
func() Printer {
return &SimplePrinter{}
},
func() string {
return "A simple string"
},
func() DocumentDescription {
return "A document description"
},
func() int {
return 42
},
); err != nil {
panic(err)
}
{
// Resolve dependencies
var printer Printer
if err := inj.Resolve(&printer); err != nil {
panic(err)
}
fmt.Println("Resolved printer:", printer.Print())
}
printDoc := func(doc *Document) {
fmt.Printf("Document id: %q\n", doc.ID)
fmt.Printf("Document description: %q\n", doc.Description)
fmt.Printf("Document printer: %q\n", doc.Printer.Print())
fmt.Printf("Document size: %d\n", doc.Size)
fmt.Printf("Document page: %d\n", doc.page)
fmt.Printf("Document name: %q\n", doc.name)
}
fmt.Println("-------")
{
// Invoke a function
results, err := inj.Invoke(func(printer Printer) *Document {
return &Document{
// This value will be retained as it is not tagged with `inject`, despite string being provided
ID: "idInvoked",
// This value will be overridden since it is tagged with `inject` and DocumentDescription is provided
Description: "DescriptionInvoked",
// This value will be overridden with the same value since it is tagged with `inject` and Printer is provided
Printer: printer,
// This value will be retained since it is tagged with `inject:"optional"` and int64 is not provided
Size: 100,
}
})
if err != nil {
panic(err)
}
printDoc(results[0].(*Document))
}
fmt.Println("-------")
{
// Apply dependencies to a struct instance
doc := &Document{}
if err := inj.Apply(doc); err != nil {
panic(err)
}
printDoc(doc)
}
fmt.Println("-------")
{
// Create a child injector and then apply dependencies to a struct instance
child := inject.New()
child.SetParent(inj)
doc := &Document{}
if err := child.Apply(doc); err != nil {
panic(err)
}
printDoc(doc)
}
// Output:
// Resolved printer: Printing document
// -------
// Document id: "idInvoked"
// Document description: "A document description"
// Document printer: "Printing document"
// Document size: 100
// Document page: 42
// Document name: "A simple string"
// -------
// Document id: ""
// Document description: "A document description"
// Document printer: "Printing document"
// Document size: 0
// Document page: 42
// Document name: "A simple string"
// -------
// Document id: ""
// Document description: "A document description"
// Document printer: "Printing document"
// Document size: 0
// Document page: 42
// Document name: "A simple string"
}