parser_test.go 2.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114
  1. package parser
  2. import (
  3. "github/runnignwater/monkey/ast"
  4. "github/runnignwater/monkey/lexer"
  5. "testing"
  6. )
  7. /**
  8. * @Author: simon
  9. * @Author: ynwdlxm@163.com
  10. * @Date: 2022/10/2 下午10:40
  11. * @Desc: LetStatement test case
  12. */
  13. func TestLetStatements(t *testing.T) {
  14. input := `
  15. let x = 5;
  16. let y = 10;
  17. let foo = 838383;
  18. `
  19. l := lexer.New(input)
  20. p := New(l)
  21. program := p.ParseProgram()
  22. checkParseErrors(t, p)
  23. if program == nil {
  24. t.Fatalf("ParseProgram() return nil")
  25. }
  26. if len(program.Statements) != 3 {
  27. t.Fatalf("Program.Statements does not contain 3 statements. got=%d", len(program.Statements))
  28. }
  29. tests := []struct {
  30. expectedIdentifies string
  31. }{
  32. {"x"},
  33. {"y"},
  34. {"foo"},
  35. }
  36. for i, tt := range tests {
  37. stmt := program.Statements[i]
  38. if !testLetStatement(t, stmt, tt.expectedIdentifies) {
  39. return
  40. }
  41. }
  42. }
  43. func TestReturnStatements(t *testing.T) {
  44. input := `
  45. return 5;
  46. return 10;
  47. return add(a,10);
  48. `
  49. l := lexer.New(input)
  50. p := New(l)
  51. program := p.ParseProgram()
  52. checkParseErrors(t, p)
  53. if len(program.Statements) != 3 {
  54. t.Fatalf("Program.Statements does not contain 3 statements. got=%d", len(program.Statements))
  55. }
  56. for _, stmt := range program.Statements {
  57. returnStmt, ok := stmt.(*ast.ReturnStatement)
  58. if !ok {
  59. t.Errorf("stmt not *ast.ReturnStatement. got=%T", stmt)
  60. continue
  61. }
  62. if returnStmt.TokenLiteral() != "return" {
  63. t.Errorf("returnStmt.TokenLiteral not 'return', got %q", returnStmt.TokenLiteral())
  64. }
  65. }
  66. }
  67. func checkParseErrors(t *testing.T, p *Parser) {
  68. errors := p.errors
  69. if len(errors) == 0 {
  70. return
  71. }
  72. t.Errorf("parse has %d errors.", len(errors))
  73. for _, msg := range errors {
  74. t.Errorf("parse error: %q", msg)
  75. }
  76. t.FailNow()
  77. }
  78. func testLetStatement(t *testing.T, s ast.Statement, name string) bool {
  79. if s.TokenLiteral() != "let" {
  80. t.Errorf("s.TokenLiteral() not 'let'. got =%q", s.TokenLiteral())
  81. return false
  82. }
  83. letStmt, ok := s.(*ast.LetStatement)
  84. if !ok {
  85. t.Errorf("s is not *ast.LetStatement. got=%T", s)
  86. return false
  87. }
  88. if letStmt.Name.Value != name {
  89. t.Errorf("letStmt.Name.Value not '%s'. got=%s", name, letStmt.Name.Value)
  90. return false
  91. }
  92. if letStmt.Name.TokenLiteral() != name {
  93. t.Errorf("s.name not '%s. got=%s", name, letStmt.Name)
  94. return false
  95. }
  96. return true
  97. }