mirror of
https://github.com/mikefarah/yq.git
synced 2024-12-19 20:19:04 +00:00
Delete now works with deep splat
This commit is contained in:
parent
b9e304e7a4
commit
71f5f76213
@ -100,6 +100,29 @@ b:
|
||||
test.AssertResult(t, expectedOutput, result.Output)
|
||||
}
|
||||
|
||||
func TestDeleteDeepSplatArrayYaml(t *testing.T) {
|
||||
content := `thing: 123
|
||||
b:
|
||||
hi:
|
||||
- thing: item1
|
||||
name: fred
|
||||
`
|
||||
filename := test.WriteTempYamlFile(content)
|
||||
defer test.RemoveTempYamlFile(filename)
|
||||
|
||||
cmd := getRootCommand()
|
||||
result := test.RunCmd(cmd, fmt.Sprintf("delete %s **.thing", filename))
|
||||
if result.Error != nil {
|
||||
t.Error(result.Error)
|
||||
}
|
||||
|
||||
expectedOutput := `b:
|
||||
hi:
|
||||
- name: fred
|
||||
`
|
||||
test.AssertResult(t, expectedOutput, result.Output)
|
||||
}
|
||||
|
||||
func TestDeleteSplatPrefixYaml(t *testing.T) {
|
||||
content := `a: 2
|
||||
b:
|
||||
|
@ -24,6 +24,7 @@ func NewDataNavigator(NavigationStrategy NavigationStrategy) DataNavigator {
|
||||
func (n *navigator) Traverse(value *yaml.Node, path []interface{}) error {
|
||||
realValue := value
|
||||
emptyArray := make([]interface{}, 0)
|
||||
log.Debugf("Traversing path %v", pathStackToString(path))
|
||||
if realValue.Kind == yaml.DocumentNode {
|
||||
log.Debugf("its a document! returning the first child")
|
||||
return n.doTraverse(value.Content[0], "", path, emptyArray)
|
||||
@ -68,6 +69,16 @@ func (n *navigator) getOrReplace(original *yaml.Node, expectedKind yaml.Kind) *y
|
||||
|
||||
func (n *navigator) recurse(value *yaml.Node, head interface{}, tail []interface{}, pathStack []interface{}) error {
|
||||
log.Debug("recursing, processing %v, pathStack %v", head, pathStackToString(pathStack))
|
||||
|
||||
nodeContext := NewNodeContext(value, head, tail, pathStack)
|
||||
|
||||
if head == "**" && !n.navigationStrategy.ShouldOnlyDeeplyVisitLeaves(nodeContext) {
|
||||
errorVisitingDeeply := n.navigationStrategy.Visit(nodeContext)
|
||||
if errorVisitingDeeply != nil {
|
||||
return errorVisitingDeeply
|
||||
}
|
||||
}
|
||||
|
||||
switch value.Kind {
|
||||
case yaml.MappingNode:
|
||||
log.Debug("its a map with %v entries", len(value.Content)/2)
|
||||
@ -85,20 +96,20 @@ func (n *navigator) recurse(value *yaml.Node, head interface{}, tail []interface
|
||||
if head == "+" {
|
||||
return n.appendArray(value, head, tail, pathStack)
|
||||
} else if len(value.Content) == 0 && head == "**" {
|
||||
return n.navigationStrategy.Visit(NewNodeContext(value, head, tail, pathStack))
|
||||
return n.navigationStrategy.Visit(nodeContext)
|
||||
}
|
||||
return n.splatArray(value, head, tail, pathStack)
|
||||
}
|
||||
case yaml.AliasNode:
|
||||
log.Debug("its an alias!")
|
||||
DebugNode(value.Alias)
|
||||
if n.navigationStrategy.FollowAlias(NewNodeContext(value, head, tail, pathStack)) {
|
||||
if n.navigationStrategy.FollowAlias(nodeContext) {
|
||||
log.Debug("following the alias")
|
||||
return n.recurse(value.Alias, head, tail, pathStack)
|
||||
}
|
||||
return nil
|
||||
default:
|
||||
return n.navigationStrategy.Visit(NewNodeContext(value, head, tail, pathStack))
|
||||
return n.navigationStrategy.Visit(nodeContext)
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -18,9 +18,12 @@ func DeleteNavigationStrategy(pathElementToDelete interface{}) NavigationStrateg
|
||||
shouldDeeplyTraverse: func(nodeContext NodeContext) bool {
|
||||
return true
|
||||
},
|
||||
shouldOnlyDeeplyVisitLeaves: func(nodeContext NodeContext) bool {
|
||||
return false
|
||||
},
|
||||
visit: func(nodeContext NodeContext) error {
|
||||
node := nodeContext.Node
|
||||
log.Debug("need to find and delete %v in here", pathElementToDelete)
|
||||
log.Debug("need to find and delete %v in here (%v)", pathElementToDelete, pathStackToString(nodeContext.PathStack))
|
||||
DebugNode(node)
|
||||
if node.Kind == yaml.SequenceNode {
|
||||
newContent := deleteFromArray(parser, node.Content, nodeContext.PathStack, pathElementToDelete)
|
||||
|
@ -35,19 +35,22 @@ type NavigationStrategy interface {
|
||||
// we use it to match against the pathExpression in head.
|
||||
ShouldTraverse(nodeContext NodeContext, nodeKey string) bool
|
||||
ShouldDeeplyTraverse(nodeContext NodeContext) bool
|
||||
// when deeply traversing, should we visit all matching nodes, or just leaves?
|
||||
ShouldOnlyDeeplyVisitLeaves(NodeContext) bool
|
||||
GetVisitedNodes() []*NodeContext
|
||||
DebugVisitedNodes()
|
||||
GetPathParser() PathParser
|
||||
}
|
||||
|
||||
type NavigationStrategyImpl struct {
|
||||
followAlias func(nodeContext NodeContext) bool
|
||||
autoCreateMap func(nodeContext NodeContext) bool
|
||||
visit func(nodeContext NodeContext) error
|
||||
shouldVisitExtraFn func(nodeContext NodeContext) bool
|
||||
shouldDeeplyTraverse func(nodeContext NodeContext) bool
|
||||
visitedNodes []*NodeContext
|
||||
pathParser PathParser
|
||||
followAlias func(nodeContext NodeContext) bool
|
||||
autoCreateMap func(nodeContext NodeContext) bool
|
||||
visit func(nodeContext NodeContext) error
|
||||
shouldVisitExtraFn func(nodeContext NodeContext) bool
|
||||
shouldDeeplyTraverse func(nodeContext NodeContext) bool
|
||||
shouldOnlyDeeplyVisitLeaves func(nodeContext NodeContext) bool
|
||||
visitedNodes []*NodeContext
|
||||
pathParser PathParser
|
||||
}
|
||||
|
||||
func (ns *NavigationStrategyImpl) GetPathParser() PathParser {
|
||||
@ -70,6 +73,10 @@ func (ns *NavigationStrategyImpl) ShouldDeeplyTraverse(nodeContext NodeContext)
|
||||
return ns.shouldDeeplyTraverse(nodeContext)
|
||||
}
|
||||
|
||||
func (ns *NavigationStrategyImpl) ShouldOnlyDeeplyVisitLeaves(nodeContext NodeContext) bool {
|
||||
return ns.shouldOnlyDeeplyVisitLeaves(nodeContext)
|
||||
}
|
||||
|
||||
func (ns *NavigationStrategyImpl) ShouldTraverse(nodeContext NodeContext, nodeKey string) bool {
|
||||
// we should traverse aliases (if enabled), but not visit them :/
|
||||
if len(nodeContext.PathStack) == 0 {
|
||||
|
@ -26,5 +26,8 @@ func ReadNavigationStrategy(deeplyTraverseArrays bool) NavigationStrategy {
|
||||
}
|
||||
return deeplyTraverseArrays || !isInArray
|
||||
},
|
||||
shouldOnlyDeeplyVisitLeaves: func(nodeContext NodeContext) bool {
|
||||
return true
|
||||
},
|
||||
}
|
||||
}
|
||||
|
@ -13,6 +13,9 @@ func UpdateNavigationStrategy(updateCommand UpdateCommand, autoCreate bool) Navi
|
||||
shouldDeeplyTraverse: func(nodeContext NodeContext) bool {
|
||||
return true
|
||||
},
|
||||
shouldOnlyDeeplyVisitLeaves: func(nodeContext NodeContext) bool {
|
||||
return true
|
||||
},
|
||||
visit: func(nodeContext NodeContext) error {
|
||||
node := nodeContext.Node
|
||||
changesToApply := updateCommand.Value
|
||||
|
Loading…
Reference in New Issue
Block a user