Skip to content

Commit d9233df

Browse files
authored
Merge branch 'main' into feature/INFOPLAT-2884-update-beholder-client-register-endpoint
2 parents 467a693 + 5193010 commit d9233df

File tree

2 files changed

+66
-2
lines changed

2 files changed

+66
-2
lines changed

pkg/capabilities/consensus/ocr3/aggregators/reduce_aggregator.go

Lines changed: 11 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -306,24 +306,33 @@ func (a *reduceAggregator) extractValues(lggr logger.Logger, observations map[oc
306306
// values are then re-wrapped here to handle aggregating against Value types
307307
// which is used for mode aggregation
308308
switch val := val.(type) {
309-
case map[string]interface{}:
309+
case map[string]any:
310310
_, ok := val[aggregationKey]
311311
if !ok {
312312
continue
313313
}
314+
if val[aggregationKey] == nil {
315+
lggr.Warnf("node %d contributed with a nil value under key %s", nodeID, aggregationKey)
316+
continue
317+
}
314318

315319
rewrapped, err := values.Wrap(val[aggregationKey])
316320
if err != nil {
317321
lggr.Warnf("unable to wrap value %s", val[aggregationKey])
318322
continue
319323
}
320324
vals = append(vals, rewrapped)
321-
case []interface{}:
325+
case []any:
322326
i, err := strconv.Atoi(aggregationKey)
323327
if err != nil {
324328
lggr.Warnf("aggregation key %s could not be used to index a list type", aggregationKey)
325329
continue
326330
}
331+
if i >= len(val) {
332+
lggr.Warnf("node %d contributed with an array shorter than index %s", nodeID, aggregationKey)
333+
continue
334+
}
335+
327336
rewrapped, err := values.Wrap(val[i])
328337
if err != nil {
329338
lggr.Warnf("unable to wrap value %s", val[i])

pkg/capabilities/consensus/ocr3/aggregators/reduce_test.go

Lines changed: 55 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -567,6 +567,61 @@ func TestReduceAggregator_Aggregate(t *testing.T) {
567567
},
568568
expectedState: map[string]any{"Price": int64(1)},
569569
},
570+
{
571+
name: "handle nils gracefully",
572+
fields: []aggregators.AggregationField{
573+
{
574+
InputKey: "FeedID",
575+
OutputKey: "FeedID",
576+
Method: "mode",
577+
},
578+
{
579+
InputKey: "BenchmarkPrice",
580+
OutputKey: "Price",
581+
Method: "median",
582+
DeviationString: "10",
583+
DeviationType: "percent",
584+
},
585+
{
586+
InputKey: "Timestamp",
587+
OutputKey: "Timestamp",
588+
Method: "median",
589+
DeviationString: "100",
590+
DeviationType: "absolute",
591+
},
592+
},
593+
extraConfig: map[string]any{},
594+
observationsFactory: func() map[commontypes.OracleID][]values.Value {
595+
mockValue, err := values.WrapMap(map[string]any{
596+
"FeedID": idABytes[:],
597+
"BenchmarkPrice": uint64(100),
598+
"Timestamp": 12341414929,
599+
})
600+
require.NoError(t, err)
601+
mockValueWithNil, err := values.WrapMap(map[string]any{
602+
"FeedID": idABytes[:],
603+
"BenchmarkPrice": uint64(100),
604+
"Timestamp": 12341414929,
605+
})
606+
mockValueWithNil.Underlying["BenchmarkPrice"] = nil // simulate failed wraping of uint64
607+
return map[commontypes.OracleID][]values.Value{1: {mockValue}, 2: {mockValue}, 3: {mockValue}, 4: {mockValueWithNil}}
608+
},
609+
shouldReport: true,
610+
expectedOutcome: map[string]any{
611+
"Reports": []any{
612+
map[string]any{
613+
"FeedID": idABytes[:],
614+
"Timestamp": int64(12341414929),
615+
"Price": uint64(100),
616+
},
617+
},
618+
},
619+
expectedState: map[string]any{
620+
"FeedID": idABytes[:],
621+
"Timestamp": int64(12341414929),
622+
"Price": uint64(100),
623+
},
624+
},
570625
}
571626
for _, tt := range cases {
572627
t.Run(tt.name, func(t *testing.T) {

0 commit comments

Comments
 (0)