parser_test.go 3.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135
  1. package parser
  2. import (
  3. "bytes"
  4. "fmt"
  5. "io/ioutil"
  6. "os"
  7. "path/filepath"
  8. "runtime"
  9. "testing"
  10. "github.com/stretchr/testify/assert"
  11. "github.com/stretchr/testify/require"
  12. )
  13. const testDir = "testfiles"
  14. const negativeTestDir = "testfiles-negative"
  15. const testFileLineInfo = "testfile-line/Dockerfile"
  16. func getDirs(t *testing.T, dir string) []string {
  17. f, err := os.Open(dir)
  18. require.NoError(t, err)
  19. defer f.Close()
  20. dirs, err := f.Readdirnames(0)
  21. require.NoError(t, err)
  22. return dirs
  23. }
  24. func TestTestNegative(t *testing.T) {
  25. for _, dir := range getDirs(t, negativeTestDir) {
  26. dockerfile := filepath.Join(negativeTestDir, dir, "Dockerfile")
  27. df, err := os.Open(dockerfile)
  28. require.NoError(t, err)
  29. defer df.Close()
  30. _, err = Parse(df)
  31. assert.Error(t, err)
  32. }
  33. }
  34. func TestTestData(t *testing.T) {
  35. for _, dir := range getDirs(t, testDir) {
  36. dockerfile := filepath.Join(testDir, dir, "Dockerfile")
  37. resultfile := filepath.Join(testDir, dir, "result")
  38. df, err := os.Open(dockerfile)
  39. require.NoError(t, err)
  40. defer df.Close()
  41. result, err := Parse(df)
  42. require.NoError(t, err)
  43. content, err := ioutil.ReadFile(resultfile)
  44. require.NoError(t, err)
  45. if runtime.GOOS == "windows" {
  46. // CRLF --> CR to match Unix behavior
  47. content = bytes.Replace(content, []byte{'\x0d', '\x0a'}, []byte{'\x0a'}, -1)
  48. }
  49. assert.Contains(t, result.AST.Dump()+"\n", string(content), "In "+dockerfile)
  50. }
  51. }
  52. func TestParseWords(t *testing.T) {
  53. tests := []map[string][]string{
  54. {
  55. "input": {"foo"},
  56. "expect": {"foo"},
  57. },
  58. {
  59. "input": {"foo bar"},
  60. "expect": {"foo", "bar"},
  61. },
  62. {
  63. "input": {"foo\\ bar"},
  64. "expect": {"foo\\ bar"},
  65. },
  66. {
  67. "input": {"foo=bar"},
  68. "expect": {"foo=bar"},
  69. },
  70. {
  71. "input": {"foo bar 'abc xyz'"},
  72. "expect": {"foo", "bar", "'abc xyz'"},
  73. },
  74. {
  75. "input": {`foo bar "abc xyz"`},
  76. "expect": {"foo", "bar", `"abc xyz"`},
  77. },
  78. {
  79. "input": {"àöû"},
  80. "expect": {"àöû"},
  81. },
  82. {
  83. "input": {`föo bàr "âbc xÿz"`},
  84. "expect": {"föo", "bàr", `"âbc xÿz"`},
  85. },
  86. }
  87. for _, test := range tests {
  88. words := parseWords(test["input"][0], NewDefaultDirective())
  89. assert.Equal(t, test["expect"], words)
  90. }
  91. }
  92. func TestLineInformation(t *testing.T) {
  93. df, err := os.Open(testFileLineInfo)
  94. require.NoError(t, err)
  95. defer df.Close()
  96. result, err := Parse(df)
  97. require.NoError(t, err)
  98. ast := result.AST
  99. if ast.StartLine != 5 || ast.endLine != 31 {
  100. fmt.Fprintf(os.Stderr, "Wrong root line information: expected(%d-%d), actual(%d-%d)\n", 5, 31, ast.StartLine, ast.endLine)
  101. t.Fatal("Root line information doesn't match result.")
  102. }
  103. assert.Len(t, ast.Children, 3)
  104. expected := [][]int{
  105. {5, 5},
  106. {11, 12},
  107. {17, 31},
  108. }
  109. for i, child := range ast.Children {
  110. if child.StartLine != expected[i][0] || child.endLine != expected[i][1] {
  111. t.Logf("Wrong line information for child %d: expected(%d-%d), actual(%d-%d)\n",
  112. i, expected[i][0], expected[i][1], child.StartLine, child.endLine)
  113. t.Fatal("Root line information doesn't match result.")
  114. }
  115. }
  116. }