mirror of
https://github.com/kubernetes-sigs/kustomize.git
synced 2026-06-12 01:14:22 +00:00
72 lines
2.0 KiB
Go
72 lines
2.0 KiB
Go
// Copyright 2019 The Kubernetes Authors.
|
|
// SPDX-License-Identifier: Apache-2.0
|
|
|
|
package merge2
|
|
|
|
import (
|
|
"fmt"
|
|
|
|
"sigs.k8s.io/kustomize/kyaml/yaml"
|
|
)
|
|
|
|
// A strategic merge patch directive.
|
|
// See https://github.com/kubernetes/community/blob/master/contributors/devel/sig-api-machinery/strategic-merge-patch.md
|
|
//
|
|
//go:generate stringer -type=smpDirective -linecomment
|
|
type smpDirective int
|
|
|
|
const (
|
|
smpUnknown smpDirective = iota // unknown
|
|
smpReplace // replace
|
|
smpDelete // delete
|
|
smpMerge // merge
|
|
)
|
|
|
|
const strategicMergePatchDirectiveKey = "$patch"
|
|
|
|
// Examine patch for a strategic merge patch directive.
|
|
// If found, return it, and remove the directive from the patch.
|
|
func determineSmpDirective(patch *yaml.RNode) (smpDirective, error) {
|
|
if patch == nil {
|
|
return smpMerge, nil
|
|
}
|
|
switch patch.YNode().Kind {
|
|
case yaml.SequenceNode:
|
|
return determineSequenceNodePatchStrategy(patch)
|
|
case yaml.MappingNode:
|
|
return determineMappingNodePatchStrategy(patch)
|
|
default:
|
|
return smpUnknown, fmt.Errorf(
|
|
"no implemented strategic merge patch strategy for '%s' ('%s')",
|
|
patch.YNode().ShortTag(), patch.MustString())
|
|
}
|
|
}
|
|
|
|
// TODO: what should this do?
|
|
func determineSequenceNodePatchStrategy(_ *yaml.RNode) (smpDirective, error) {
|
|
return smpMerge, nil
|
|
}
|
|
|
|
func determineMappingNodePatchStrategy(patch *yaml.RNode) (smpDirective, error) {
|
|
node, err := patch.Pipe(yaml.Get(strategicMergePatchDirectiveKey))
|
|
if err != nil || node == nil || node.YNode() == nil {
|
|
return smpMerge, nil
|
|
}
|
|
v := node.YNode().Value
|
|
if v == smpDelete.String() {
|
|
return smpDelete, elidePatchDirective(patch)
|
|
}
|
|
if v == smpReplace.String() {
|
|
return smpReplace, elidePatchDirective(patch)
|
|
}
|
|
if v == smpMerge.String() {
|
|
return smpMerge, elidePatchDirective(patch)
|
|
}
|
|
return smpUnknown, fmt.Errorf(
|
|
"unknown patch strategy '%s'", v)
|
|
}
|
|
|
|
func elidePatchDirective(patch *yaml.RNode) error {
|
|
return patch.PipeE(yaml.Clear(strategicMergePatchDirectiveKey))
|
|
}
|