1/* 2Copyright 2015 The Kubernetes Authors. 3 4Licensed under the Apache License, Version 2.0 (the "License"); 5you may not use this file except in compliance with the License. 6You may obtain a copy of the License at 7 8 http://www.apache.org/licenses/LICENSE-2.0 9 10Unless required by applicable law or agreed to in writing, software 11distributed under the License is distributed on an "AS IS" BASIS, 12WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13See the License for the specific language governing permissions and 14limitations under the License. 15*/ 16 17package jsonpath 18 19import "fmt" 20 21// NodeType identifies the type of a parse tree node. 22type NodeType int 23 24// Type returns itself and provides an easy default implementation 25func (t NodeType) Type() NodeType { 26 return t 27} 28 29func (t NodeType) String() string { 30 return NodeTypeName[t] 31} 32 33const ( 34 NodeText NodeType = iota 35 NodeArray 36 NodeList 37 NodeField 38 NodeIdentifier 39 NodeFilter 40 NodeInt 41 NodeFloat 42 NodeWildcard 43 NodeRecursive 44 NodeUnion 45 NodeBool 46) 47 48var NodeTypeName = map[NodeType]string{ 49 NodeText: "NodeText", 50 NodeArray: "NodeArray", 51 NodeList: "NodeList", 52 NodeField: "NodeField", 53 NodeIdentifier: "NodeIdentifier", 54 NodeFilter: "NodeFilter", 55 NodeInt: "NodeInt", 56 NodeFloat: "NodeFloat", 57 NodeWildcard: "NodeWildcard", 58 NodeRecursive: "NodeRecursive", 59 NodeUnion: "NodeUnion", 60 NodeBool: "NodeBool", 61} 62 63type Node interface { 64 Type() NodeType 65 String() string 66} 67 68// ListNode holds a sequence of nodes. 69type ListNode struct { 70 NodeType 71 Nodes []Node // The element nodes in lexical order. 72} 73 74func newList() *ListNode { 75 return &ListNode{NodeType: NodeList} 76} 77 78func (l *ListNode) append(n Node) { 79 l.Nodes = append(l.Nodes, n) 80} 81 82func (l *ListNode) String() string { 83 return l.Type().String() 84} 85 86// TextNode holds plain text. 87type TextNode struct { 88 NodeType 89 Text string // The text; may span newlines. 90} 91 92func newText(text string) *TextNode { 93 return &TextNode{NodeType: NodeText, Text: text} 94} 95 96func (t *TextNode) String() string { 97 return fmt.Sprintf("%s: %s", t.Type(), t.Text) 98} 99 100// FieldNode holds field of struct 101type FieldNode struct { 102 NodeType 103 Value string 104} 105 106func newField(value string) *FieldNode { 107 return &FieldNode{NodeType: NodeField, Value: value} 108} 109 110func (f *FieldNode) String() string { 111 return fmt.Sprintf("%s: %s", f.Type(), f.Value) 112} 113 114// IdentifierNode holds an identifier 115type IdentifierNode struct { 116 NodeType 117 Name string 118} 119 120func newIdentifier(value string) *IdentifierNode { 121 return &IdentifierNode{ 122 NodeType: NodeIdentifier, 123 Name: value, 124 } 125} 126 127func (f *IdentifierNode) String() string { 128 return fmt.Sprintf("%s: %s", f.Type(), f.Name) 129} 130 131// ParamsEntry holds param information for ArrayNode 132type ParamsEntry struct { 133 Value int 134 Known bool // whether the value is known when parse it 135 Derived bool 136} 137 138// ArrayNode holds start, end, step information for array index selection 139type ArrayNode struct { 140 NodeType 141 Params [3]ParamsEntry // start, end, step 142} 143 144func newArray(params [3]ParamsEntry) *ArrayNode { 145 return &ArrayNode{ 146 NodeType: NodeArray, 147 Params: params, 148 } 149} 150 151func (a *ArrayNode) String() string { 152 return fmt.Sprintf("%s: %v", a.Type(), a.Params) 153} 154 155// FilterNode holds operand and operator information for filter 156type FilterNode struct { 157 NodeType 158 Left *ListNode 159 Right *ListNode 160 Operator string 161} 162 163func newFilter(left, right *ListNode, operator string) *FilterNode { 164 return &FilterNode{ 165 NodeType: NodeFilter, 166 Left: left, 167 Right: right, 168 Operator: operator, 169 } 170} 171 172func (f *FilterNode) String() string { 173 return fmt.Sprintf("%s: %s %s %s", f.Type(), f.Left, f.Operator, f.Right) 174} 175 176// IntNode holds integer value 177type IntNode struct { 178 NodeType 179 Value int 180} 181 182func newInt(num int) *IntNode { 183 return &IntNode{NodeType: NodeInt, Value: num} 184} 185 186func (i *IntNode) String() string { 187 return fmt.Sprintf("%s: %d", i.Type(), i.Value) 188} 189 190// FloatNode holds float value 191type FloatNode struct { 192 NodeType 193 Value float64 194} 195 196func newFloat(num float64) *FloatNode { 197 return &FloatNode{NodeType: NodeFloat, Value: num} 198} 199 200func (i *FloatNode) String() string { 201 return fmt.Sprintf("%s: %f", i.Type(), i.Value) 202} 203 204// WildcardNode means a wildcard 205type WildcardNode struct { 206 NodeType 207} 208 209func newWildcard() *WildcardNode { 210 return &WildcardNode{NodeType: NodeWildcard} 211} 212 213func (i *WildcardNode) String() string { 214 return i.Type().String() 215} 216 217// RecursiveNode means a recursive descent operator 218type RecursiveNode struct { 219 NodeType 220} 221 222func newRecursive() *RecursiveNode { 223 return &RecursiveNode{NodeType: NodeRecursive} 224} 225 226func (r *RecursiveNode) String() string { 227 return r.Type().String() 228} 229 230// UnionNode is union of ListNode 231type UnionNode struct { 232 NodeType 233 Nodes []*ListNode 234} 235 236func newUnion(nodes []*ListNode) *UnionNode { 237 return &UnionNode{NodeType: NodeUnion, Nodes: nodes} 238} 239 240func (u *UnionNode) String() string { 241 return u.Type().String() 242} 243 244// BoolNode holds bool value 245type BoolNode struct { 246 NodeType 247 Value bool 248} 249 250func newBool(value bool) *BoolNode { 251 return &BoolNode{NodeType: NodeBool, Value: value} 252} 253 254func (b *BoolNode) String() string { 255 return fmt.Sprintf("%s: %t", b.Type(), b.Value) 256} 257