parser_expression.go 11 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491
  1. package pongo2
  2. import (
  3. "fmt"
  4. "math"
  5. )
  6. type Expression struct {
  7. // TODO: Add location token?
  8. expr1 IEvaluator
  9. expr2 IEvaluator
  10. opToken *Token
  11. }
  12. type relationalExpression struct {
  13. // TODO: Add location token?
  14. expr1 IEvaluator
  15. expr2 IEvaluator
  16. opToken *Token
  17. }
  18. type simpleExpression struct {
  19. negate bool
  20. negativeSign bool
  21. term1 IEvaluator
  22. term2 IEvaluator
  23. opToken *Token
  24. }
  25. type term struct {
  26. // TODO: Add location token?
  27. factor1 IEvaluator
  28. factor2 IEvaluator
  29. opToken *Token
  30. }
  31. type power struct {
  32. // TODO: Add location token?
  33. power1 IEvaluator
  34. power2 IEvaluator
  35. }
  36. func (expr *Expression) FilterApplied(name string) bool {
  37. return expr.expr1.FilterApplied(name) && (expr.expr2 == nil ||
  38. (expr.expr2 != nil && expr.expr2.FilterApplied(name)))
  39. }
  40. func (expr *relationalExpression) FilterApplied(name string) bool {
  41. return expr.expr1.FilterApplied(name) && (expr.expr2 == nil ||
  42. (expr.expr2 != nil && expr.expr2.FilterApplied(name)))
  43. }
  44. func (expr *simpleExpression) FilterApplied(name string) bool {
  45. return expr.term1.FilterApplied(name) && (expr.term2 == nil ||
  46. (expr.term2 != nil && expr.term2.FilterApplied(name)))
  47. }
  48. func (expr *term) FilterApplied(name string) bool {
  49. return expr.factor1.FilterApplied(name) && (expr.factor2 == nil ||
  50. (expr.factor2 != nil && expr.factor2.FilterApplied(name)))
  51. }
  52. func (expr *power) FilterApplied(name string) bool {
  53. return expr.power1.FilterApplied(name) && (expr.power2 == nil ||
  54. (expr.power2 != nil && expr.power2.FilterApplied(name)))
  55. }
  56. func (expr *Expression) GetPositionToken() *Token {
  57. return expr.expr1.GetPositionToken()
  58. }
  59. func (expr *relationalExpression) GetPositionToken() *Token {
  60. return expr.expr1.GetPositionToken()
  61. }
  62. func (expr *simpleExpression) GetPositionToken() *Token {
  63. return expr.term1.GetPositionToken()
  64. }
  65. func (expr *term) GetPositionToken() *Token {
  66. return expr.factor1.GetPositionToken()
  67. }
  68. func (expr *power) GetPositionToken() *Token {
  69. return expr.power1.GetPositionToken()
  70. }
  71. func (expr *Expression) Execute(ctx *ExecutionContext, writer TemplateWriter) *Error {
  72. value, err := expr.Evaluate(ctx)
  73. if err != nil {
  74. return err
  75. }
  76. writer.WriteString(value.String())
  77. return nil
  78. }
  79. func (expr *relationalExpression) Execute(ctx *ExecutionContext, writer TemplateWriter) *Error {
  80. value, err := expr.Evaluate(ctx)
  81. if err != nil {
  82. return err
  83. }
  84. writer.WriteString(value.String())
  85. return nil
  86. }
  87. func (expr *simpleExpression) Execute(ctx *ExecutionContext, writer TemplateWriter) *Error {
  88. value, err := expr.Evaluate(ctx)
  89. if err != nil {
  90. return err
  91. }
  92. writer.WriteString(value.String())
  93. return nil
  94. }
  95. func (expr *term) Execute(ctx *ExecutionContext, writer TemplateWriter) *Error {
  96. value, err := expr.Evaluate(ctx)
  97. if err != nil {
  98. return err
  99. }
  100. writer.WriteString(value.String())
  101. return nil
  102. }
  103. func (expr *power) Execute(ctx *ExecutionContext, writer TemplateWriter) *Error {
  104. value, err := expr.Evaluate(ctx)
  105. if err != nil {
  106. return err
  107. }
  108. writer.WriteString(value.String())
  109. return nil
  110. }
  111. func (expr *Expression) Evaluate(ctx *ExecutionContext) (*Value, *Error) {
  112. v1, err := expr.expr1.Evaluate(ctx)
  113. if err != nil {
  114. return nil, err
  115. }
  116. if expr.expr2 != nil {
  117. v2, err := expr.expr2.Evaluate(ctx)
  118. if err != nil {
  119. return nil, err
  120. }
  121. switch expr.opToken.Val {
  122. case "and", "&&":
  123. return AsValue(v1.IsTrue() && v2.IsTrue()), nil
  124. case "or", "||":
  125. return AsValue(v1.IsTrue() || v2.IsTrue()), nil
  126. default:
  127. return nil, ctx.Error(fmt.Sprintf("unimplemented: %s", expr.opToken.Val), expr.opToken)
  128. }
  129. } else {
  130. return v1, nil
  131. }
  132. }
  133. func (expr *relationalExpression) Evaluate(ctx *ExecutionContext) (*Value, *Error) {
  134. v1, err := expr.expr1.Evaluate(ctx)
  135. if err != nil {
  136. return nil, err
  137. }
  138. if expr.expr2 != nil {
  139. v2, err := expr.expr2.Evaluate(ctx)
  140. if err != nil {
  141. return nil, err
  142. }
  143. switch expr.opToken.Val {
  144. case "<=":
  145. if v1.IsFloat() || v2.IsFloat() {
  146. return AsValue(v1.Float() <= v2.Float()), nil
  147. }
  148. return AsValue(v1.Integer() <= v2.Integer()), nil
  149. case ">=":
  150. if v1.IsFloat() || v2.IsFloat() {
  151. return AsValue(v1.Float() >= v2.Float()), nil
  152. }
  153. return AsValue(v1.Integer() >= v2.Integer()), nil
  154. case "==":
  155. return AsValue(v1.EqualValueTo(v2)), nil
  156. case ">":
  157. if v1.IsFloat() || v2.IsFloat() {
  158. return AsValue(v1.Float() > v2.Float()), nil
  159. }
  160. return AsValue(v1.Integer() > v2.Integer()), nil
  161. case "<":
  162. if v1.IsFloat() || v2.IsFloat() {
  163. return AsValue(v1.Float() < v2.Float()), nil
  164. }
  165. return AsValue(v1.Integer() < v2.Integer()), nil
  166. case "!=", "<>":
  167. return AsValue(!v1.EqualValueTo(v2)), nil
  168. case "in":
  169. return AsValue(v2.Contains(v1)), nil
  170. default:
  171. return nil, ctx.Error(fmt.Sprintf("unimplemented: %s", expr.opToken.Val), expr.opToken)
  172. }
  173. } else {
  174. return v1, nil
  175. }
  176. }
  177. func (expr *simpleExpression) Evaluate(ctx *ExecutionContext) (*Value, *Error) {
  178. t1, err := expr.term1.Evaluate(ctx)
  179. if err != nil {
  180. return nil, err
  181. }
  182. result := t1
  183. if expr.negate {
  184. result = result.Negate()
  185. }
  186. if expr.negativeSign {
  187. if result.IsNumber() {
  188. switch {
  189. case result.IsFloat():
  190. result = AsValue(-1 * result.Float())
  191. case result.IsInteger():
  192. result = AsValue(-1 * result.Integer())
  193. default:
  194. return nil, ctx.Error("Operation between a number and a non-(float/integer) is not possible", nil)
  195. }
  196. } else {
  197. return nil, ctx.Error("Negative sign on a non-number expression", expr.GetPositionToken())
  198. }
  199. }
  200. if expr.term2 != nil {
  201. t2, err := expr.term2.Evaluate(ctx)
  202. if err != nil {
  203. return nil, err
  204. }
  205. switch expr.opToken.Val {
  206. case "+":
  207. if result.IsFloat() || t2.IsFloat() {
  208. // Result will be a float
  209. return AsValue(result.Float() + t2.Float()), nil
  210. }
  211. // Result will be an integer
  212. return AsValue(result.Integer() + t2.Integer()), nil
  213. case "-":
  214. if result.IsFloat() || t2.IsFloat() {
  215. // Result will be a float
  216. return AsValue(result.Float() - t2.Float()), nil
  217. }
  218. // Result will be an integer
  219. return AsValue(result.Integer() - t2.Integer()), nil
  220. default:
  221. return nil, ctx.Error("Unimplemented", expr.GetPositionToken())
  222. }
  223. }
  224. return result, nil
  225. }
  226. func (expr *term) Evaluate(ctx *ExecutionContext) (*Value, *Error) {
  227. f1, err := expr.factor1.Evaluate(ctx)
  228. if err != nil {
  229. return nil, err
  230. }
  231. if expr.factor2 != nil {
  232. f2, err := expr.factor2.Evaluate(ctx)
  233. if err != nil {
  234. return nil, err
  235. }
  236. switch expr.opToken.Val {
  237. case "*":
  238. if f1.IsFloat() || f2.IsFloat() {
  239. // Result will be float
  240. return AsValue(f1.Float() * f2.Float()), nil
  241. }
  242. // Result will be int
  243. return AsValue(f1.Integer() * f2.Integer()), nil
  244. case "/":
  245. if f1.IsFloat() || f2.IsFloat() {
  246. // Result will be float
  247. return AsValue(f1.Float() / f2.Float()), nil
  248. }
  249. // Result will be int
  250. return AsValue(f1.Integer() / f2.Integer()), nil
  251. case "%":
  252. // Result will be int
  253. return AsValue(f1.Integer() % f2.Integer()), nil
  254. default:
  255. return nil, ctx.Error("unimplemented", expr.opToken)
  256. }
  257. } else {
  258. return f1, nil
  259. }
  260. }
  261. func (expr *power) Evaluate(ctx *ExecutionContext) (*Value, *Error) {
  262. p1, err := expr.power1.Evaluate(ctx)
  263. if err != nil {
  264. return nil, err
  265. }
  266. if expr.power2 != nil {
  267. p2, err := expr.power2.Evaluate(ctx)
  268. if err != nil {
  269. return nil, err
  270. }
  271. return AsValue(math.Pow(p1.Float(), p2.Float())), nil
  272. }
  273. return p1, nil
  274. }
  275. func (p *Parser) parseFactor() (IEvaluator, *Error) {
  276. if p.Match(TokenSymbol, "(") != nil {
  277. expr, err := p.ParseExpression()
  278. if err != nil {
  279. return nil, err
  280. }
  281. if p.Match(TokenSymbol, ")") == nil {
  282. return nil, p.Error("Closing bracket expected after expression", nil)
  283. }
  284. return expr, nil
  285. }
  286. return p.parseVariableOrLiteralWithFilter()
  287. }
  288. func (p *Parser) parsePower() (IEvaluator, *Error) {
  289. pw := new(power)
  290. power1, err := p.parseFactor()
  291. if err != nil {
  292. return nil, err
  293. }
  294. pw.power1 = power1
  295. if p.Match(TokenSymbol, "^") != nil {
  296. power2, err := p.parsePower()
  297. if err != nil {
  298. return nil, err
  299. }
  300. pw.power2 = power2
  301. }
  302. if pw.power2 == nil {
  303. // Shortcut for faster evaluation
  304. return pw.power1, nil
  305. }
  306. return pw, nil
  307. }
  308. func (p *Parser) parseTerm() (IEvaluator, *Error) {
  309. returnTerm := new(term)
  310. factor1, err := p.parsePower()
  311. if err != nil {
  312. return nil, err
  313. }
  314. returnTerm.factor1 = factor1
  315. for p.PeekOne(TokenSymbol, "*", "/", "%") != nil {
  316. if returnTerm.opToken != nil {
  317. // Create new sub-term
  318. returnTerm = &term{
  319. factor1: returnTerm,
  320. }
  321. }
  322. op := p.Current()
  323. p.Consume()
  324. factor2, err := p.parsePower()
  325. if err != nil {
  326. return nil, err
  327. }
  328. returnTerm.opToken = op
  329. returnTerm.factor2 = factor2
  330. }
  331. if returnTerm.opToken == nil {
  332. // Shortcut for faster evaluation
  333. return returnTerm.factor1, nil
  334. }
  335. return returnTerm, nil
  336. }
  337. func (p *Parser) parseSimpleExpression() (IEvaluator, *Error) {
  338. expr := new(simpleExpression)
  339. if sign := p.MatchOne(TokenSymbol, "+", "-"); sign != nil {
  340. if sign.Val == "-" {
  341. expr.negativeSign = true
  342. }
  343. }
  344. if p.Match(TokenSymbol, "!") != nil || p.Match(TokenKeyword, "not") != nil {
  345. expr.negate = true
  346. }
  347. term1, err := p.parseTerm()
  348. if err != nil {
  349. return nil, err
  350. }
  351. expr.term1 = term1
  352. for p.PeekOne(TokenSymbol, "+", "-") != nil {
  353. if expr.opToken != nil {
  354. // New sub expr
  355. expr = &simpleExpression{
  356. term1: expr,
  357. }
  358. }
  359. op := p.Current()
  360. p.Consume()
  361. term2, err := p.parseTerm()
  362. if err != nil {
  363. return nil, err
  364. }
  365. expr.term2 = term2
  366. expr.opToken = op
  367. }
  368. if expr.negate == false && expr.negativeSign == false && expr.term2 == nil {
  369. // Shortcut for faster evaluation
  370. return expr.term1, nil
  371. }
  372. return expr, nil
  373. }
  374. func (p *Parser) parseRelationalExpression() (IEvaluator, *Error) {
  375. expr1, err := p.parseSimpleExpression()
  376. if err != nil {
  377. return nil, err
  378. }
  379. expr := &relationalExpression{
  380. expr1: expr1,
  381. }
  382. if t := p.MatchOne(TokenSymbol, "==", "<=", ">=", "!=", "<>", ">", "<"); t != nil {
  383. expr2, err := p.parseRelationalExpression()
  384. if err != nil {
  385. return nil, err
  386. }
  387. expr.opToken = t
  388. expr.expr2 = expr2
  389. } else if t := p.MatchOne(TokenKeyword, "in"); t != nil {
  390. expr2, err := p.parseSimpleExpression()
  391. if err != nil {
  392. return nil, err
  393. }
  394. expr.opToken = t
  395. expr.expr2 = expr2
  396. }
  397. if expr.expr2 == nil {
  398. // Shortcut for faster evaluation
  399. return expr.expr1, nil
  400. }
  401. return expr, nil
  402. }
  403. func (p *Parser) ParseExpression() (IEvaluator, *Error) {
  404. rexpr1, err := p.parseRelationalExpression()
  405. if err != nil {
  406. return nil, err
  407. }
  408. exp := &Expression{
  409. expr1: rexpr1,
  410. }
  411. if p.PeekOne(TokenSymbol, "&&", "||") != nil || p.PeekOne(TokenKeyword, "and", "or") != nil {
  412. op := p.Current()
  413. p.Consume()
  414. expr2, err := p.ParseExpression()
  415. if err != nil {
  416. return nil, err
  417. }
  418. exp.expr2 = expr2
  419. exp.opToken = op
  420. }
  421. if exp.expr2 == nil {
  422. // Shortcut for faster evaluation
  423. return exp.expr1, nil
  424. }
  425. return exp, nil
  426. }