parser.go 18 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748
  1. // Copyright 2019 Yunion
  2. //
  3. // Licensed under the Apache License, Version 2.0 (the "License");
  4. // you may not use this file except in compliance with the License.
  5. // You may obtain a copy of the License at
  6. //
  7. // http://www.apache.org/licenses/LICENSE-2.0
  8. //
  9. // Unless required by applicable law or agreed to in writing, software
  10. // distributed under the License is distributed on an "AS IS" BASIS,
  11. // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  12. // See the License for the specific language governing permissions and
  13. // limitations under the License.
  14. package conditionparser
  15. import (
  16. "fmt"
  17. "go/ast"
  18. "go/parser"
  19. "go/token"
  20. "reflect"
  21. "strconv"
  22. "strings"
  23. "yunion.io/x/jsonutils"
  24. "yunion.io/x/pkg/errors"
  25. "yunion.io/x/pkg/utils"
  26. )
  27. var (
  28. ErrInvalidOp = errors.Error("invalid operation")
  29. ErrFieldNotFound = errors.Error("field not found")
  30. ErrOutOfIndex = errors.Error("out of index")
  31. ErrFuncArgument = errors.Error("invalid function arguments")
  32. ErrMethodNotFound = errors.Error("method not found")
  33. )
  34. func IsValid(exprStr string) bool {
  35. _, err := parser.ParseExpr(exprStr)
  36. if err != nil {
  37. return false
  38. }
  39. return true
  40. }
  41. func EvalString(exprStr string, input interface{}) (string, error) {
  42. if len(exprStr) == 0 {
  43. return "", nil
  44. }
  45. expr, err := parser.ParseExpr(exprStr)
  46. if err != nil {
  47. return "", errors.Wrapf(err, "parse expr %s error", exprStr)
  48. }
  49. result, err := eval(expr, input)
  50. if err != nil {
  51. return "", errors.Wrap(err, "eval")
  52. }
  53. switch strVal := result.(type) {
  54. case string:
  55. return strVal, nil
  56. case *jsonutils.JSONString:
  57. return strVal.GetString()
  58. default:
  59. return fmt.Sprintf("%s", strVal), nil
  60. }
  61. }
  62. func EvalBool(exprStr string, input interface{}) (bool, error) {
  63. if len(exprStr) == 0 {
  64. return true, nil
  65. }
  66. expr, err := parser.ParseExpr(exprStr)
  67. if err != nil {
  68. return false, errors.Wrapf(err, "parse expr %s", exprStr)
  69. }
  70. result, err := eval(expr, input)
  71. if err != nil {
  72. return false, errors.Wrap(err, "eval")
  73. }
  74. switch bVal := result.(type) {
  75. case bool:
  76. return bVal, nil
  77. case *jsonutils.JSONBool:
  78. return bVal.Bool()
  79. case []interface{}, *jsonutils.JSONArray:
  80. arrX := getArray(result)
  81. for i := 0; i < len(arrX); i += 1 {
  82. val := getBool(arrX[i])
  83. if val {
  84. return true, nil
  85. }
  86. }
  87. }
  88. return false, nil
  89. }
  90. func eval(expr ast.Expr, input interface{}) (interface{}, error) {
  91. switch expr.(type) {
  92. case *ast.BinaryExpr:
  93. v, err := evalBinary(expr.(*ast.BinaryExpr), input)
  94. if err != nil {
  95. return nil, errors.Wrap(err, "evalBinary")
  96. }
  97. return v, nil
  98. case *ast.UnaryExpr:
  99. v, err := evalUnary(expr.(*ast.UnaryExpr), input)
  100. if err != nil {
  101. return nil, errors.Wrap(err, "evalUnary")
  102. }
  103. return v, nil
  104. case *ast.SelectorExpr:
  105. v, err := evalSelector(expr.(*ast.SelectorExpr), input)
  106. if err != nil {
  107. return nil, errors.Wrap(err, "evalSelector")
  108. }
  109. return v, nil
  110. case *ast.Ident:
  111. v, err := evalIdent(expr.(*ast.Ident), input)
  112. if err != nil {
  113. return nil, errors.Wrap(err, "evalIdent")
  114. }
  115. return v, nil
  116. case *ast.ParenExpr:
  117. v, err := evalParen(expr.(*ast.ParenExpr), input)
  118. if err != nil {
  119. return nil, errors.Wrap(err, "evalParen")
  120. }
  121. return v, nil
  122. case *ast.CallExpr:
  123. v, err := evalCall(expr.(*ast.CallExpr), input)
  124. if err != nil {
  125. return nil, errors.Wrap(err, "evalCall")
  126. }
  127. return v, nil
  128. case *ast.IndexExpr:
  129. v, err := evalIndex(expr.(*ast.IndexExpr), input)
  130. if err != nil {
  131. return nil, errors.Wrap(err, "evalIndex")
  132. }
  133. return v, nil
  134. case *ast.BasicLit:
  135. v, err := evalBasicLit(expr.(*ast.BasicLit), input)
  136. if err != nil {
  137. return nil, errors.Wrap(err, "evalBasicLit")
  138. }
  139. return v, nil
  140. default:
  141. return nil, errors.Wrapf(ErrInvalidOp, "unsupported expr type %s", reflect.TypeOf(expr))
  142. }
  143. }
  144. func evalBasicLit(expr *ast.BasicLit, input interface{}) (interface{}, error) {
  145. switch expr.Kind {
  146. case token.IDENT:
  147. switch input.(type) {
  148. case *jsonutils.JSONDict:
  149. jsonX := input.(*jsonutils.JSONDict)
  150. return jsonX.Get(expr.Value)
  151. default:
  152. return nil, errors.Wrapf(ErrInvalidOp, "evalBasicLit unsupported type %s", reflect.TypeOf(input))
  153. }
  154. case token.INT:
  155. return strconv.Atoi(expr.Value)
  156. case token.FLOAT:
  157. return strconv.ParseFloat(expr.Value, 64)
  158. case token.CHAR:
  159. return expr.Value[1 : len(expr.Value)-1][0], nil
  160. case token.STRING:
  161. return expr.Value[1 : len(expr.Value)-1], nil
  162. default:
  163. return nil, errors.Wrapf(ErrInvalidOp, "evalBasicLit unsupported kind %s", expr.Kind)
  164. }
  165. }
  166. func evalIndex(expr *ast.IndexExpr, input interface{}) (interface{}, error) {
  167. X, err := eval(expr.X, input)
  168. if err != nil {
  169. return nil, err
  170. }
  171. indexV, err := eval(expr.Index, input)
  172. if err != nil {
  173. return nil, err
  174. }
  175. switch X.(type) {
  176. case []interface{}, *jsonutils.JSONArray:
  177. arrX := getArray(X)
  178. indexI := getInt(indexV)
  179. if indexI >= 0 && indexI < int64(len(arrX)) {
  180. return arrX[indexI], nil
  181. } else {
  182. return nil, ErrOutOfIndex
  183. }
  184. case *jsonutils.JSONDict:
  185. jsonX := X.(*jsonutils.JSONDict)
  186. field := getString(indexV)
  187. return getJSONProperty(jsonX, field)
  188. case string:
  189. strX := X.(string)
  190. indexI := getInt(indexV)
  191. if indexI >= 0 && indexI < int64(len(strX)) {
  192. return strX[indexI], nil
  193. } else {
  194. return nil, ErrOutOfIndex
  195. }
  196. default:
  197. return nil, err
  198. }
  199. }
  200. func args2Strings(args []interface{}) []string {
  201. strs := make([]string, len(args))
  202. for i := 0; i < len(args); i += 1 {
  203. strs[i] = getString(args[i])
  204. }
  205. return strs
  206. }
  207. func args2Ints(args []interface{}) []int {
  208. ints := make([]int, len(args))
  209. for i := 0; i < len(args); i += 1 {
  210. ints[i] = int(getInt(args[i]))
  211. }
  212. return ints
  213. }
  214. func evalCallInternal(funcV interface{}, args []interface{}) (interface{}, error) {
  215. switch funcV.(type) {
  216. case []interface{}, *jsonutils.JSONArray:
  217. arrFuncV := getArray(funcV)
  218. ret := make([]interface{}, len(arrFuncV))
  219. for i := 0; i < len(arrFuncV); i += 1 {
  220. reti, err := evalCallInternal(arrFuncV[i], args)
  221. if err != nil {
  222. return nil, err
  223. }
  224. ret[i] = reti
  225. }
  226. return ret, nil
  227. case *funcCaller:
  228. caller := funcV.(*funcCaller)
  229. switch caller.caller.(type) {
  230. case string:
  231. strX := caller.caller.(string)
  232. switch caller.method {
  233. case "startswith":
  234. strArgs := args2Strings(args)
  235. if len(strArgs) != 1 {
  236. return nil, ErrFuncArgument
  237. }
  238. return strings.HasPrefix(strX, strArgs[0]), nil
  239. case "endswith":
  240. strArgs := args2Strings(args)
  241. if len(strArgs) != 1 {
  242. return nil, ErrFuncArgument
  243. }
  244. return strings.HasSuffix(strX, strArgs[0]), nil
  245. case "contains":
  246. strArgs := args2Strings(args)
  247. if len(strArgs) != 1 {
  248. return nil, ErrFuncArgument
  249. }
  250. return strings.Contains(strX, strArgs[0]), nil
  251. case "in":
  252. var strArgs []string
  253. if len(args) == 0 {
  254. return nil, ErrFuncArgument
  255. } else if len(args) == 1 {
  256. switch args[0].(type) {
  257. case string, *jsonutils.JSONString:
  258. strArgs = []string{args[0].(string)}
  259. case []interface{}, *jsonutils.JSONArray:
  260. strArgs = args2Strings(getArray(args[0]))
  261. default:
  262. return nil, ErrFuncArgument
  263. }
  264. } else {
  265. strArgs = args2Strings(args)
  266. }
  267. return utils.IsInStringArray(strX, strArgs), nil
  268. case "len":
  269. if len(args) > 0 {
  270. return nil, ErrFuncArgument
  271. }
  272. return len(strX), nil
  273. case "substr":
  274. intArgs := args2Ints(args)
  275. var o1, o2 int
  276. if len(intArgs) == 1 {
  277. o1 = 0
  278. o2 = intArgs[0]
  279. } else if len(intArgs) == 2 {
  280. o1 = intArgs[0]
  281. o2 = intArgs[1]
  282. } else {
  283. return nil, ErrFuncArgument
  284. }
  285. if o1 < 0 {
  286. o1 = len(strX) + o1
  287. }
  288. if o2 < 0 {
  289. o2 = len(strX) + o2
  290. }
  291. if o1 < 0 || o1 >= len(strX) {
  292. return nil, ErrFuncArgument
  293. }
  294. if o2 <= o1 || o2 > len(strX) {
  295. return nil, ErrFuncArgument
  296. }
  297. return strX[o1:o2], nil
  298. default:
  299. return nil, ErrInvalidOp
  300. }
  301. case *jsonutils.JSONDict:
  302. jsonX := caller.caller.(*jsonutils.JSONDict)
  303. switch caller.method {
  304. case "contains":
  305. strArgs := args2Strings(args)
  306. return jsonX.Contains(strArgs...), nil
  307. case "len":
  308. if len(args) > 0 {
  309. return nil, ErrFuncArgument
  310. }
  311. return jsonX.Size(), nil
  312. case "keys":
  313. if len(args) > 0 {
  314. return nil, ErrFuncArgument
  315. }
  316. return jsonutils.NewStringArray(jsonX.SortedKeys()), nil
  317. default:
  318. return nil, ErrMethodNotFound
  319. }
  320. case []interface{}, *jsonutils.JSONArray:
  321. array := getArray(caller.caller)
  322. switch caller.method {
  323. case "len":
  324. if len(args) > 0 {
  325. return nil, ErrFuncArgument
  326. }
  327. return len(array), nil
  328. case "contains":
  329. if len(args) < 1 {
  330. return nil, ErrFuncArgument
  331. }
  332. for j := 0; j < len(args); j += 1 {
  333. find := false
  334. for i := 0; i < len(array); i += 1 {
  335. findInf, err := evalBinaryInternal(array[i], args[j], token.EQL)
  336. if err != nil {
  337. return nil, err
  338. }
  339. switch findInf.(type) {
  340. case bool:
  341. if findInf.(bool) {
  342. find = true
  343. }
  344. default:
  345. return nil, ErrInvalidOp
  346. }
  347. }
  348. if !find {
  349. return false, nil
  350. }
  351. }
  352. return true, nil
  353. default:
  354. return nil, ErrMethodNotFound
  355. }
  356. default:
  357. return nil, ErrInvalidOp
  358. }
  359. default:
  360. return nil, ErrInvalidOp
  361. }
  362. }
  363. func evalCall(expr *ast.CallExpr, input interface{}) (interface{}, error) {
  364. funcV, err := eval(expr.Fun, input)
  365. if err != nil {
  366. return nil, err
  367. }
  368. args := make([]interface{}, len(expr.Args))
  369. for i := 0; i < len(expr.Args); i += 1 {
  370. args[i], err = eval(expr.Args[i], input)
  371. if err != nil {
  372. return nil, err
  373. }
  374. }
  375. return evalCallInternal(funcV, args)
  376. }
  377. func evalParen(expr *ast.ParenExpr, input interface{}) (interface{}, error) {
  378. return eval(expr.X, input)
  379. }
  380. func getJSONProperty(json *jsonutils.JSONDict, identStr string) (jsonutils.JSONObject, error) {
  381. if json.Contains(identStr) {
  382. return json.Get(identStr)
  383. } else {
  384. identArray := jsonutils.GetArrayOfPrefix(json, identStr)
  385. if len(identArray) > 0 {
  386. return jsonutils.NewArray(identArray...), nil
  387. } else {
  388. return nil, ErrFieldNotFound
  389. }
  390. }
  391. }
  392. func evalIdent(expr *ast.Ident, input interface{}) (interface{}, error) {
  393. if input == nil {
  394. return expr.Name, nil
  395. } else {
  396. switch input.(type) {
  397. case *jsonutils.JSONDict:
  398. json := input.(*jsonutils.JSONDict)
  399. return getJSONProperty(json, expr.Name)
  400. default:
  401. return nil, errors.Wrapf(ErrInvalidOp, "evalIdent unsupported type %s", reflect.TypeOf(input))
  402. }
  403. }
  404. }
  405. type funcCaller struct {
  406. caller interface{}
  407. method string
  408. }
  409. func getArray(X interface{}) []interface{} {
  410. switch X.(type) {
  411. case *jsonutils.JSONArray:
  412. arr := X.(*jsonutils.JSONArray)
  413. ret := make([]interface{}, arr.Size())
  414. for i := 0; i < arr.Size(); i += 1 {
  415. ret[i], _ = arr.GetAt(i)
  416. }
  417. return ret
  418. default:
  419. return X.([]interface{})
  420. }
  421. }
  422. func evalSelectorInternal(X interface{}, identStr string) (interface{}, error) {
  423. switch X.(type) {
  424. case *jsonutils.JSONDict:
  425. json := X.(*jsonutils.JSONDict)
  426. ret, err := getJSONProperty(json, identStr)
  427. if err == ErrFieldNotFound {
  428. return &funcCaller{caller: X, method: identStr}, nil
  429. } else {
  430. return ret, errors.Wrapf(err, "getJSONProperty %s", identStr)
  431. }
  432. case []interface{}, *jsonutils.JSONArray:
  433. if identStr == "len" || identStr == "contains" {
  434. return &funcCaller{caller: X, method: identStr}, nil
  435. }
  436. arrX := getArray(X)
  437. ret := make([]interface{}, len(arrX))
  438. for i := 0; i < len(arrX); i += 1 {
  439. reti, err := evalSelectorInternal(arrX[i], identStr)
  440. if err != nil {
  441. return nil, err
  442. }
  443. ret[i] = reti
  444. }
  445. return ret, nil
  446. case string, *jsonutils.JSONString:
  447. return &funcCaller{caller: getString(X), method: identStr}, nil
  448. default:
  449. return nil, errors.Wrapf(ErrInvalidOp, "unsupported type %s", reflect.TypeOf(X))
  450. }
  451. }
  452. func evalSelector(expr *ast.SelectorExpr, input interface{}) (interface{}, error) {
  453. X, err := eval(expr.X, input)
  454. if err != nil {
  455. return nil, errors.Wrap(ErrInvalidOp, "eval selector X")
  456. }
  457. ident, err := evalIdent(expr.Sel, nil)
  458. if err != nil {
  459. return nil, errors.Wrap(ErrInvalidOp, "eval selector Sel")
  460. }
  461. identStr := ident.(string)
  462. return evalSelectorInternal(X, identStr)
  463. }
  464. func evalUnaryInternal(X interface{}, op token.Token) (interface{}, error) {
  465. switch X.(type) {
  466. case []interface{}, *jsonutils.JSONArray:
  467. arrX := getArray(X)
  468. ret := make([]interface{}, len(arrX))
  469. for i := 0; i < len(arrX); i += 1 {
  470. reti, err := evalUnaryInternal(arrX[i], op)
  471. if err != nil {
  472. return nil, err
  473. }
  474. ret[i] = reti
  475. }
  476. return ret, nil
  477. case bool, *jsonutils.JSONBool:
  478. boolX := getBool(X)
  479. switch op {
  480. case token.NOT:
  481. return !boolX, nil
  482. default:
  483. return nil, ErrInvalidOp
  484. }
  485. case int, int8, int16, int32, int64, uint, uint8, uint16, uint32, uint64, *jsonutils.JSONInt:
  486. intX := getInt(X)
  487. switch op {
  488. case token.SUB:
  489. return -intX, nil
  490. default:
  491. return nil, ErrInvalidOp
  492. }
  493. case float32, float64, *jsonutils.JSONFloat:
  494. floatX := getFloat(X)
  495. switch op {
  496. case token.SUB:
  497. return -floatX, nil
  498. default:
  499. return nil, ErrInvalidOp
  500. }
  501. default:
  502. return nil, ErrInvalidOp
  503. }
  504. }
  505. func evalUnary(expr *ast.UnaryExpr, input interface{}) (interface{}, error) {
  506. X, err := eval(expr.X, input)
  507. if err != nil {
  508. return nil, err
  509. }
  510. op := expr.Op
  511. return evalUnaryInternal(X, op)
  512. }
  513. func getString(val interface{}) string {
  514. switch val.(type) {
  515. case *jsonutils.JSONString:
  516. jsonVal, _ := val.(*jsonutils.JSONString).GetString()
  517. return jsonVal
  518. default:
  519. return val.(string)
  520. }
  521. }
  522. func getBool(val interface{}) bool {
  523. switch val.(type) {
  524. case *jsonutils.JSONBool:
  525. jsonVal, _ := val.(*jsonutils.JSONBool).Bool()
  526. return jsonVal
  527. default:
  528. return val.(bool)
  529. }
  530. }
  531. func getInt(val interface{}) int64 {
  532. switch val.(type) {
  533. case *jsonutils.JSONInt:
  534. jsonVal, _ := val.(*jsonutils.JSONInt).Int()
  535. return jsonVal
  536. default:
  537. return reflect.ValueOf(val).Int()
  538. }
  539. }
  540. func getFloat(val interface{}) float64 {
  541. switch val.(type) {
  542. case *jsonutils.JSONFloat:
  543. jsonVal, _ := val.(*jsonutils.JSONFloat).Float()
  544. return jsonVal
  545. default:
  546. return reflect.ValueOf(val).Float()
  547. }
  548. }
  549. func evalBinaryInternal(X, Y interface{}, op token.Token) (interface{}, error) {
  550. switch X.(type) {
  551. case []interface{}, *jsonutils.JSONArray:
  552. arrX := getArray(X)
  553. ret := make([]interface{}, len(arrX))
  554. for i := 0; i < len(arrX); i += 1 {
  555. reti, err := evalBinaryInternal(arrX[i], Y, op)
  556. if err != nil {
  557. return nil, errors.Wrapf(err, "X.evalBinaryInternal at [%d]", i)
  558. }
  559. ret[i] = reti
  560. }
  561. return ret, nil
  562. }
  563. switch Y.(type) {
  564. case []interface{}, *jsonutils.JSONArray:
  565. arrY := getArray(Y)
  566. ret := make([]interface{}, len(arrY))
  567. for i := 0; i < len(arrY); i += 1 {
  568. reti, err := evalBinaryInternal(X, arrY[i], op)
  569. if err != nil {
  570. return nil, errors.Wrapf(err, "Y.evalBinaryInternal at [%d]", i)
  571. }
  572. ret[i] = reti
  573. }
  574. return ret, nil
  575. }
  576. switch X.(type) {
  577. case bool, *jsonutils.JSONBool:
  578. switch Y.(type) {
  579. case bool, *jsonutils.JSONBool:
  580. boolX := getBool(X)
  581. boolY := getBool(Y)
  582. switch op {
  583. case token.LAND:
  584. return boolX && boolY, nil
  585. case token.LOR:
  586. return boolX || boolY, nil
  587. default:
  588. return nil, errors.Wrapf(ErrInvalidOp, "bool op %v", op)
  589. }
  590. default:
  591. return nil, errors.Wrap(ErrInvalidOp, "mismatch bool type")
  592. }
  593. case string, *jsonutils.JSONString:
  594. switch Y.(type) {
  595. case string, *jsonutils.JSONString:
  596. strX := getString(X)
  597. strY := getString(Y)
  598. switch op {
  599. case token.ADD:
  600. return strX + strY, nil
  601. case token.EQL:
  602. return strX == strY, nil
  603. case token.NEQ:
  604. return strX != strY, nil
  605. default:
  606. return nil, errors.Wrapf(ErrInvalidOp, "string op %v", op)
  607. }
  608. default:
  609. return nil, errors.Wrap(ErrInvalidOp, "mismatch string type")
  610. }
  611. case int, int8, int16, int32, int64, uint, uint8, uint16, uint32, uint64, *jsonutils.JSONInt:
  612. intX := getInt(X)
  613. switch Y.(type) {
  614. case int, int8, int16, int32, int64, uint, uint8, uint16, uint32, uint64, *jsonutils.JSONInt:
  615. intY := getInt(Y)
  616. return evalIntegerOp(intX, intY, op)
  617. case float32, float64, jsonutils.JSONFloat:
  618. floatX := float64(intX)
  619. floatY := getFloat(Y)
  620. return evalFloatOp(floatX, floatY, op)
  621. default:
  622. return nil, errors.Wrap(ErrInvalidOp, "mismatch type int")
  623. }
  624. case float32, float64, *jsonutils.JSONFloat:
  625. floatX := getFloat(X)
  626. switch Y.(type) {
  627. case int, int8, int16, int32, int64, uint, uint8, uint16, uint32, uint64, *jsonutils.JSONInt:
  628. floatY := float64(getInt(Y))
  629. return evalFloatOp(floatX, floatY, op)
  630. case float32, float64, *jsonutils.JSONFloat:
  631. floatY := getFloat(Y)
  632. return evalFloatOp(floatX, floatY, op)
  633. default:
  634. return nil, errors.Wrap(ErrInvalidOp, "mismatch type float")
  635. }
  636. default:
  637. return nil, errors.Wrapf(ErrInvalidOp, "unsupported op type %v", reflect.TypeOf(X))
  638. }
  639. }
  640. func evalBinary(bExpr *ast.BinaryExpr, input interface{}) (interface{}, error) {
  641. X, err := eval(bExpr.X, input)
  642. if err != nil {
  643. return nil, errors.Wrap(err, "eval binary left")
  644. }
  645. Y, err := eval(bExpr.Y, input)
  646. if err != nil {
  647. return nil, errors.Wrap(err, "eval binary right")
  648. }
  649. return evalBinaryInternal(X, Y, bExpr.Op)
  650. }
  651. func evalIntegerOp(X, Y int64, op token.Token) (interface{}, error) {
  652. switch op {
  653. case token.ADD:
  654. return X + Y, nil
  655. case token.SUB:
  656. return X - Y, nil
  657. case token.MUL:
  658. return X * Y, nil
  659. case token.QUO:
  660. return X / Y, nil
  661. case token.REM:
  662. return X % Y, nil
  663. case token.AND:
  664. return X & Y, nil
  665. case token.OR:
  666. return X | Y, nil
  667. case token.XOR:
  668. return X ^ Y, nil
  669. case token.SHL:
  670. return X << uint64(Y), nil
  671. case token.SHR:
  672. return X >> uint64(Y), nil
  673. case token.AND_NOT:
  674. return X &^ Y, nil
  675. case token.EQL:
  676. return X == Y, nil
  677. case token.LSS:
  678. return X < Y, nil
  679. case token.GTR:
  680. return X > Y, nil
  681. case token.NEQ:
  682. return X != Y, nil
  683. case token.LEQ:
  684. return X <= Y, nil
  685. case token.GEQ:
  686. return X >= Y, nil
  687. default:
  688. return nil, ErrInvalidOp
  689. }
  690. }
  691. func evalFloatOp(X, Y float64, op token.Token) (interface{}, error) {
  692. switch op {
  693. case token.ADD:
  694. return X + Y, nil
  695. case token.SUB:
  696. return X - Y, nil
  697. case token.MUL:
  698. return X * Y, nil
  699. case token.QUO:
  700. return X / Y, nil
  701. case token.EQL:
  702. return X == Y, nil
  703. case token.LSS:
  704. return X < Y, nil
  705. case token.GTR:
  706. return X > Y, nil
  707. case token.NEQ:
  708. return X != Y, nil
  709. case token.LEQ:
  710. return X <= Y, nil
  711. case token.GEQ:
  712. return X >= Y, nil
  713. default:
  714. return nil, ErrInvalidOp
  715. }
  716. }