github.com/golang/dep@v0.5.4/gps/filesystem_test.go (about) 1 // Copyright 2017 The Go Authors. All rights reserved. 2 // Use of this source code is governed by a BSD-style 3 // license that can be found in the LICENSE file. 4 5 package gps 6 7 import ( 8 "fmt" 9 "os" 10 "path/filepath" 11 "reflect" 12 "testing" 13 14 "github.com/golang/dep/internal/test" 15 ) 16 17 // This file contains utilities for running tests around file system state. 18 19 type fsTestCase struct { 20 before, after filesystemState 21 } 22 23 // assert makes sure that the tc.after state matches the state of the actual host 24 // file system at tc.after.root. 25 func (tc fsTestCase) assert(t *testing.T) { 26 dirMap := make(map[string]bool) 27 fileMap := make(map[string]bool) 28 linkMap := make(map[string]bool) 29 30 for _, d := range tc.after.dirs { 31 dirMap[filepath.Join(tc.after.root, d)] = true 32 } 33 for _, f := range tc.after.files { 34 fileMap[filepath.Join(tc.after.root, f)] = true 35 } 36 for _, l := range tc.after.links { 37 linkMap[filepath.Join(tc.after.root, l.path)] = true 38 } 39 40 err := filepath.Walk(tc.after.root, func(path string, info os.FileInfo, err error) error { 41 if err != nil { 42 t.Errorf("filepath.Walk path=%q err=%q", path, err) 43 return err 44 } 45 46 if path == tc.after.root { 47 return nil 48 } 49 50 // Careful! Have to check whether the path is a symlink first because, on 51 // windows, a symlink to a directory will return 'true' for info.IsDir(). 52 if (info.Mode() & os.ModeSymlink) != 0 { 53 if linkMap[path] { 54 delete(linkMap, path) 55 } else { 56 t.Errorf("unexpected symlink exists %q", path) 57 } 58 return nil 59 } 60 61 if info.IsDir() { 62 if dirMap[path] { 63 delete(dirMap, path) 64 } else { 65 t.Errorf("unexpected directory exists %q", path) 66 } 67 return nil 68 } 69 70 if fileMap[path] { 71 delete(fileMap, path) 72 } else { 73 t.Errorf("unexpected file exists %q", path) 74 } 75 return nil 76 }) 77 78 if err != nil { 79 t.Errorf("filesystem.Walk err=%q", err) 80 } 81 82 for d := range dirMap { 83 t.Errorf("could not find expected directory %q", d) 84 } 85 for f := range fileMap { 86 t.Errorf("could not find expected file %q", f) 87 } 88 for l := range linkMap { 89 t.Errorf("could not find expected symlink %q", l) 90 } 91 } 92 93 // setup inflates fs onto the actual host file system at tc.before.root. 94 // It doesn't delete existing files and should be used on empty roots only. 95 func (tc fsTestCase) setup(t *testing.T) { 96 if err := tc.before.setup(); err != nil { 97 t.Fatal(err) 98 } 99 } 100 101 func TestDeriveFilesystemState(t *testing.T) { 102 testcases := []struct { 103 name string 104 fs fsTestCase 105 }{ 106 { 107 name: "simple-case", 108 fs: fsTestCase{ 109 before: filesystemState{ 110 dirs: []string{ 111 "simple-dir", 112 }, 113 files: []string{ 114 "simple-file", 115 }, 116 }, 117 after: filesystemState{ 118 dirs: []string{ 119 "simple-dir", 120 }, 121 files: []string{ 122 "simple-file", 123 }, 124 }, 125 }, 126 }, 127 { 128 name: "simple-symlink-case", 129 fs: fsTestCase{ 130 before: filesystemState{ 131 dirs: []string{ 132 "simple-dir", 133 }, 134 files: []string{ 135 "simple-file", 136 }, 137 links: []fsLink{ 138 { 139 path: "link", 140 to: "nonexisting", 141 broken: true, 142 }, 143 }, 144 }, 145 after: filesystemState{ 146 dirs: []string{ 147 "simple-dir", 148 }, 149 files: []string{ 150 "simple-file", 151 }, 152 links: []fsLink{ 153 { 154 path: "link", 155 to: "", 156 broken: true, 157 }, 158 }, 159 }, 160 }, 161 }, 162 { 163 name: "complex-symlink-case", 164 fs: fsTestCase{ 165 before: filesystemState{ 166 links: []fsLink{ 167 { 168 path: "link1", 169 to: "link2", 170 circular: true, 171 }, 172 { 173 path: "link2", 174 to: "link1", 175 circular: true, 176 }, 177 }, 178 }, 179 after: filesystemState{ 180 links: []fsLink{ 181 { 182 path: "link1", 183 to: "", 184 circular: true, 185 }, 186 { 187 path: "link2", 188 to: "", 189 circular: true, 190 }, 191 }, 192 }, 193 }, 194 }, 195 } 196 197 for _, tc := range testcases { 198 h := test.NewHelper(t) 199 200 h.TempDir(tc.name) 201 202 tc.fs.before.root = h.Path(tc.name) 203 tc.fs.after.root = h.Path(tc.name) 204 205 tc.fs.setup(t) 206 207 state, err := deriveFilesystemState(h.Path(tc.name)) 208 if err != nil { 209 t.Fatal(err) 210 } 211 212 if !reflect.DeepEqual(tc.fs.after, state) { 213 fmt.Println(tc.fs.after) 214 fmt.Println(state) 215 t.Fatal("filesystem state mismatch") 216 } 217 218 h.Cleanup() 219 } 220 }