Skip to content

Commit d86944e

Browse files
committed
Track the key of any named group objects.
As part of #380 we allowed names and groups tags/options to co-exist to ultimately support Fx feature request uber-go/fx#998. We now intend to support Map value groups as per uber-go/fx#1036. We will do this in 2 steps. 1. This PR will begin tracking any names passed into value groups with out changing any external facing functionality. 2. a subsequent PR will exploit this structure to support Map value groups.
1 parent d587461 commit d86944e

File tree

6 files changed

+49
-34
lines changed

6 files changed

+49
-34
lines changed

constructor.go

Lines changed: 8 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -181,15 +181,15 @@ func (n *constructorNode) Call(c containerStore) (err error) {
181181
// would be made to a containerWriter and defers them until Commit is called.
182182
type stagingContainerWriter struct {
183183
values map[key]reflect.Value
184-
groups map[key][]reflect.Value
184+
groups map[key][]keyedGroupValue
185185
}
186186

187187
var _ containerWriter = (*stagingContainerWriter)(nil)
188188

189189
func newStagingContainerWriter() *stagingContainerWriter {
190190
return &stagingContainerWriter{
191191
values: make(map[key]reflect.Value),
192-
groups: make(map[key][]reflect.Value),
192+
groups: make(map[key][]keyedGroupValue),
193193
}
194194
}
195195

@@ -201,12 +201,12 @@ func (sr *stagingContainerWriter) setDecoratedValue(_ string, _ reflect.Type, _
201201
digerror.BugPanicf("stagingContainerWriter.setDecoratedValue must never be called")
202202
}
203203

204-
func (sr *stagingContainerWriter) submitGroupedValue(group string, t reflect.Type, v reflect.Value) {
204+
func (sr *stagingContainerWriter) submitGroupedValue(group, mapKey string, t reflect.Type, v reflect.Value) {
205205
k := key{t: t, group: group}
206-
sr.groups[k] = append(sr.groups[k], v)
206+
sr.groups[k] = append(sr.groups[k], keyedGroupValue{key: mapKey, value: v})
207207
}
208208

209-
func (sr *stagingContainerWriter) submitDecoratedGroupedValue(_ string, _ reflect.Type, _ reflect.Value) {
209+
func (sr *stagingContainerWriter) submitDecoratedGroupedValue(_, _ string, _ reflect.Type, _ reflect.Value) {
210210
digerror.BugPanicf("stagingContainerWriter.submitDecoratedGroupedValue must never be called")
211211
}
212212

@@ -216,9 +216,9 @@ func (sr *stagingContainerWriter) Commit(cw containerWriter) {
216216
cw.setValue(k.name, k.t, v)
217217
}
218218

219-
for k, vs := range sr.groups {
220-
for _, v := range vs {
221-
cw.submitGroupedValue(k.group, k.t, v)
219+
for k, kgvs := range sr.groups {
220+
for _, kgv := range kgvs {
221+
cw.submitGroupedValue(k.group, kgv.key, k.t, kgv.value)
222222
}
223223
}
224224
}

container.go

Lines changed: 7 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -81,12 +81,12 @@ type containerWriter interface {
8181
setDecoratedValue(name string, t reflect.Type, v reflect.Value)
8282

8383
// submitGroupedValue submits a value to the value group with the provided
84-
// name.
85-
submitGroupedValue(name string, t reflect.Type, v reflect.Value)
84+
// name and optional map key.
85+
submitGroupedValue(name, mapKey string, t reflect.Type, v reflect.Value)
8686

8787
// submitDecoratedGroupedValue submits a decorated value to the value group
88-
// with the provided name.
89-
submitDecoratedGroupedValue(name string, t reflect.Type, v reflect.Value)
88+
// with the provided name and optional map key.
89+
submitDecoratedGroupedValue(name, mapKey string, t reflect.Type, v reflect.Value)
9090
}
9191

9292
// containerStore provides access to the Container's underlying data store.
@@ -108,7 +108,7 @@ type containerStore interface {
108108
// Retrieves all values for the provided group and type.
109109
//
110110
// The order in which the values are returned is undefined.
111-
getValueGroup(name string, t reflect.Type) []reflect.Value
111+
getValueGroup(name string, t reflect.Type) []keyedGroupValue
112112

113113
// Retrieves all decorated values for the provided group and type, if any.
114114
getDecoratedValueGroup(name string, t reflect.Type) (reflect.Value, bool)
@@ -273,8 +273,8 @@ func (bs byTypeName) Swap(i int, j int) {
273273
bs[i], bs[j] = bs[j], bs[i]
274274
}
275275

276-
func shuffledCopy(rand *rand.Rand, items []reflect.Value) []reflect.Value {
277-
newItems := make([]reflect.Value, len(items))
276+
func shuffledCopy(rand *rand.Rand, items []keyedGroupValue) []keyedGroupValue {
277+
newItems := make([]keyedGroupValue, len(items))
278278
for i, j := range rand.Perm(len(items)) {
279279
newItems[i] = items[j]
280280
}

param.go

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -627,6 +627,7 @@ func (pt paramGroupedSlice) Build(c containerStore) (reflect.Value, error) {
627627
}
628628

629629
// Check if we have decorated values
630+
// qjeremy(how to handle this with maps?)
630631
if decoratedItems, ok := pt.getDecoratedValues(c); ok {
631632
return decoratedItems, nil
632633
}
@@ -645,7 +646,10 @@ func (pt paramGroupedSlice) Build(c containerStore) (reflect.Value, error) {
645646
stores := c.storesToRoot()
646647
result := reflect.MakeSlice(pt.Type, 0, itemCount)
647648
for _, c := range stores {
648-
result = reflect.Append(result, c.getValueGroup(pt.Group, pt.Type.Elem())...)
649+
kgvs := c.getValueGroup(pt.Group, pt.Type.Elem())
650+
for _, kgv := range kgvs {
651+
result = reflect.Append(result, kgv.value)
652+
}
649653
}
650654
return result, nil
651655
}

result.go

Lines changed: 10 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -495,6 +495,9 @@ type resultGrouped struct {
495495
// Name of the group as specified in the `group:".."` tag.
496496
Group string
497497

498+
// Key if a name tag or option was provided, for populating maps
499+
Key string
500+
498501
// Type of value produced.
499502
Type reflect.Type
500503

@@ -531,8 +534,10 @@ func newResultGrouped(f reflect.StructField) (resultGrouped, error) {
531534
if err != nil {
532535
return resultGrouped{}, err
533536
}
537+
name := f.Tag.Get(_nameTag)
534538
rg := resultGrouped{
535539
Group: g.Name,
540+
Key: name,
536541
Flatten: g.Flatten,
537542
Type: f.Type,
538543
}
@@ -557,18 +562,19 @@ func newResultGrouped(f reflect.StructField) (resultGrouped, error) {
557562
func (rt resultGrouped) Extract(cw containerWriter, decorated bool, v reflect.Value) {
558563
// Decorated values are always flattened.
559564
if !decorated && !rt.Flatten {
560-
cw.submitGroupedValue(rt.Group, rt.Type, v)
565+
cw.submitGroupedValue(rt.Group, rt.Key, rt.Type, v)
561566
for _, asType := range rt.As {
562-
cw.submitGroupedValue(rt.Group, asType, v)
567+
cw.submitGroupedValue(rt.Group, rt.Key, asType, v)
563568
}
564569
return
565570
}
566571

567572
if decorated {
568-
cw.submitDecoratedGroupedValue(rt.Group, rt.Type, v)
573+
cw.submitDecoratedGroupedValue(rt.Group, rt.Key, rt.Type, v)
569574
return
570575
}
576+
// it's not possible to provide a key for the flattening case
571577
for i := 0; i < v.Len(); i++ {
572-
cw.submitGroupedValue(rt.Group, rt.Type, v.Index(i))
578+
cw.submitGroupedValue(rt.Group, "", rt.Type, v.Index(i))
573579
}
574580
}

result_test.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -196,7 +196,7 @@ func TestNewResultObject(t *testing.T) {
196196
FieldName: "Writer",
197197
FieldIndex: 1,
198198
Results: []result{
199-
resultGrouped{Group: "writers", Type: typeOfWriter},
199+
resultGrouped{Group: "writers", Key: "writer1", Type: typeOfWriter},
200200
resultSingle{Name: "writer1", Type: typeOfWriter},
201201
},
202202
},

scope.go

Lines changed: 18 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -35,6 +35,11 @@ type ScopeOption interface {
3535
noScopeOption() //yet
3636
}
3737

38+
type keyedGroupValue struct {
39+
key string
40+
value reflect.Value
41+
}
42+
3843
// Scope is a scoped DAG of types and their dependencies.
3944
// A Scope may also have one or more child Scopes that inherit
4045
// from it.
@@ -61,10 +66,10 @@ type Scope struct {
6166
values map[key]reflect.Value
6267

6368
// Values groups that generated directly in the Scope.
64-
groups map[key][]reflect.Value
69+
groups map[key][]keyedGroupValue
6570

6671
// Values groups that generated via decoraters in the Scope.
67-
decoratedGroups map[key]reflect.Value
72+
decoratedGroups map[key]keyedGroupValue
6873

6974
// Source of randomness.
7075
rand *rand.Rand
@@ -98,8 +103,8 @@ func newScope() *Scope {
98103
decorators: make(map[key]*decoratorNode),
99104
values: make(map[key]reflect.Value),
100105
decoratedValues: make(map[key]reflect.Value),
101-
groups: make(map[key][]reflect.Value),
102-
decoratedGroups: make(map[key]reflect.Value),
106+
groups: make(map[key][]keyedGroupValue),
107+
decoratedGroups: make(map[key]keyedGroupValue),
103108
invokerFn: defaultInvoker,
104109
rand: rand.New(rand.NewSource(time.Now().UnixNano())),
105110
}
@@ -190,25 +195,25 @@ func (s *Scope) setDecoratedValue(name string, t reflect.Type, v reflect.Value)
190195
s.decoratedValues[key{name: name, t: t}] = v
191196
}
192197

193-
func (s *Scope) getValueGroup(name string, t reflect.Type) []reflect.Value {
198+
func (s *Scope) getValueGroup(name string, t reflect.Type) []keyedGroupValue {
194199
items := s.groups[key{group: name, t: t}]
195200
// shuffle the list so users don't rely on the ordering of grouped values
196201
return shuffledCopy(s.rand, items)
197202
}
198203

199204
func (s *Scope) getDecoratedValueGroup(name string, t reflect.Type) (reflect.Value, bool) {
200205
items, ok := s.decoratedGroups[key{group: name, t: t}]
201-
return items, ok
206+
return items.value, ok
202207
}
203208

204-
func (s *Scope) submitGroupedValue(name string, t reflect.Type, v reflect.Value) {
209+
func (s *Scope) submitGroupedValue(name, mapKey string, t reflect.Type, v reflect.Value) {
205210
k := key{group: name, t: t}
206-
s.groups[k] = append(s.groups[k], v)
211+
s.groups[k] = append(s.groups[k], keyedGroupValue{key: mapKey, value: v})
207212
}
208213

209-
func (s *Scope) submitDecoratedGroupedValue(name string, t reflect.Type, v reflect.Value) {
214+
func (s *Scope) submitDecoratedGroupedValue(name, mapKey string, t reflect.Type, v reflect.Value) {
210215
k := key{group: name, t: t}
211-
s.decoratedGroups[k] = v
216+
s.decoratedGroups[k] = keyedGroupValue{key: mapKey, value: v}
212217
}
213218

214219
func (s *Scope) getValueProviders(name string, t reflect.Type) []provider {
@@ -310,9 +315,9 @@ func (s *Scope) String() string {
310315
for k, v := range s.values {
311316
fmt.Fprintln(b, "\t", k, "=>", v)
312317
}
313-
for k, vs := range s.groups {
314-
for _, v := range vs {
315-
fmt.Fprintln(b, "\t", k, "=>", v)
318+
for k, kgvs := range s.groups {
319+
for _, kgv := range kgvs {
320+
fmt.Fprintln(b, "\t", k, "=>", kgv.value)
316321
}
317322
}
318323
fmt.Fprintln(b, "}")

0 commit comments

Comments
 (0)