1
2
3
4
5
6
7 package imports
8
9 import (
10 "io"
11 "strings"
12 "testing"
13 )
14
15 const quote = "`"
16
17 type readTest struct {
18
19 in string
20 err string
21 }
22
23 var readImportsTests = []readTest{
24 {
25 `package p`,
26 "",
27 },
28 {
29 `package p; import "x"`,
30 "",
31 },
32 {
33 `package p; import . "x"`,
34 "",
35 },
36 {
37 `package p; import "x";ℙvar x = 1`,
38 "",
39 },
40 {
41 `package p
42
43 // comment
44
45 import "x"
46 import _ "x"
47 import a "x"
48
49 /* comment */
50
51 import (
52 "x" /* comment */
53 _ "x"
54 a "x" // comment
55 ` + quote + `x` + quote + `
56 _ /*comment*/ ` + quote + `x` + quote + `
57 a ` + quote + `x` + quote + `
58 )
59 import (
60 )
61 import ()
62 import()import()import()
63 import();import();import()
64
65 ℙvar x = 1
66 `,
67 "",
68 },
69 {
70 "\ufeff𝔻" + `package p; import "x";ℙvar x = 1`,
71 "",
72 },
73 }
74
75 var readCommentsTests = []readTest{
76 {
77 `ℙpackage p`,
78 "",
79 },
80 {
81 `ℙpackage p; import "x"`,
82 "",
83 },
84 {
85 `ℙpackage p; import . "x"`,
86 "",
87 },
88 {
89 "\ufeff𝔻" + `ℙpackage p; import . "x"`,
90 "",
91 },
92 {
93 `// foo
94
95 /* bar */
96
97 /* quux */ // baz
98
99 /*/ zot */
100
101 // asdf
102 ℙHello, world`,
103 "",
104 },
105 {
106 "\ufeff𝔻" + `// foo
107
108 /* bar */
109
110 /* quux */ // baz
111
112 /*/ zot */
113
114 // asdf
115 ℙHello, world`,
116 "",
117 },
118 }
119
120 func testRead(t *testing.T, tests []readTest, read func(io.Reader) ([]byte, error)) {
121 for i, tt := range tests {
122 var in, testOut string
123 j := strings.Index(tt.in, "ℙ")
124 if j < 0 {
125 in = tt.in
126 testOut = tt.in
127 } else {
128 in = tt.in[:j] + tt.in[j+len("ℙ"):]
129 testOut = tt.in[:j]
130 }
131 d := strings.Index(tt.in, "𝔻")
132 if d >= 0 {
133 in = in[:d] + in[d+len("𝔻"):]
134 testOut = testOut[d+len("𝔻"):]
135 }
136 r := strings.NewReader(in)
137 buf, err := read(r)
138 if err != nil {
139 if tt.err == "" {
140 t.Errorf("#%d: err=%q, expected success (%q)", i, err, string(buf))
141 continue
142 }
143 if !strings.Contains(err.Error(), tt.err) {
144 t.Errorf("#%d: err=%q, expected %q", i, err, tt.err)
145 continue
146 }
147 continue
148 }
149 if err == nil && tt.err != "" {
150 t.Errorf("#%d: success, expected %q", i, tt.err)
151 continue
152 }
153
154 out := string(buf)
155 if out != testOut {
156 t.Errorf("#%d: wrong output:\nhave %q\nwant %q\n", i, out, testOut)
157 }
158 }
159 }
160
161 func TestReadImports(t *testing.T) {
162 testRead(t, readImportsTests, func(r io.Reader) ([]byte, error) { return ReadImports(r, true, nil) })
163 }
164
165 func TestReadComments(t *testing.T) {
166 testRead(t, readCommentsTests, ReadComments)
167 }
168
169 var readFailuresTests = []readTest{
170 {
171 `package`,
172 "syntax error",
173 },
174 {
175 "package p\n\x00\nimport `math`\n",
176 "unexpected NUL in input",
177 },
178 {
179 `package p; import`,
180 "syntax error",
181 },
182 {
183 `package p; import "`,
184 "syntax error",
185 },
186 {
187 "package p; import ` \n\n",
188 "syntax error",
189 },
190 {
191 `package p; import "x`,
192 "syntax error",
193 },
194 {
195 `package p; import _`,
196 "syntax error",
197 },
198 {
199 `package p; import _ "`,
200 "syntax error",
201 },
202 {
203 `package p; import _ "x`,
204 "syntax error",
205 },
206 {
207 `package p; import .`,
208 "syntax error",
209 },
210 {
211 `package p; import . "`,
212 "syntax error",
213 },
214 {
215 `package p; import . "x`,
216 "syntax error",
217 },
218 {
219 `package p; import (`,
220 "syntax error",
221 },
222 {
223 `package p; import ("`,
224 "syntax error",
225 },
226 {
227 `package p; import ("x`,
228 "syntax error",
229 },
230 {
231 `package p; import ("x"`,
232 "syntax error",
233 },
234 }
235
236 func TestReadFailures(t *testing.T) {
237
238 testRead(t, readFailuresTests, func(r io.Reader) ([]byte, error) { return ReadImports(r, true, nil) })
239 }
240
241 func TestReadFailuresIgnored(t *testing.T) {
242
243
244
245 tests := make([]readTest, len(readFailuresTests))
246 copy(tests, readFailuresTests)
247 for i := range tests {
248 tt := &tests[i]
249 if !strings.Contains(tt.err, "NUL") {
250 tt.err = ""
251 }
252 }
253 testRead(t, tests, func(r io.Reader) ([]byte, error) { return ReadImports(r, false, nil) })
254 }
255
View as plain text