github.com/pingcap/tidb/parser@v0.0.0-20231013125129-93a834a6bf8d/ast/expressions.go (about) 1 // Copyright 2015 PingCAP, Inc. 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 // See the License for the specific language governing permissions and 12 // limitations under the License. 13 14 package ast 15 16 import ( 17 "fmt" 18 "io" 19 "reflect" 20 "regexp" 21 "strings" 22 23 "github.com/pingcap/errors" 24 "github.com/pingcap/tidb/parser/format" 25 "github.com/pingcap/tidb/parser/model" 26 "github.com/pingcap/tidb/parser/opcode" 27 ) 28 29 var ( 30 _ ExprNode = &BetweenExpr{} 31 _ ExprNode = &BinaryOperationExpr{} 32 _ ExprNode = &CaseExpr{} 33 _ ExprNode = &ColumnNameExpr{} 34 _ ExprNode = &TableNameExpr{} 35 _ ExprNode = &CompareSubqueryExpr{} 36 _ ExprNode = &DefaultExpr{} 37 _ ExprNode = &ExistsSubqueryExpr{} 38 _ ExprNode = &IsNullExpr{} 39 _ ExprNode = &IsTruthExpr{} 40 _ ExprNode = &ParenthesesExpr{} 41 _ ExprNode = &PatternInExpr{} 42 _ ExprNode = &PatternLikeOrIlikeExpr{} 43 _ ExprNode = &PatternRegexpExpr{} 44 _ ExprNode = &PositionExpr{} 45 _ ExprNode = &RowExpr{} 46 _ ExprNode = &SubqueryExpr{} 47 _ ExprNode = &UnaryOperationExpr{} 48 _ ExprNode = &ValuesExpr{} 49 _ ExprNode = &VariableExpr{} 50 _ ExprNode = &MatchAgainst{} 51 _ ExprNode = &SetCollationExpr{} 52 53 _ Node = &ColumnName{} 54 _ Node = &WhenClause{} 55 ) 56 57 // ValueExpr define a interface for ValueExpr. 58 type ValueExpr interface { 59 ExprNode 60 SetValue(val interface{}) 61 GetValue() interface{} 62 GetDatumString() string 63 GetString() string 64 GetProjectionOffset() int 65 SetProjectionOffset(offset int) 66 } 67 68 // NewValueExpr creates a ValueExpr with value, and sets default field type. 69 var NewValueExpr func(value interface{}, charset string, collate string) ValueExpr 70 71 // NewParamMarkerExpr creates a ParamMarkerExpr. 72 var NewParamMarkerExpr func(offset int) ParamMarkerExpr 73 74 // BetweenExpr is for "between and" or "not between and" expression. 75 type BetweenExpr struct { 76 exprNode 77 // Expr is the expression to be checked. 78 Expr ExprNode 79 // Left is the expression for minimal value in the range. 80 Left ExprNode 81 // Right is the expression for maximum value in the range. 82 Right ExprNode 83 // Not is true, the expression is "not between and". 84 Not bool 85 } 86 87 // Restore implements Node interface. 88 func (n *BetweenExpr) Restore(ctx *format.RestoreCtx) error { 89 if err := n.Expr.Restore(ctx); err != nil { 90 return errors.Annotate(err, "An error occurred while restore BetweenExpr.Expr") 91 } 92 if n.Not { 93 ctx.WriteKeyWord(" NOT BETWEEN ") 94 } else { 95 ctx.WriteKeyWord(" BETWEEN ") 96 } 97 if err := n.Left.Restore(ctx); err != nil { 98 return errors.Annotate(err, "An error occurred while restore BetweenExpr.Left") 99 } 100 ctx.WriteKeyWord(" AND ") 101 if err := n.Right.Restore(ctx); err != nil { 102 return errors.Annotate(err, "An error occurred while restore BetweenExpr.Right ") 103 } 104 return nil 105 } 106 107 // Format the ExprNode into a Writer. 108 func (n *BetweenExpr) Format(w io.Writer) { 109 n.Expr.Format(w) 110 if n.Not { 111 fmt.Fprint(w, " NOT BETWEEN ") 112 } else { 113 fmt.Fprint(w, " BETWEEN ") 114 } 115 n.Left.Format(w) 116 fmt.Fprint(w, " AND ") 117 n.Right.Format(w) 118 } 119 120 // Accept implements Node interface. 121 func (n *BetweenExpr) Accept(v Visitor) (Node, bool) { 122 newNode, skipChildren := v.Enter(n) 123 if skipChildren { 124 return v.Leave(newNode) 125 } 126 127 n = newNode.(*BetweenExpr) 128 node, ok := n.Expr.Accept(v) 129 if !ok { 130 return n, false 131 } 132 n.Expr = node.(ExprNode) 133 134 node, ok = n.Left.Accept(v) 135 if !ok { 136 return n, false 137 } 138 n.Left = node.(ExprNode) 139 140 node, ok = n.Right.Accept(v) 141 if !ok { 142 return n, false 143 } 144 n.Right = node.(ExprNode) 145 146 return v.Leave(n) 147 } 148 149 // BinaryOperationExpr is for binary operation like `1 + 1`, `1 - 1`, etc. 150 type BinaryOperationExpr struct { 151 exprNode 152 // Op is the operator code for BinaryOperation. 153 Op opcode.Op 154 // L is the left expression in BinaryOperation. 155 L ExprNode 156 // R is the right expression in BinaryOperation. 157 R ExprNode 158 } 159 160 func restoreBinaryOpWithSpacesAround(ctx *format.RestoreCtx, op opcode.Op) error { 161 shouldInsertSpace := ctx.Flags.HasSpacesAroundBinaryOperationFlag() || op.IsKeyword() 162 if shouldInsertSpace { 163 ctx.WritePlain(" ") 164 } 165 if err := op.Restore(ctx); err != nil { 166 return err // no need to annotate, the caller will annotate. 167 } 168 if shouldInsertSpace { 169 ctx.WritePlain(" ") 170 } 171 return nil 172 } 173 174 // Restore implements Node interface. 175 func (n *BinaryOperationExpr) Restore(ctx *format.RestoreCtx) error { 176 if ctx.Flags.HasRestoreBracketAroundBinaryOperation() { 177 ctx.WritePlain("(") 178 } 179 if err := n.L.Restore(ctx); err != nil { 180 return errors.Annotate(err, "An error occurred when restore BinaryOperationExpr.L") 181 } 182 if err := restoreBinaryOpWithSpacesAround(ctx, n.Op); err != nil { 183 return errors.Annotate(err, "An error occurred when restore BinaryOperationExpr.Op") 184 } 185 if err := n.R.Restore(ctx); err != nil { 186 return errors.Annotate(err, "An error occurred when restore BinaryOperationExpr.R") 187 } 188 if ctx.Flags.HasRestoreBracketAroundBinaryOperation() { 189 ctx.WritePlain(")") 190 } 191 return nil 192 } 193 194 // Format the ExprNode into a Writer. 195 func (n *BinaryOperationExpr) Format(w io.Writer) { 196 n.L.Format(w) 197 fmt.Fprint(w, " ") 198 n.Op.Format(w) 199 fmt.Fprint(w, " ") 200 n.R.Format(w) 201 } 202 203 // Accept implements Node interface. 204 func (n *BinaryOperationExpr) Accept(v Visitor) (Node, bool) { 205 newNode, skipChildren := v.Enter(n) 206 if skipChildren { 207 return v.Leave(newNode) 208 } 209 210 n = newNode.(*BinaryOperationExpr) 211 node, ok := n.L.Accept(v) 212 if !ok { 213 return n, false 214 } 215 n.L = node.(ExprNode) 216 217 node, ok = n.R.Accept(v) 218 if !ok { 219 return n, false 220 } 221 n.R = node.(ExprNode) 222 223 return v.Leave(n) 224 } 225 226 // WhenClause is the when clause in Case expression for "when condition then result". 227 type WhenClause struct { 228 node 229 // Expr is the condition expression in WhenClause. 230 Expr ExprNode 231 // Result is the result expression in WhenClause. 232 Result ExprNode 233 } 234 235 // Restore implements Node interface. 236 func (n *WhenClause) Restore(ctx *format.RestoreCtx) error { 237 ctx.WriteKeyWord("WHEN ") 238 if err := n.Expr.Restore(ctx); err != nil { 239 return errors.Annotate(err, "An error occurred while restore WhenClauses.Expr") 240 } 241 ctx.WriteKeyWord(" THEN ") 242 if err := n.Result.Restore(ctx); err != nil { 243 return errors.Annotate(err, "An error occurred while restore WhenClauses.Result") 244 } 245 return nil 246 } 247 248 // Accept implements Node Accept interface. 249 func (n *WhenClause) Accept(v Visitor) (Node, bool) { 250 newNode, skipChildren := v.Enter(n) 251 if skipChildren { 252 return v.Leave(newNode) 253 } 254 255 n = newNode.(*WhenClause) 256 node, ok := n.Expr.Accept(v) 257 if !ok { 258 return n, false 259 } 260 n.Expr = node.(ExprNode) 261 262 node, ok = n.Result.Accept(v) 263 if !ok { 264 return n, false 265 } 266 n.Result = node.(ExprNode) 267 return v.Leave(n) 268 } 269 270 // CaseExpr is the case expression. 271 type CaseExpr struct { 272 exprNode 273 // Value is the compare value expression. 274 Value ExprNode 275 // WhenClauses is the condition check expression. 276 WhenClauses []*WhenClause 277 // ElseClause is the else result expression. 278 ElseClause ExprNode 279 } 280 281 // Restore implements Node interface. 282 func (n *CaseExpr) Restore(ctx *format.RestoreCtx) error { 283 ctx.WriteKeyWord("CASE") 284 if n.Value != nil { 285 ctx.WritePlain(" ") 286 if err := n.Value.Restore(ctx); err != nil { 287 return errors.Annotate(err, "An error occurred while restore CaseExpr.Value") 288 } 289 } 290 for _, clause := range n.WhenClauses { 291 ctx.WritePlain(" ") 292 if err := clause.Restore(ctx); err != nil { 293 return errors.Annotate(err, "An error occurred while restore CaseExpr.WhenClauses") 294 } 295 } 296 if n.ElseClause != nil { 297 ctx.WriteKeyWord(" ELSE ") 298 if err := n.ElseClause.Restore(ctx); err != nil { 299 return errors.Annotate(err, "An error occurred while restore CaseExpr.ElseClause") 300 } 301 } 302 ctx.WriteKeyWord(" END") 303 304 return nil 305 } 306 307 // Format the ExprNode into a Writer. 308 func (n *CaseExpr) Format(w io.Writer) { 309 fmt.Fprint(w, "CASE") 310 // Because the presence of `case when` syntax, `Value` could be nil and we need check this. 311 if n.Value != nil { 312 fmt.Fprint(w, " ") 313 n.Value.Format(w) 314 } 315 for _, clause := range n.WhenClauses { 316 fmt.Fprint(w, " ") 317 fmt.Fprint(w, "WHEN ") 318 clause.Expr.Format(w) 319 fmt.Fprint(w, " THEN ") 320 clause.Result.Format(w) 321 } 322 if n.ElseClause != nil { 323 fmt.Fprint(w, " ELSE ") 324 n.ElseClause.Format(w) 325 } 326 fmt.Fprint(w, " END") 327 } 328 329 // Accept implements Node Accept interface. 330 func (n *CaseExpr) Accept(v Visitor) (Node, bool) { 331 newNode, skipChildren := v.Enter(n) 332 if skipChildren { 333 return v.Leave(newNode) 334 } 335 336 n = newNode.(*CaseExpr) 337 if n.Value != nil { 338 node, ok := n.Value.Accept(v) 339 if !ok { 340 return n, false 341 } 342 n.Value = node.(ExprNode) 343 } 344 for i, val := range n.WhenClauses { 345 node, ok := val.Accept(v) 346 if !ok { 347 return n, false 348 } 349 n.WhenClauses[i] = node.(*WhenClause) 350 } 351 if n.ElseClause != nil { 352 node, ok := n.ElseClause.Accept(v) 353 if !ok { 354 return n, false 355 } 356 n.ElseClause = node.(ExprNode) 357 } 358 return v.Leave(n) 359 } 360 361 // SubqueryExpr represents a subquery. 362 type SubqueryExpr struct { 363 exprNode 364 // Query is the query SelectNode. 365 Query ResultSetNode 366 Evaluated bool 367 Correlated bool 368 MultiRows bool 369 Exists bool 370 } 371 372 func (*SubqueryExpr) resultSet() {} 373 374 // Restore implements Node interface. 375 func (n *SubqueryExpr) Restore(ctx *format.RestoreCtx) error { 376 ctx.WritePlain("(") 377 if err := n.Query.Restore(ctx); err != nil { 378 return errors.Annotate(err, "An error occurred while restore SubqueryExpr.Query") 379 } 380 ctx.WritePlain(")") 381 return nil 382 } 383 384 // Format the ExprNode into a Writer. 385 func (n *SubqueryExpr) Format(w io.Writer) { 386 panic("Not implemented") 387 } 388 389 // Accept implements Node Accept interface. 390 func (n *SubqueryExpr) Accept(v Visitor) (Node, bool) { 391 newNode, skipChildren := v.Enter(n) 392 if skipChildren { 393 return v.Leave(newNode) 394 } 395 n = newNode.(*SubqueryExpr) 396 node, ok := n.Query.Accept(v) 397 if !ok { 398 return n, false 399 } 400 n.Query = node.(ResultSetNode) 401 return v.Leave(n) 402 } 403 404 // CompareSubqueryExpr is the expression for "expr cmp (select ...)". 405 // See https://dev.mysql.com/doc/refman/5.7/en/comparisons-using-subqueries.html 406 // See https://dev.mysql.com/doc/refman/5.7/en/any-in-some-subqueries.html 407 // See https://dev.mysql.com/doc/refman/5.7/en/all-subqueries.html 408 type CompareSubqueryExpr struct { 409 exprNode 410 // L is the left expression 411 L ExprNode 412 // Op is the comparison opcode. 413 Op opcode.Op 414 // R is the subquery for right expression, may be rewritten to other type of expression. 415 R ExprNode 416 // All is true, we should compare all records in subquery. 417 All bool 418 } 419 420 // Restore implements Node interface. 421 func (n *CompareSubqueryExpr) Restore(ctx *format.RestoreCtx) error { 422 if err := n.L.Restore(ctx); err != nil { 423 return errors.Annotate(err, "An error occurred while restore CompareSubqueryExpr.L") 424 } 425 if err := restoreBinaryOpWithSpacesAround(ctx, n.Op); err != nil { 426 return errors.Annotate(err, "An error occurred while restore CompareSubqueryExpr.Op") 427 } 428 if n.All { 429 ctx.WriteKeyWord("ALL ") 430 } else { 431 ctx.WriteKeyWord("ANY ") 432 } 433 if err := n.R.Restore(ctx); err != nil { 434 return errors.Annotate(err, "An error occurred while restore CompareSubqueryExpr.R") 435 } 436 return nil 437 } 438 439 // Format the ExprNode into a Writer. 440 func (n *CompareSubqueryExpr) Format(w io.Writer) { 441 panic("Not implemented") 442 } 443 444 // Accept implements Node Accept interface. 445 func (n *CompareSubqueryExpr) Accept(v Visitor) (Node, bool) { 446 newNode, skipChildren := v.Enter(n) 447 if skipChildren { 448 return v.Leave(newNode) 449 } 450 n = newNode.(*CompareSubqueryExpr) 451 node, ok := n.L.Accept(v) 452 if !ok { 453 return n, false 454 } 455 n.L = node.(ExprNode) 456 node, ok = n.R.Accept(v) 457 if !ok { 458 return n, false 459 } 460 n.R = node.(ExprNode) 461 return v.Leave(n) 462 } 463 464 // TableNameExpr represents a table-level object name expression, such as sequence/table/view etc. 465 type TableNameExpr struct { 466 exprNode 467 468 // Name is the referenced object name expression. 469 Name *TableName 470 } 471 472 // Restore implements Node interface. 473 func (n *TableNameExpr) Restore(ctx *format.RestoreCtx) error { 474 if err := n.Name.Restore(ctx); err != nil { 475 return errors.Trace(err) 476 } 477 return nil 478 } 479 480 // Format the ExprNode into a Writer. 481 func (n *TableNameExpr) Format(w io.Writer) { 482 dbName, tbName := n.Name.Schema.L, n.Name.Name.L 483 if dbName == "" { 484 fmt.Fprintf(w, "`%s`", tbName) 485 } else { 486 fmt.Fprintf(w, "`%s`.`%s`", dbName, tbName) 487 } 488 } 489 490 // Accept implements Node Accept interface. 491 func (n *TableNameExpr) Accept(v Visitor) (Node, bool) { 492 newNode, skipChildren := v.Enter(n) 493 if skipChildren { 494 return v.Leave(newNode) 495 } 496 n = newNode.(*TableNameExpr) 497 node, ok := n.Name.Accept(v) 498 if !ok { 499 return n, false 500 } 501 n.Name = node.(*TableName) 502 return v.Leave(n) 503 } 504 505 // ColumnName represents column name. 506 type ColumnName struct { 507 node 508 Schema model.CIStr 509 Table model.CIStr 510 Name model.CIStr 511 } 512 513 // Restore implements Node interface. 514 func (n *ColumnName) Restore(ctx *format.RestoreCtx) error { 515 if n.Schema.O != "" && !ctx.IsCTETableName(n.Table.L) && !ctx.Flags.HasWithoutSchemaNameFlag() { 516 ctx.WriteName(n.Schema.O) 517 ctx.WritePlain(".") 518 } 519 if n.Table.O != "" && !ctx.Flags.HasWithoutTableNameFlag() { 520 ctx.WriteName(n.Table.O) 521 ctx.WritePlain(".") 522 } 523 ctx.WriteName(n.Name.O) 524 return nil 525 } 526 527 // Accept implements Node Accept interface. 528 func (n *ColumnName) Accept(v Visitor) (Node, bool) { 529 newNode, skipChildren := v.Enter(n) 530 if skipChildren { 531 return v.Leave(newNode) 532 } 533 n = newNode.(*ColumnName) 534 return v.Leave(n) 535 } 536 537 // String implements Stringer interface. 538 func (n *ColumnName) String() string { 539 result := n.Name.L 540 if n.Table.L != "" { 541 result = n.Table.L + "." + result 542 } 543 if n.Schema.L != "" { 544 result = n.Schema.L + "." + result 545 } 546 return result 547 } 548 549 // OrigColName returns the full original column name. 550 func (n *ColumnName) OrigColName() (ret string) { 551 ret = n.Name.O 552 if n.Table.O == "" { 553 return 554 } 555 ret = n.Table.O + "." + ret 556 if n.Schema.O == "" { 557 return 558 } 559 ret = n.Schema.O + "." + ret 560 return 561 } 562 563 // ColumnNameExpr represents a column name expression. 564 type ColumnNameExpr struct { 565 exprNode 566 567 // Name is the referenced column name. 568 Name *ColumnName 569 570 // Refer is the result field the column name refers to. 571 // The value of Refer.Expr is used as the value of the expression. 572 Refer *ResultField 573 } 574 575 // Restore implements Node interface. 576 func (n *ColumnNameExpr) Restore(ctx *format.RestoreCtx) error { 577 if err := n.Name.Restore(ctx); err != nil { 578 return errors.Trace(err) 579 } 580 return nil 581 } 582 583 // Format the ExprNode into a Writer. 584 func (n *ColumnNameExpr) Format(w io.Writer) { 585 name := strings.ReplaceAll(n.Name.String(), ".", "`.`") 586 fmt.Fprintf(w, "`%s`", name) 587 } 588 589 // Accept implements Node Accept interface. 590 func (n *ColumnNameExpr) Accept(v Visitor) (Node, bool) { 591 newNode, skipChildren := v.Enter(n) 592 if skipChildren { 593 return v.Leave(newNode) 594 } 595 n = newNode.(*ColumnNameExpr) 596 node, ok := n.Name.Accept(v) 597 if !ok { 598 return n, false 599 } 600 n.Name = node.(*ColumnName) 601 return v.Leave(n) 602 } 603 604 // DefaultExpr is the default expression using default value for a column. 605 type DefaultExpr struct { 606 exprNode 607 // Name is the column name. 608 Name *ColumnName 609 } 610 611 // Restore implements Node interface. 612 func (n *DefaultExpr) Restore(ctx *format.RestoreCtx) error { 613 ctx.WriteKeyWord("DEFAULT") 614 if n.Name != nil { 615 ctx.WritePlain("(") 616 if err := n.Name.Restore(ctx); err != nil { 617 return errors.Annotate(err, "An error occurred while restore DefaultExpr.Name") 618 } 619 ctx.WritePlain(")") 620 } 621 return nil 622 } 623 624 // Format the ExprNode into a Writer. 625 func (n *DefaultExpr) Format(w io.Writer) { 626 fmt.Fprint(w, "DEFAULT") 627 if n.Name != nil { 628 panic("Not implemented") 629 } 630 } 631 632 // Accept implements Node Accept interface. 633 func (n *DefaultExpr) Accept(v Visitor) (Node, bool) { 634 newNode, skipChildren := v.Enter(n) 635 if skipChildren { 636 return v.Leave(newNode) 637 } 638 n = newNode.(*DefaultExpr) 639 return v.Leave(n) 640 } 641 642 // ExistsSubqueryExpr is the expression for "exists (select ...)". 643 // See https://dev.mysql.com/doc/refman/5.7/en/exists-and-not-exists-subqueries.html 644 type ExistsSubqueryExpr struct { 645 exprNode 646 // Sel is the subquery, may be rewritten to other type of expression. 647 Sel ExprNode 648 // Not is true, the expression is "not exists". 649 Not bool 650 } 651 652 // Restore implements Node interface. 653 func (n *ExistsSubqueryExpr) Restore(ctx *format.RestoreCtx) error { 654 if n.Not { 655 ctx.WriteKeyWord("NOT EXISTS ") 656 } else { 657 ctx.WriteKeyWord("EXISTS ") 658 } 659 if err := n.Sel.Restore(ctx); err != nil { 660 return errors.Annotate(err, "An error occurred while restore ExistsSubqueryExpr.Sel") 661 } 662 return nil 663 } 664 665 // Format the ExprNode into a Writer. 666 func (n *ExistsSubqueryExpr) Format(w io.Writer) { 667 panic("Not implemented") 668 } 669 670 // Accept implements Node Accept interface. 671 func (n *ExistsSubqueryExpr) Accept(v Visitor) (Node, bool) { 672 newNode, skipChildren := v.Enter(n) 673 if skipChildren { 674 return v.Leave(newNode) 675 } 676 n = newNode.(*ExistsSubqueryExpr) 677 node, ok := n.Sel.Accept(v) 678 if !ok { 679 return n, false 680 } 681 n.Sel = node.(ExprNode) 682 return v.Leave(n) 683 } 684 685 // PatternInExpr is the expression for in operator, like "expr in (1, 2, 3)" or "expr in (select c from t)". 686 type PatternInExpr struct { 687 exprNode 688 // Expr is the value expression to be compared. 689 Expr ExprNode 690 // List is the list expression in compare list. 691 List []ExprNode 692 // Not is true, the expression is "not in". 693 Not bool 694 // Sel is the subquery, may be rewritten to other type of expression. 695 Sel ExprNode 696 } 697 698 // Restore implements Node interface. 699 func (n *PatternInExpr) Restore(ctx *format.RestoreCtx) error { 700 if err := n.Expr.Restore(ctx); err != nil { 701 return errors.Annotate(err, "An error occurred while restore PatternInExpr.Expr") 702 } 703 if n.Not { 704 ctx.WriteKeyWord(" NOT IN ") 705 } else { 706 ctx.WriteKeyWord(" IN ") 707 } 708 if n.Sel != nil { 709 if err := n.Sel.Restore(ctx); err != nil { 710 return errors.Annotate(err, "An error occurred while restore PatternInExpr.Sel") 711 } 712 } else { 713 ctx.WritePlain("(") 714 for i, expr := range n.List { 715 if i != 0 { 716 ctx.WritePlain(",") 717 } 718 if err := expr.Restore(ctx); err != nil { 719 return errors.Annotatef(err, "An error occurred while restore PatternInExpr.List[%d]", i) 720 } 721 } 722 ctx.WritePlain(")") 723 } 724 return nil 725 } 726 727 // Format the ExprNode into a Writer. 728 func (n *PatternInExpr) Format(w io.Writer) { 729 n.Expr.Format(w) 730 if n.Not { 731 fmt.Fprint(w, " NOT IN (") 732 } else { 733 fmt.Fprint(w, " IN (") 734 } 735 for i, expr := range n.List { 736 if i != 0 { 737 fmt.Fprint(w, ",") 738 } 739 expr.Format(w) 740 } 741 fmt.Fprint(w, ")") 742 } 743 744 // Accept implements Node Accept interface. 745 func (n *PatternInExpr) Accept(v Visitor) (Node, bool) { 746 newNode, skipChildren := v.Enter(n) 747 if skipChildren { 748 return v.Leave(newNode) 749 } 750 n = newNode.(*PatternInExpr) 751 node, ok := n.Expr.Accept(v) 752 if !ok { 753 return n, false 754 } 755 n.Expr = node.(ExprNode) 756 for i, val := range n.List { 757 node, ok = val.Accept(v) 758 if !ok { 759 return n, false 760 } 761 n.List[i] = node.(ExprNode) 762 } 763 if n.Sel != nil { 764 node, ok = n.Sel.Accept(v) 765 if !ok { 766 return n, false 767 } 768 n.Sel = node.(ExprNode) 769 } 770 return v.Leave(n) 771 } 772 773 // IsNullExpr is the expression for null check. 774 type IsNullExpr struct { 775 exprNode 776 // Expr is the expression to be checked. 777 Expr ExprNode 778 // Not is true, the expression is "is not null". 779 Not bool 780 } 781 782 // Restore implements Node interface. 783 func (n *IsNullExpr) Restore(ctx *format.RestoreCtx) error { 784 if err := n.Expr.Restore(ctx); err != nil { 785 return errors.Trace(err) 786 } 787 if n.Not { 788 ctx.WriteKeyWord(" IS NOT NULL") 789 } else { 790 ctx.WriteKeyWord(" IS NULL") 791 } 792 return nil 793 } 794 795 // Format the ExprNode into a Writer. 796 func (n *IsNullExpr) Format(w io.Writer) { 797 n.Expr.Format(w) 798 if n.Not { 799 fmt.Fprint(w, " IS NOT NULL") 800 return 801 } 802 fmt.Fprint(w, " IS NULL") 803 } 804 805 // Accept implements Node Accept interface. 806 func (n *IsNullExpr) Accept(v Visitor) (Node, bool) { 807 newNode, skipChildren := v.Enter(n) 808 if skipChildren { 809 return v.Leave(newNode) 810 } 811 n = newNode.(*IsNullExpr) 812 node, ok := n.Expr.Accept(v) 813 if !ok { 814 return n, false 815 } 816 n.Expr = node.(ExprNode) 817 return v.Leave(n) 818 } 819 820 // IsTruthExpr is the expression for true/false check. 821 type IsTruthExpr struct { 822 exprNode 823 // Expr is the expression to be checked. 824 Expr ExprNode 825 // Not is true, the expression is "is not true/false". 826 Not bool 827 // True indicates checking true or false. 828 True int64 829 } 830 831 // Restore implements Node interface. 832 func (n *IsTruthExpr) Restore(ctx *format.RestoreCtx) error { 833 if err := n.Expr.Restore(ctx); err != nil { 834 return errors.Trace(err) 835 } 836 if n.Not { 837 ctx.WriteKeyWord(" IS NOT") 838 } else { 839 ctx.WriteKeyWord(" IS") 840 } 841 if n.True > 0 { 842 ctx.WriteKeyWord(" TRUE") 843 } else { 844 ctx.WriteKeyWord(" FALSE") 845 } 846 return nil 847 } 848 849 // Format the ExprNode into a Writer. 850 func (n *IsTruthExpr) Format(w io.Writer) { 851 n.Expr.Format(w) 852 if n.Not { 853 fmt.Fprint(w, " IS NOT") 854 } else { 855 fmt.Fprint(w, " IS") 856 } 857 if n.True > 0 { 858 fmt.Fprint(w, " TRUE") 859 } else { 860 fmt.Fprint(w, " FALSE") 861 } 862 } 863 864 // Accept implements Node Accept interface. 865 func (n *IsTruthExpr) Accept(v Visitor) (Node, bool) { 866 newNode, skipChildren := v.Enter(n) 867 if skipChildren { 868 return v.Leave(newNode) 869 } 870 n = newNode.(*IsTruthExpr) 871 node, ok := n.Expr.Accept(v) 872 if !ok { 873 return n, false 874 } 875 n.Expr = node.(ExprNode) 876 return v.Leave(n) 877 } 878 879 // PatternLikeOrIlikeExpr is the expression for like operator, e.g, expr like "%123%" 880 type PatternLikeOrIlikeExpr struct { 881 exprNode 882 // Expr is the expression to be checked. 883 Expr ExprNode 884 // Pattern is the like expression. 885 Pattern ExprNode 886 // Not is true, the expression is "not like". 887 Not bool 888 889 IsLike bool 890 891 Escape byte 892 893 PatChars []byte 894 PatTypes []byte 895 } 896 897 // Restore implements Node interface. 898 func (n *PatternLikeOrIlikeExpr) Restore(ctx *format.RestoreCtx) error { 899 if err := n.Expr.Restore(ctx); err != nil { 900 return errors.Annotate(err, "An error occurred while restore PatternLikeOrIlikeExpr.Expr") 901 } 902 903 if n.IsLike { 904 if n.Not { 905 ctx.WriteKeyWord(" NOT LIKE ") 906 } else { 907 ctx.WriteKeyWord(" LIKE ") 908 } 909 } else { 910 if n.Not { 911 ctx.WriteKeyWord(" NOT ILIKE ") 912 } else { 913 ctx.WriteKeyWord(" ILIKE ") 914 } 915 } 916 917 if err := n.Pattern.Restore(ctx); err != nil { 918 return errors.Annotate(err, "An error occurred while restore PatternLikeOrIlikeExpr.Pattern") 919 } 920 921 escape := string(n.Escape) 922 if escape != "\\" { 923 ctx.WriteKeyWord(" ESCAPE ") 924 ctx.WriteString(escape) 925 } 926 return nil 927 } 928 929 // Format the ExprNode into a Writer. 930 func (n *PatternLikeOrIlikeExpr) Format(w io.Writer) { 931 n.Expr.Format(w) 932 if n.IsLike { 933 if n.Not { 934 fmt.Fprint(w, " NOT LIKE ") 935 } else { 936 fmt.Fprint(w, " LIKE ") 937 } 938 } else { 939 if n.Not { 940 fmt.Fprint(w, " NOT ILIKE ") 941 } else { 942 fmt.Fprint(w, " ILIKE ") 943 } 944 } 945 946 n.Pattern.Format(w) 947 if n.Escape != '\\' { 948 fmt.Fprint(w, " ESCAPE ") 949 fmt.Fprintf(w, "'%c'", n.Escape) 950 } 951 } 952 953 // Accept implements Node Accept interface. 954 func (n *PatternLikeOrIlikeExpr) Accept(v Visitor) (Node, bool) { 955 newNode, skipChildren := v.Enter(n) 956 if skipChildren { 957 return v.Leave(newNode) 958 } 959 n = newNode.(*PatternLikeOrIlikeExpr) 960 if n.Expr != nil { 961 node, ok := n.Expr.Accept(v) 962 if !ok { 963 return n, false 964 } 965 n.Expr = node.(ExprNode) 966 } 967 if n.Pattern != nil { 968 node, ok := n.Pattern.Accept(v) 969 if !ok { 970 return n, false 971 } 972 n.Pattern = node.(ExprNode) 973 } 974 return v.Leave(n) 975 } 976 977 // ParamMarkerExpr expression holds a place for another expression. 978 // Used in parsing prepare statement. 979 type ParamMarkerExpr interface { 980 ValueExpr 981 SetOrder(int) 982 } 983 984 // ParenthesesExpr is the parentheses expression. 985 type ParenthesesExpr struct { 986 exprNode 987 // Expr is the expression in parentheses. 988 Expr ExprNode 989 } 990 991 // Restore implements Node interface. 992 func (n *ParenthesesExpr) Restore(ctx *format.RestoreCtx) error { 993 ctx.WritePlain("(") 994 if err := n.Expr.Restore(ctx); err != nil { 995 return errors.Annotate(err, "An error occurred when restore ParenthesesExpr.Expr") 996 } 997 ctx.WritePlain(")") 998 return nil 999 } 1000 1001 // Format the ExprNode into a Writer. 1002 func (n *ParenthesesExpr) Format(w io.Writer) { 1003 fmt.Fprint(w, "(") 1004 n.Expr.Format(w) 1005 fmt.Fprint(w, ")") 1006 } 1007 1008 // Accept implements Node Accept interface. 1009 func (n *ParenthesesExpr) Accept(v Visitor) (Node, bool) { 1010 newNode, skipChildren := v.Enter(n) 1011 if skipChildren { 1012 return v.Leave(newNode) 1013 } 1014 n = newNode.(*ParenthesesExpr) 1015 if n.Expr != nil { 1016 node, ok := n.Expr.Accept(v) 1017 if !ok { 1018 return n, false 1019 } 1020 n.Expr = node.(ExprNode) 1021 } 1022 return v.Leave(n) 1023 } 1024 1025 // PositionExpr is the expression for order by and group by position. 1026 // MySQL use position expression started from 1, it looks a little confused inner. 1027 // maybe later we will use 0 at first. 1028 type PositionExpr struct { 1029 exprNode 1030 // N is the position, started from 1 now. 1031 N int 1032 // P is the parameterized position. 1033 P ExprNode 1034 // Refer is the result field the position refers to. 1035 Refer *ResultField 1036 } 1037 1038 // Restore implements Node interface. 1039 func (n *PositionExpr) Restore(ctx *format.RestoreCtx) error { 1040 ctx.WritePlainf("%d", n.N) 1041 return nil 1042 } 1043 1044 // Format the ExprNode into a Writer. 1045 func (n *PositionExpr) Format(w io.Writer) { 1046 panic("Not implemented") 1047 } 1048 1049 // Accept implements Node Accept interface. 1050 func (n *PositionExpr) Accept(v Visitor) (Node, bool) { 1051 newNode, skipChildren := v.Enter(n) 1052 if skipChildren { 1053 return v.Leave(newNode) 1054 } 1055 n = newNode.(*PositionExpr) 1056 if n.P != nil { 1057 node, ok := n.P.Accept(v) 1058 if !ok { 1059 return n, false 1060 } 1061 n.P = node.(ExprNode) 1062 } 1063 return v.Leave(n) 1064 } 1065 1066 // PatternRegexpExpr is the pattern expression for pattern match. 1067 type PatternRegexpExpr struct { 1068 exprNode 1069 // Expr is the expression to be checked. 1070 Expr ExprNode 1071 // Pattern is the expression for pattern. 1072 Pattern ExprNode 1073 // Not is true, the expression is "not rlike", 1074 Not bool 1075 1076 // Re is the compiled regexp. 1077 Re *regexp.Regexp 1078 // Sexpr is the string for Expr expression. 1079 Sexpr *string 1080 } 1081 1082 // Restore implements Node interface. 1083 func (n *PatternRegexpExpr) Restore(ctx *format.RestoreCtx) error { 1084 if err := n.Expr.Restore(ctx); err != nil { 1085 return errors.Annotate(err, "An error occurred while restore PatternRegexpExpr.Expr") 1086 } 1087 1088 if n.Not { 1089 ctx.WriteKeyWord(" NOT REGEXP ") 1090 } else { 1091 ctx.WriteKeyWord(" REGEXP ") 1092 } 1093 1094 if err := n.Pattern.Restore(ctx); err != nil { 1095 return errors.Annotate(err, "An error occurred while restore PatternRegexpExpr.Pattern") 1096 } 1097 1098 return nil 1099 } 1100 1101 // Format the ExprNode into a Writer. 1102 func (n *PatternRegexpExpr) Format(w io.Writer) { 1103 n.Expr.Format(w) 1104 if n.Not { 1105 fmt.Fprint(w, " NOT REGEXP ") 1106 } else { 1107 fmt.Fprint(w, " REGEXP ") 1108 } 1109 n.Pattern.Format(w) 1110 } 1111 1112 // Accept implements Node Accept interface. 1113 func (n *PatternRegexpExpr) Accept(v Visitor) (Node, bool) { 1114 newNode, skipChildren := v.Enter(n) 1115 if skipChildren { 1116 return v.Leave(newNode) 1117 } 1118 n = newNode.(*PatternRegexpExpr) 1119 node, ok := n.Expr.Accept(v) 1120 if !ok { 1121 return n, false 1122 } 1123 n.Expr = node.(ExprNode) 1124 node, ok = n.Pattern.Accept(v) 1125 if !ok { 1126 return n, false 1127 } 1128 n.Pattern = node.(ExprNode) 1129 return v.Leave(n) 1130 } 1131 1132 // RowExpr is the expression for row constructor. 1133 // See https://dev.mysql.com/doc/refman/5.7/en/row-subqueries.html 1134 type RowExpr struct { 1135 exprNode 1136 1137 Values []ExprNode 1138 } 1139 1140 // Restore implements Node interface. 1141 func (n *RowExpr) Restore(ctx *format.RestoreCtx) error { 1142 ctx.WriteKeyWord("ROW") 1143 ctx.WritePlain("(") 1144 for i, v := range n.Values { 1145 if i != 0 { 1146 ctx.WritePlain(",") 1147 } 1148 if err := v.Restore(ctx); err != nil { 1149 return errors.Annotatef(err, "An error occurred when restore RowExpr.Values[%v]", i) 1150 } 1151 } 1152 ctx.WritePlain(")") 1153 return nil 1154 } 1155 1156 // Format the ExprNode into a Writer. 1157 func (n *RowExpr) Format(w io.Writer) { 1158 panic("Not implemented") 1159 } 1160 1161 // Accept implements Node Accept interface. 1162 func (n *RowExpr) Accept(v Visitor) (Node, bool) { 1163 newNode, skipChildren := v.Enter(n) 1164 if skipChildren { 1165 return v.Leave(newNode) 1166 } 1167 n = newNode.(*RowExpr) 1168 for i, val := range n.Values { 1169 node, ok := val.Accept(v) 1170 if !ok { 1171 return n, false 1172 } 1173 n.Values[i] = node.(ExprNode) 1174 } 1175 return v.Leave(n) 1176 } 1177 1178 // UnaryOperationExpr is the expression for unary operator. 1179 type UnaryOperationExpr struct { 1180 exprNode 1181 // Op is the operator opcode. 1182 Op opcode.Op 1183 // V is the unary expression. 1184 V ExprNode 1185 } 1186 1187 // Restore implements Node interface. 1188 func (n *UnaryOperationExpr) Restore(ctx *format.RestoreCtx) error { 1189 if err := n.Op.Restore(ctx); err != nil { 1190 return errors.Trace(err) 1191 } 1192 if err := n.V.Restore(ctx); err != nil { 1193 return errors.Trace(err) 1194 } 1195 return nil 1196 } 1197 1198 // Format the ExprNode into a Writer. 1199 func (n *UnaryOperationExpr) Format(w io.Writer) { 1200 n.Op.Format(w) 1201 n.V.Format(w) 1202 } 1203 1204 // Accept implements Node Accept interface. 1205 func (n *UnaryOperationExpr) Accept(v Visitor) (Node, bool) { 1206 newNode, skipChildren := v.Enter(n) 1207 if skipChildren { 1208 return v.Leave(newNode) 1209 } 1210 n = newNode.(*UnaryOperationExpr) 1211 node, ok := n.V.Accept(v) 1212 if !ok { 1213 return n, false 1214 } 1215 n.V = node.(ExprNode) 1216 return v.Leave(n) 1217 } 1218 1219 // ValuesExpr is the expression used in INSERT VALUES. 1220 type ValuesExpr struct { 1221 exprNode 1222 // Column is column name. 1223 Column *ColumnNameExpr 1224 } 1225 1226 // Restore implements Node interface. 1227 func (n *ValuesExpr) Restore(ctx *format.RestoreCtx) error { 1228 ctx.WriteKeyWord("VALUES") 1229 ctx.WritePlain("(") 1230 if err := n.Column.Restore(ctx); err != nil { 1231 return errors.Annotate(err, "An error occurred while restore ValuesExpr.Column") 1232 } 1233 ctx.WritePlain(")") 1234 1235 return nil 1236 } 1237 1238 // Format the ExprNode into a Writer. 1239 func (n *ValuesExpr) Format(w io.Writer) { 1240 panic("Not implemented") 1241 } 1242 1243 // Accept implements Node Accept interface. 1244 func (n *ValuesExpr) Accept(v Visitor) (Node, bool) { 1245 newNode, skipChildren := v.Enter(n) 1246 if skipChildren { 1247 return v.Leave(newNode) 1248 } 1249 n = newNode.(*ValuesExpr) 1250 node, ok := n.Column.Accept(v) 1251 if !ok { 1252 return n, false 1253 } 1254 // `node` may be *ast.ValueExpr, to avoid panic, we write `_` and do not use 1255 // it. 1256 n.Column, _ = node.(*ColumnNameExpr) 1257 return v.Leave(n) 1258 } 1259 1260 // VariableExpr is the expression for variable. 1261 type VariableExpr struct { 1262 exprNode 1263 // Name is the variable name. 1264 Name string 1265 // IsGlobal indicates whether this variable is global. 1266 IsGlobal bool 1267 // IsSystem indicates whether this variable is a system variable in current session. 1268 IsSystem bool 1269 // ExplicitScope indicates whether this variable scope is set explicitly. 1270 ExplicitScope bool 1271 // Value is the variable value. 1272 Value ExprNode 1273 } 1274 1275 // Restore implements Node interface. 1276 func (n *VariableExpr) Restore(ctx *format.RestoreCtx) error { 1277 if n.IsSystem { 1278 ctx.WritePlain("@@") 1279 if n.ExplicitScope { 1280 if n.IsGlobal { 1281 ctx.WriteKeyWord("GLOBAL") 1282 } else { 1283 ctx.WriteKeyWord("SESSION") 1284 } 1285 ctx.WritePlain(".") 1286 } 1287 } else { 1288 ctx.WritePlain("@") 1289 } 1290 ctx.WriteName(n.Name) 1291 1292 if n.Value != nil { 1293 ctx.WritePlain(":=") 1294 if err := n.Value.Restore(ctx); err != nil { 1295 return errors.Annotate(err, "An error occurred while restore VariableExpr.Value") 1296 } 1297 } 1298 1299 return nil 1300 } 1301 1302 // Format the ExprNode into a Writer. 1303 func (n *VariableExpr) Format(w io.Writer) { 1304 panic("Not implemented") 1305 } 1306 1307 // Accept implements Node Accept interface. 1308 func (n *VariableExpr) Accept(v Visitor) (Node, bool) { 1309 newNode, skipChildren := v.Enter(n) 1310 if skipChildren { 1311 return v.Leave(newNode) 1312 } 1313 n = newNode.(*VariableExpr) 1314 if n.Value == nil { 1315 return v.Leave(n) 1316 } 1317 1318 node, ok := n.Value.Accept(v) 1319 if !ok { 1320 return n, false 1321 } 1322 n.Value = node.(ExprNode) 1323 return v.Leave(n) 1324 } 1325 1326 // MaxValueExpr is the expression for "maxvalue" used in partition. 1327 type MaxValueExpr struct { 1328 exprNode 1329 } 1330 1331 // Restore implements Node interface. 1332 func (n *MaxValueExpr) Restore(ctx *format.RestoreCtx) error { 1333 ctx.WriteKeyWord("MAXVALUE") 1334 return nil 1335 } 1336 1337 // Format the ExprNode into a Writer. 1338 func (n *MaxValueExpr) Format(w io.Writer) { 1339 fmt.Fprint(w, "MAXVALUE") 1340 } 1341 1342 // Accept implements Node Accept interface. 1343 func (n *MaxValueExpr) Accept(v Visitor) (Node, bool) { 1344 newNode, skipChildren := v.Enter(n) 1345 if skipChildren { 1346 return v.Leave(newNode) 1347 } 1348 return v.Leave(n) 1349 } 1350 1351 // MatchAgainst is the expression for matching against fulltext index. 1352 type MatchAgainst struct { 1353 exprNode 1354 // ColumnNames are the columns to match. 1355 ColumnNames []*ColumnName 1356 // Against 1357 Against ExprNode 1358 // Modifier 1359 Modifier FulltextSearchModifier 1360 } 1361 1362 func (n *MatchAgainst) Restore(ctx *format.RestoreCtx) error { 1363 ctx.WriteKeyWord("MATCH") 1364 ctx.WritePlain(" (") 1365 for i, v := range n.ColumnNames { 1366 if i != 0 { 1367 ctx.WritePlain(",") 1368 } 1369 if err := v.Restore(ctx); err != nil { 1370 return errors.Annotatef(err, "An error occurred while restore MatchAgainst.ColumnNames[%d]", i) 1371 } 1372 } 1373 ctx.WritePlain(") ") 1374 ctx.WriteKeyWord("AGAINST") 1375 ctx.WritePlain(" (") 1376 if err := n.Against.Restore(ctx); err != nil { 1377 return errors.Annotate(err, "An error occurred while restore MatchAgainst.Against") 1378 } 1379 if n.Modifier.IsBooleanMode() { 1380 ctx.WritePlain(" IN BOOLEAN MODE") 1381 if n.Modifier.WithQueryExpansion() { 1382 return errors.New("BOOLEAN MODE doesn't support QUERY EXPANSION") 1383 } 1384 } else if n.Modifier.WithQueryExpansion() { 1385 ctx.WritePlain(" WITH QUERY EXPANSION") 1386 } 1387 ctx.WritePlain(")") 1388 return nil 1389 } 1390 1391 func (n *MatchAgainst) Format(w io.Writer) { 1392 fmt.Fprint(w, "MATCH(") 1393 for i, v := range n.ColumnNames { 1394 if i != 0 { 1395 fmt.Fprintf(w, ",%s", v.String()) 1396 } else { 1397 fmt.Fprint(w, v.String()) 1398 } 1399 } 1400 fmt.Fprint(w, ") AGAINST(") 1401 n.Against.Format(w) 1402 if n.Modifier.IsBooleanMode() { 1403 fmt.Fprint(w, " IN BOOLEAN MODE") 1404 } else if n.Modifier.WithQueryExpansion() { 1405 fmt.Fprint(w, " WITH QUERY EXPANSION") 1406 } 1407 fmt.Fprint(w, ")") 1408 } 1409 1410 func (n *MatchAgainst) Accept(v Visitor) (Node, bool) { 1411 newNode, skipChildren := v.Enter(n) 1412 if skipChildren { 1413 return v.Leave(newNode) 1414 } 1415 n = newNode.(*MatchAgainst) 1416 for i, colName := range n.ColumnNames { 1417 newColName, ok := colName.Accept(v) 1418 if !ok { 1419 return n, false 1420 } 1421 n.ColumnNames[i] = newColName.(*ColumnName) 1422 } 1423 newAgainst, ok := n.Against.Accept(v) 1424 if !ok { 1425 return n, false 1426 } 1427 n.Against = newAgainst.(ExprNode) 1428 return v.Leave(n) 1429 } 1430 1431 // SetCollationExpr is the expression for the `COLLATE collation_name` clause. 1432 type SetCollationExpr struct { 1433 exprNode 1434 // Expr is the expression to be set. 1435 Expr ExprNode 1436 // Collate is the name of collation to set. 1437 Collate string 1438 } 1439 1440 // Restore implements Node interface. 1441 func (n *SetCollationExpr) Restore(ctx *format.RestoreCtx) error { 1442 if err := n.Expr.Restore(ctx); err != nil { 1443 return errors.Trace(err) 1444 } 1445 ctx.WriteKeyWord(" COLLATE ") 1446 ctx.WritePlain(n.Collate) 1447 return nil 1448 } 1449 1450 // Format the ExprNode into a Writer. 1451 func (n *SetCollationExpr) Format(w io.Writer) { 1452 n.Expr.Format(w) 1453 fmt.Fprintf(w, " COLLATE %s", n.Collate) 1454 } 1455 1456 // Accept implements Node Accept interface. 1457 func (n *SetCollationExpr) Accept(v Visitor) (Node, bool) { 1458 newNode, skipChildren := v.Enter(n) 1459 if skipChildren { 1460 return v.Leave(newNode) 1461 } 1462 n = newNode.(*SetCollationExpr) 1463 node, ok := n.Expr.Accept(v) 1464 if !ok { 1465 return n, false 1466 } 1467 n.Expr = node.(ExprNode) 1468 return v.Leave(n) 1469 } 1470 1471 type exprTextPositionCleaner struct { 1472 oldTextPos []int 1473 restore bool 1474 } 1475 1476 func (e *exprTextPositionCleaner) BeginRestore() { 1477 e.restore = true 1478 } 1479 1480 func (e *exprTextPositionCleaner) Enter(n Node) (node Node, skipChildren bool) { 1481 if e.restore { 1482 n.SetOriginTextPosition(e.oldTextPos[0]) 1483 e.oldTextPos = e.oldTextPos[1:] 1484 return n, false 1485 } 1486 e.oldTextPos = append(e.oldTextPos, n.OriginTextPosition()) 1487 n.SetOriginTextPosition(0) 1488 return n, false 1489 } 1490 1491 func (e *exprTextPositionCleaner) Leave(n Node) (node Node, ok bool) { 1492 return n, true 1493 } 1494 1495 // ExpressionDeepEqual compares the equivalence of two expressions. 1496 func ExpressionDeepEqual(a ExprNode, b ExprNode) bool { 1497 cleanerA := &exprTextPositionCleaner{} 1498 cleanerB := &exprTextPositionCleaner{} 1499 a.Accept(cleanerA) 1500 b.Accept(cleanerB) 1501 result := reflect.DeepEqual(a, b) 1502 cleanerA.BeginRestore() 1503 cleanerB.BeginRestore() 1504 a.Accept(cleanerA) 1505 b.Accept(cleanerB) 1506 return result 1507 }