1
2
3
4 package localizer
5
6 import (
7 "fmt"
8 "os"
9 "path/filepath"
10 "strings"
11 "testing"
12
13 "github.com/stretchr/testify/require"
14 "sigs.k8s.io/kustomize/api/ifc"
15 "sigs.k8s.io/kustomize/api/internal/git"
16 "sigs.k8s.io/kustomize/kyaml/filesys"
17 )
18
19 func TestDefaultNewDirRepo(t *testing.T) {
20 for name, test := range map[string]struct {
21 url, dst string
22 }{
23 "simple": {
24 url: "https://github.com/org/repo?ref=value",
25 dst: "localized-repo-value",
26 },
27 "slashed_ref": {
28 url: "https://github.com/org/repo?ref=group/version",
29 dst: "localized-repo-group-version",
30 },
31 } {
32 t.Run(name, func(t *testing.T) {
33 repoSpec, err := git.NewRepoSpecFromURL(test.url)
34 require.NoError(t, err)
35 require.Equal(t, test.dst, defaultNewDir(&fakeLoader{t.TempDir()}, repoSpec))
36 })
37 }
38 }
39
40 type fakeLoader struct {
41 root string
42 }
43
44 func (fl *fakeLoader) Root() string {
45 return fl.root
46 }
47 func (fl *fakeLoader) Repo() string {
48 return fl.root
49 }
50 func (fl *fakeLoader) Load(_ string) ([]byte, error) {
51 return []byte{}, nil
52 }
53 func (fl *fakeLoader) New(path string) (ifc.Loader, error) {
54 return &fakeLoader{path}, nil
55 }
56 func (fl *fakeLoader) Cleanup() error {
57 return nil
58 }
59
60 func TestUrlBase(t *testing.T) {
61 require.Equal(t, "repo", urlBase("https://github.com/org/repo"))
62 }
63
64 func TestUrlBaseTrailingSlash(t *testing.T) {
65 require.Equal(t, "repo", urlBase("github.com/org/repo//"))
66 }
67
68
69 func simpleJoin(t *testing.T, elems ...string) string {
70 t.Helper()
71
72 return strings.Join(elems, string(filepath.Separator))
73 }
74
75 func TestLocFilePath(t *testing.T) {
76 for name, tUnit := range map[string]struct {
77 url, path string
78 }{
79 "official": {
80 url: "https://raw.githubusercontent.com/org/repo/ref/path/to/file.yaml",
81 path: simpleJoin(t, "raw.githubusercontent.com", "org", "repo", "ref", "path", "to", "file.yaml"),
82 },
83 "http-scheme": {
84 url: "http://host/path",
85 path: simpleJoin(t, "host", "path"),
86 },
87 "extraneous_components": {
88 url: "http://userinfo@host:1234/path/file?query",
89 path: simpleJoin(t, "host", "path", "file"),
90 },
91 "empty_path": {
92 url: "https://host",
93 path: "host",
94 },
95 "empty_path_segment": {
96 url: "https://host//",
97 path: "host",
98 },
99 "percent-encoded_path": {
100 url: "https://host/file%2Eyaml",
101 path: simpleJoin(t, "host", "file%2Eyaml"),
102 },
103 "dot-segments": {
104 url: "https://host/path/blah/../to/foo/bar/../../file/./",
105 path: simpleJoin(t, "host", "path", "to", "file"),
106 },
107 "extraneous_dot-segments": {
108 url: "https://host/foo/bar/baz/../../../../file",
109 path: simpleJoin(t, "host", "file"),
110 },
111 } {
112 t.Run(name, func(t *testing.T) {
113 require.Equal(t, simpleJoin(t, LocalizeDir, tUnit.path), locFilePath(tUnit.url))
114 })
115 }
116 }
117
118 func TestLocFilePathColon(t *testing.T) {
119 req := require.New(t)
120
121
122 const url = "https://[2001:4860:4860::8888]/file.yaml"
123 const host = "2001:4860:4860::8888"
124 const file = "file.yaml"
125 req.Equal(simpleJoin(t, LocalizeDir, host, file), locFilePath(url))
126
127 fSys := filesys.MakeFsOnDisk()
128 targetDir := simpleJoin(t, t.TempDir(), host)
129
130
131 req.NoError(fSys.Mkdir(targetDir))
132 _, err := fSys.Create(simpleJoin(t, targetDir, file))
133 req.NoError(err)
134
135
136 files, err := fSys.ReadDir(targetDir)
137 req.NoError(err)
138 req.Equal([]string{file}, files)
139 }
140
141 func TestLocFilePath_SpecialChar(t *testing.T) {
142 req := require.New(t)
143
144
145
146 const wildcard = "*"
147 req.Equal(simpleJoin(t, LocalizeDir, "host", wildcard), locFilePath("https://host/*"))
148
149 fSys := filesys.MakeFsOnDisk()
150 testDir := t.TempDir()
151 req.NoError(fSys.Mkdir(simpleJoin(t, testDir, "a")))
152 req.NoError(fSys.WriteFile(simpleJoin(t, testDir, "b"), []byte{}))
153
154
155
156 req.NoError(fSys.WriteFile(simpleJoin(t, testDir, wildcard), []byte("test")))
157 content, err := fSys.ReadFile(simpleJoin(t, testDir, wildcard))
158 req.NoError(err)
159 req.Equal("test", string(content))
160 }
161
162 func TestLocFilePath_SpecialFiles(t *testing.T) {
163 for name, tFSys := range map[string]struct {
164 urlPath string
165 pathDir, pathFile string
166 }{
167 "windows_reserved_name": {
168 urlPath: "/aux/file",
169 pathDir: "aux",
170 pathFile: "file",
171 },
172 "hidden_files": {
173 urlPath: "/.../.file",
174 pathDir: "...",
175 pathFile: ".file",
176 },
177 } {
178 t.Run(name, func(t *testing.T) {
179 req := require.New(t)
180
181 expectedPath := simpleJoin(t, LocalizeDir, "host", tFSys.pathDir, tFSys.pathFile)
182 req.Equal(expectedPath, locFilePath("https://host"+tFSys.urlPath))
183
184 fSys := filesys.MakeFsOnDisk()
185 targetDir := simpleJoin(t, t.TempDir(), tFSys.pathDir)
186 req.NoError(fSys.Mkdir(targetDir))
187 req.NoError(fSys.WriteFile(simpleJoin(t, targetDir, tFSys.pathFile), []byte("test")))
188
189 content, err := fSys.ReadFile(simpleJoin(t, targetDir, tFSys.pathFile))
190 req.NoError(err)
191 req.Equal([]byte("test"), content)
192 })
193 }
194 }
195
196 func makeConfirmedDir(t *testing.T) (filesys.FileSystem, filesys.ConfirmedDir) {
197 t.Helper()
198
199 fSys := filesys.MakeFsOnDisk()
200 testDir, err := filesys.NewTmpConfirmedDir()
201 require.NoError(t, err)
202 t.Cleanup(func() {
203 _ = fSys.RemoveAll(testDir.String())
204 })
205
206 return fSys, testDir
207 }
208
209 func TestLocRootPath_URLComponents(t *testing.T) {
210 for name, test := range map[string]struct {
211 urlf, path string
212 }{
213 "ssh": {
214 urlf: "ssh://git@github.com/org/repo//%s?ref=value",
215 path: simpleJoin(t, "github.com", "org", "repo", "value"),
216 },
217 "rel_ssh": {
218 urlf: "git@github.com:org/repo//%s?ref=value",
219 path: simpleJoin(t, "github.com", "org", "repo", "value"),
220 },
221 "https": {
222 urlf: "https://gitlab.com/org/repo//%s?ref=value",
223 path: simpleJoin(t, "gitlab.com", "org", "repo", "value"),
224 },
225 "file": {
226 urlf: "file:///var/run/repo//%s?ref=value",
227 path: simpleJoin(t, FileSchemeDir, "var", "run", "repo", "value"),
228 },
229 "IPv6": {
230 urlf: "https://[2001:4860:4860::8888]/org/repo//%s?ref=value",
231 path: simpleJoin(t, "2001:4860:4860::8888", "org", "repo", "value"),
232 },
233 "port": {
234 urlf: "https://localhost.com:8080/org/repo//%s?ref=value",
235 path: simpleJoin(t, "localhost.com", "org", "repo", "value"),
236 },
237 "no_org": {
238 urlf: "https://github.com/repo//%s?ref=value",
239 path: simpleJoin(t, "github.com", "repo", "value"),
240 },
241 ".git_suffix": {
242 urlf: "https://github.com/org1/org2/repo.git//%s?ref=value",
243 path: simpleJoin(t, "github.com", "org1", "org2", "repo", "value"),
244 },
245 "dot-segments": {
246 urlf: "https://github.com/./../org/../org/repo.git//%s?ref=value",
247 path: simpleJoin(t, "github.com", "org", "repo", "value"),
248 },
249 "no_path_delimiter": {
250 urlf: "https://github.com/org/repo/%s?ref=value",
251 path: simpleJoin(t, "github.com", "org", "repo", "value"),
252 },
253 "illegal_windows_dir": {
254 urlf: "https://gitlab.com/org./repo..git//%s?ref=value",
255 path: simpleJoin(t, "gitlab.com", "org.", "repo.", "value"),
256 },
257 "ref_has_slash": {
258 urlf: "https://gitlab.com/org/repo//%s?ref=group/version/kind",
259 path: simpleJoin(t, "gitlab.com", "org", "repo", "group", "version", "kind"),
260 },
261 } {
262 t.Run(name, func(t *testing.T) {
263 u := fmt.Sprintf(test.urlf, "path/to/root")
264 path := simpleJoin(t, LocalizeDir, test.path, "path", "to", "root")
265
266 fSys, testDir := makeConfirmedDir(t)
267 repoDir := simpleJoin(t, testDir.String(), "repo_random-hash")
268 require.NoError(t, fSys.Mkdir(repoDir))
269 rootDir := simpleJoin(t, repoDir, "path", "to", "root")
270 require.NoError(t, fSys.MkdirAll(rootDir))
271
272 actual, err := locRootPath(u, repoDir, filesys.ConfirmedDir(rootDir), fSys)
273 require.NoError(t, err)
274 require.Equal(t, path, actual)
275
276 require.NoError(t, fSys.MkdirAll(simpleJoin(t, testDir.String(), path)))
277 })
278 }
279 }
280
281 func TestLocRootPath_Repo(t *testing.T) {
282 const url = "https://github.com/org/repo?ref=value"
283 expected := simpleJoin(t, LocalizeDir, "github.com", "org", "repo", "value")
284
285 fSys, testDir := makeConfirmedDir(t)
286 actual, err := locRootPath(url, testDir.String(), testDir, fSys)
287 require.NoError(t, err)
288 require.Equal(t, expected, actual)
289 }
290
291 func TestLocRootPath_SymlinkPath(t *testing.T) {
292 const url = "https://github.com/org/repo//symlink?ref=value"
293
294 fSys, repoDir := makeConfirmedDir(t)
295 rootDir := simpleJoin(t, repoDir.String(), "actual-root")
296 require.NoError(t, fSys.Mkdir(rootDir))
297 require.NoError(t, os.Symlink(rootDir, simpleJoin(t, repoDir.String(), "symlink")))
298
299 expected := simpleJoin(t, LocalizeDir, "github.com", "org", "repo", "value", "actual-root")
300 actual, err := locRootPath(url, repoDir.String(), filesys.ConfirmedDir(rootDir), fSys)
301 require.NoError(t, err)
302 require.Equal(t, expected, actual)
303 }
304
View as plain text