parser_let_test.go 1.5 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273
  1. package parser
  2. import (
  3. "testing"
  4. "code.osinet.fr/fgm/waiig15/lexer"
  5. "code.osinet.fr/fgm/waiig15/ast"
  6. )
  7. func TestLetStatements(t *testing.T) {
  8. // Try removing the ident, the =, or both, to get human-readable errors.
  9. input := `
  10. let x = 5;
  11. let y = 10;
  12. let foobar = 838383;
  13. `
  14. l := lexer.New(input)
  15. p := New(l)
  16. program := p.ParseProgram()
  17. checkParserErrors(t, p)
  18. if program == nil {
  19. t.Fatalf("ParseProgram() returned nil.")
  20. }
  21. if len(program.Statements) != 3 {
  22. t.Fatalf("program.Statements does not contain 3 statements, got=%d",
  23. len(program.Statements))
  24. }
  25. tests := []struct {
  26. expectedIdentifier string
  27. }{
  28. {"x"},
  29. {"y"},
  30. {"foobar"},
  31. }
  32. for i, tt := range tests {
  33. stmt := program.Statements[i]
  34. if !testLetStatement(t, stmt, tt.expectedIdentifier) {
  35. return
  36. }
  37. }
  38. }
  39. func testLetStatement(t *testing.T, s ast.Statement, name string) bool {
  40. if s.TokenLiteral() != "let" {
  41. t.Errorf("s.TokenLiteral not 'let', got=%q", s.TokenLiteral())
  42. return false
  43. }
  44. // Statement is an interface, we need a concrete type for the value, and we
  45. // just determined this looked like a LetStatement.
  46. letStmt, ok := s.(*ast.LetStatement)
  47. if !ok {
  48. t.Errorf("s not *ast.LetStatement{}, got=%T", s)
  49. }
  50. if letStmt.Name.Value != name {
  51. t.Errorf("letStmt.Name.Value not %s, got=%s",
  52. name, letStmt.Name.Value)
  53. return false
  54. }
  55. if letStmt.Name.TokenLiteral() != name {
  56. t.Errorf("letStmt.Name.TokenLiteral not %s, got=%s",
  57. name, letStmt.Name.TokenLiteral())
  58. return false
  59. }
  60. return true
  61. }