...

Source file src/edge-infra.dev/pkg/sds/display/k8s/apis/v2/displayconfig_merge_transformers.go

Documentation: edge-infra.dev/pkg/sds/display/k8s/apis/v2

     1  package v2
     2  
     3  import (
     4  	"reflect"
     5  
     6  	"dario.cat/mergo"
     7  )
     8  
     9  var t = newMultiTransformer(
    10  	newIgnoreAttributesTransformer(ignoreTypes...),
    11  	newOnlyDereferenceStructTransformer(),
    12  	newInputDeviceMappingsTransformer(),
    13  )
    14  
    15  type multiTransformer struct {
    16  	transformers []mergo.Transformers
    17  }
    18  
    19  func newMultiTransformer(transformers ...mergo.Transformers) mergo.Transformers {
    20  	return multiTransformer{
    21  		transformers: transformers,
    22  	}
    23  }
    24  
    25  // Iterates through each transformer with the given type, returning the
    26  // first transformer function that is not nil.
    27  func (t multiTransformer) Transformer(typ reflect.Type) func(base, overlay reflect.Value) error {
    28  	for _, transformer := range t.transformers {
    29  		if f := transformer.Transformer(typ); f != nil {
    30  			return f
    31  		}
    32  	}
    33  	return nil
    34  }
    35  
    36  type ignoreAttributesTransformer struct {
    37  	ignoredTypes []reflect.Type
    38  }
    39  
    40  func newIgnoreAttributesTransformer(ignoredTypes ...reflect.Type) mergo.Transformers {
    41  	return ignoreAttributesTransformer{
    42  		ignoredTypes: ignoredTypes,
    43  	}
    44  }
    45  
    46  // For attributes of types we want to ignore return a transformer
    47  // function that does nothing, making the merge for that type a no-op.
    48  func (t ignoreAttributesTransformer) Transformer(typ reflect.Type) func(base, overlay reflect.Value) error {
    49  	for _, ignoreType := range t.ignoredTypes {
    50  		if typ == ignoreType || typ == reflect.PointerTo(ignoreType) {
    51  			return func(_, _ reflect.Value) error {
    52  				return nil
    53  			}
    54  		}
    55  	}
    56  	return nil
    57  }
    58  
    59  type onlyDereferenceStructTransformer struct{}
    60  
    61  func newOnlyDereferenceStructTransformer() mergo.Transformers {
    62  	return onlyDereferenceStructTransformer{}
    63  }
    64  
    65  // Always override non-struct pointers as we want 'empty' values such
    66  // as boolean false and integer 0 to be respected during the merge.
    67  func (t onlyDereferenceStructTransformer) Transformer(typ reflect.Type) func(base, overlay reflect.Value) error {
    68  	if typ.Kind() == reflect.Pointer {
    69  		if typ.Elem().Kind() == reflect.Struct {
    70  			return nil
    71  		}
    72  		return func(base, overlay reflect.Value) error {
    73  			if !overlay.IsNil() {
    74  				base.Set(overlay)
    75  			}
    76  			return nil
    77  		}
    78  	}
    79  	return nil
    80  }
    81  
    82  type inputDeviceMappingsTransformer struct{}
    83  
    84  func newInputDeviceMappingsTransformer() mergo.Transformers {
    85  	return inputDeviceMappingsTransformer{}
    86  }
    87  
    88  // Allows input device mappings to be overridden by merging with
    89  // empty slice. Sets input device mappings to nil the the overlay
    90  // slice is empty, otherwise uses the merged mappings.
    91  func (t inputDeviceMappingsTransformer) Transformer(typ reflect.Type) func(base, overlay reflect.Value) error {
    92  	if typ == reflect.TypeOf([]InputDeviceName{}) {
    93  		return func(base, overlay reflect.Value) error {
    94  			if overlay.Len() == 0 {
    95  				var nilSlice []InputDeviceName
    96  				overlay = reflect.ValueOf(nilSlice)
    97  			}
    98  			base.Set(overlay)
    99  			return nil
   100  		}
   101  	}
   102  	return nil
   103  }
   104  

View as plain text