1*333d2b36SAndroid Build Coastguard Worker// Copyright 2017 Google Inc. All rights reserved. 2*333d2b36SAndroid Build Coastguard Worker// 3*333d2b36SAndroid Build Coastguard Worker// Licensed under the Apache License, Version 2.0 (the "License"); 4*333d2b36SAndroid Build Coastguard Worker// you may not use this file except in compliance with the License. 5*333d2b36SAndroid Build Coastguard Worker// You may obtain a copy of the License at 6*333d2b36SAndroid Build Coastguard Worker// 7*333d2b36SAndroid Build Coastguard Worker// http://www.apache.org/licenses/LICENSE-2.0 8*333d2b36SAndroid Build Coastguard Worker// 9*333d2b36SAndroid Build Coastguard Worker// Unless required by applicable law or agreed to in writing, software 10*333d2b36SAndroid Build Coastguard Worker// distributed under the License is distributed on an "AS IS" BASIS, 11*333d2b36SAndroid Build Coastguard Worker// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12*333d2b36SAndroid Build Coastguard Worker// See the License for the specific language governing permissions and 13*333d2b36SAndroid Build Coastguard Worker// limitations under the License. 14*333d2b36SAndroid Build Coastguard Worker 15*333d2b36SAndroid Build Coastguard Workerpackage finder 16*333d2b36SAndroid Build Coastguard Worker 17*333d2b36SAndroid Build Coastguard Workerimport ( 18*333d2b36SAndroid Build Coastguard Worker "fmt" 19*333d2b36SAndroid Build Coastguard Worker "io/ioutil" 20*333d2b36SAndroid Build Coastguard Worker "log" 21*333d2b36SAndroid Build Coastguard Worker "os" 22*333d2b36SAndroid Build Coastguard Worker "path/filepath" 23*333d2b36SAndroid Build Coastguard Worker "sort" 24*333d2b36SAndroid Build Coastguard Worker "strings" 25*333d2b36SAndroid Build Coastguard Worker "testing" 26*333d2b36SAndroid Build Coastguard Worker 27*333d2b36SAndroid Build Coastguard Worker "android/soong/finder/fs" 28*333d2b36SAndroid Build Coastguard Worker) 29*333d2b36SAndroid Build Coastguard Worker 30*333d2b36SAndroid Build Coastguard Worker// some utils for tests to use 31*333d2b36SAndroid Build Coastguard Workerfunc newFs() *fs.MockFs { 32*333d2b36SAndroid Build Coastguard Worker return fs.NewMockFs(map[string][]byte{}) 33*333d2b36SAndroid Build Coastguard Worker} 34*333d2b36SAndroid Build Coastguard Worker 35*333d2b36SAndroid Build Coastguard Workerfunc newFinder(t *testing.T, filesystem *fs.MockFs, cacheParams CacheParams) *Finder { 36*333d2b36SAndroid Build Coastguard Worker return newFinderWithNumThreads(t, filesystem, cacheParams, 2) 37*333d2b36SAndroid Build Coastguard Worker} 38*333d2b36SAndroid Build Coastguard Worker 39*333d2b36SAndroid Build Coastguard Workerfunc newFinderWithNumThreads(t *testing.T, filesystem *fs.MockFs, cacheParams CacheParams, numThreads int) *Finder { 40*333d2b36SAndroid Build Coastguard Worker f, err := newFinderAndErr(t, filesystem, cacheParams, numThreads) 41*333d2b36SAndroid Build Coastguard Worker if err != nil { 42*333d2b36SAndroid Build Coastguard Worker t.Fatal(err.Error()) 43*333d2b36SAndroid Build Coastguard Worker } 44*333d2b36SAndroid Build Coastguard Worker return f 45*333d2b36SAndroid Build Coastguard Worker} 46*333d2b36SAndroid Build Coastguard Worker 47*333d2b36SAndroid Build Coastguard Workerfunc newFinderAndErr(t *testing.T, filesystem *fs.MockFs, cacheParams CacheParams, numThreads int) (*Finder, error) { 48*333d2b36SAndroid Build Coastguard Worker cachePath := "/finder/finder-db" 49*333d2b36SAndroid Build Coastguard Worker cacheDir := filepath.Dir(cachePath) 50*333d2b36SAndroid Build Coastguard Worker filesystem.MkDirs(cacheDir) 51*333d2b36SAndroid Build Coastguard Worker if cacheParams.WorkingDirectory == "" { 52*333d2b36SAndroid Build Coastguard Worker cacheParams.WorkingDirectory = "/cwd" 53*333d2b36SAndroid Build Coastguard Worker } 54*333d2b36SAndroid Build Coastguard Worker 55*333d2b36SAndroid Build Coastguard Worker logger := log.New(ioutil.Discard, "", 0) 56*333d2b36SAndroid Build Coastguard Worker f, err := newImpl(cacheParams, filesystem, logger, cachePath, numThreads) 57*333d2b36SAndroid Build Coastguard Worker return f, err 58*333d2b36SAndroid Build Coastguard Worker} 59*333d2b36SAndroid Build Coastguard Worker 60*333d2b36SAndroid Build Coastguard Workerfunc finderWithSameParams(t *testing.T, original *Finder) *Finder { 61*333d2b36SAndroid Build Coastguard Worker f, err := finderAndErrorWithSameParams(t, original) 62*333d2b36SAndroid Build Coastguard Worker if err != nil { 63*333d2b36SAndroid Build Coastguard Worker t.Fatal(err.Error()) 64*333d2b36SAndroid Build Coastguard Worker } 65*333d2b36SAndroid Build Coastguard Worker return f 66*333d2b36SAndroid Build Coastguard Worker} 67*333d2b36SAndroid Build Coastguard Worker 68*333d2b36SAndroid Build Coastguard Workerfunc finderAndErrorWithSameParams(t *testing.T, original *Finder) (*Finder, error) { 69*333d2b36SAndroid Build Coastguard Worker f, err := newImpl( 70*333d2b36SAndroid Build Coastguard Worker original.cacheMetadata.Config.CacheParams, 71*333d2b36SAndroid Build Coastguard Worker original.filesystem, 72*333d2b36SAndroid Build Coastguard Worker original.logger, 73*333d2b36SAndroid Build Coastguard Worker original.DbPath, 74*333d2b36SAndroid Build Coastguard Worker original.numDbLoadingThreads, 75*333d2b36SAndroid Build Coastguard Worker ) 76*333d2b36SAndroid Build Coastguard Worker return f, err 77*333d2b36SAndroid Build Coastguard Worker} 78*333d2b36SAndroid Build Coastguard Worker 79*333d2b36SAndroid Build Coastguard Worker// runSimpleTests creates a few files, searches for findme.txt, and checks for the expected matches 80*333d2b36SAndroid Build Coastguard Workerfunc runSimpleTest(t *testing.T, existentPaths []string, expectedMatches []string) { 81*333d2b36SAndroid Build Coastguard Worker filesystem := newFs() 82*333d2b36SAndroid Build Coastguard Worker root := "/tmp" 83*333d2b36SAndroid Build Coastguard Worker filesystem.MkDirs(root) 84*333d2b36SAndroid Build Coastguard Worker for _, path := range existentPaths { 85*333d2b36SAndroid Build Coastguard Worker fs.Create(t, filepath.Join(root, path), filesystem) 86*333d2b36SAndroid Build Coastguard Worker } 87*333d2b36SAndroid Build Coastguard Worker 88*333d2b36SAndroid Build Coastguard Worker finder := newFinder(t, 89*333d2b36SAndroid Build Coastguard Worker filesystem, 90*333d2b36SAndroid Build Coastguard Worker CacheParams{ 91*333d2b36SAndroid Build Coastguard Worker "/cwd", 92*333d2b36SAndroid Build Coastguard Worker []string{root}, 93*333d2b36SAndroid Build Coastguard Worker false, 94*333d2b36SAndroid Build Coastguard Worker nil, 95*333d2b36SAndroid Build Coastguard Worker nil, 96*333d2b36SAndroid Build Coastguard Worker []string{"findme.txt", "skipme.txt"}, 97*333d2b36SAndroid Build Coastguard Worker nil, 98*333d2b36SAndroid Build Coastguard Worker }, 99*333d2b36SAndroid Build Coastguard Worker ) 100*333d2b36SAndroid Build Coastguard Worker defer finder.Shutdown() 101*333d2b36SAndroid Build Coastguard Worker 102*333d2b36SAndroid Build Coastguard Worker foundPaths := finder.FindNamedAt(root, "findme.txt") 103*333d2b36SAndroid Build Coastguard Worker absoluteMatches := []string{} 104*333d2b36SAndroid Build Coastguard Worker for i := range expectedMatches { 105*333d2b36SAndroid Build Coastguard Worker absoluteMatches = append(absoluteMatches, filepath.Join(root, expectedMatches[i])) 106*333d2b36SAndroid Build Coastguard Worker } 107*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, absoluteMatches) 108*333d2b36SAndroid Build Coastguard Worker} 109*333d2b36SAndroid Build Coastguard Worker 110*333d2b36SAndroid Build Coastguard Worker// runTestWithSuffixes creates a few files, searches for findme.txt or any file 111*333d2b36SAndroid Build Coastguard Worker// with suffix `.findme_ext` and checks for the expected matches 112*333d2b36SAndroid Build Coastguard Workerfunc runTestWithSuffixes(t *testing.T, existentPaths []string, expectedMatches []string) { 113*333d2b36SAndroid Build Coastguard Worker filesystem := newFs() 114*333d2b36SAndroid Build Coastguard Worker root := "/tmp" 115*333d2b36SAndroid Build Coastguard Worker filesystem.MkDirs(root) 116*333d2b36SAndroid Build Coastguard Worker for _, path := range existentPaths { 117*333d2b36SAndroid Build Coastguard Worker fs.Create(t, filepath.Join(root, path), filesystem) 118*333d2b36SAndroid Build Coastguard Worker } 119*333d2b36SAndroid Build Coastguard Worker 120*333d2b36SAndroid Build Coastguard Worker finder := newFinder(t, 121*333d2b36SAndroid Build Coastguard Worker filesystem, 122*333d2b36SAndroid Build Coastguard Worker CacheParams{ 123*333d2b36SAndroid Build Coastguard Worker "/cwd", 124*333d2b36SAndroid Build Coastguard Worker []string{root}, 125*333d2b36SAndroid Build Coastguard Worker false, 126*333d2b36SAndroid Build Coastguard Worker nil, 127*333d2b36SAndroid Build Coastguard Worker nil, 128*333d2b36SAndroid Build Coastguard Worker []string{"findme.txt", "skipme.txt"}, 129*333d2b36SAndroid Build Coastguard Worker []string{".findme_ext"}, 130*333d2b36SAndroid Build Coastguard Worker }, 131*333d2b36SAndroid Build Coastguard Worker ) 132*333d2b36SAndroid Build Coastguard Worker defer finder.Shutdown() 133*333d2b36SAndroid Build Coastguard Worker 134*333d2b36SAndroid Build Coastguard Worker foundPaths := finder.FindMatching(root, 135*333d2b36SAndroid Build Coastguard Worker func(entries DirEntries) (dirs []string, files []string) { 136*333d2b36SAndroid Build Coastguard Worker matches := []string{} 137*333d2b36SAndroid Build Coastguard Worker for _, foundName := range entries.FileNames { 138*333d2b36SAndroid Build Coastguard Worker if foundName == "findme.txt" || strings.HasSuffix(foundName, ".findme_ext") { 139*333d2b36SAndroid Build Coastguard Worker matches = append(matches, foundName) 140*333d2b36SAndroid Build Coastguard Worker } 141*333d2b36SAndroid Build Coastguard Worker } 142*333d2b36SAndroid Build Coastguard Worker return entries.DirNames, matches 143*333d2b36SAndroid Build Coastguard Worker }) 144*333d2b36SAndroid Build Coastguard Worker absoluteMatches := []string{} 145*333d2b36SAndroid Build Coastguard Worker for i := range expectedMatches { 146*333d2b36SAndroid Build Coastguard Worker absoluteMatches = append(absoluteMatches, filepath.Join(root, expectedMatches[i])) 147*333d2b36SAndroid Build Coastguard Worker } 148*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, absoluteMatches) 149*333d2b36SAndroid Build Coastguard Worker} 150*333d2b36SAndroid Build Coastguard Worker 151*333d2b36SAndroid Build Coastguard Worker// testAgainstSeveralThreadcounts runs the given test for each threadcount that we care to test 152*333d2b36SAndroid Build Coastguard Workerfunc testAgainstSeveralThreadcounts(t *testing.T, tester func(t *testing.T, numThreads int)) { 153*333d2b36SAndroid Build Coastguard Worker // test singlethreaded, multithreaded, and also using the same number of threads as 154*333d2b36SAndroid Build Coastguard Worker // will be used on the current system 155*333d2b36SAndroid Build Coastguard Worker threadCounts := []int{1, 2, defaultNumThreads} 156*333d2b36SAndroid Build Coastguard Worker for _, numThreads := range threadCounts { 157*333d2b36SAndroid Build Coastguard Worker testName := fmt.Sprintf("%v threads", numThreads) 158*333d2b36SAndroid Build Coastguard Worker // store numThreads in a new variable to prevent numThreads from changing in each loop 159*333d2b36SAndroid Build Coastguard Worker localNumThreads := numThreads 160*333d2b36SAndroid Build Coastguard Worker t.Run(testName, func(t *testing.T) { 161*333d2b36SAndroid Build Coastguard Worker tester(t, localNumThreads) 162*333d2b36SAndroid Build Coastguard Worker }) 163*333d2b36SAndroid Build Coastguard Worker } 164*333d2b36SAndroid Build Coastguard Worker} 165*333d2b36SAndroid Build Coastguard Worker 166*333d2b36SAndroid Build Coastguard Worker// end of utils, start of individual tests 167*333d2b36SAndroid Build Coastguard Worker 168*333d2b36SAndroid Build Coastguard Workerfunc TestSingleFile(t *testing.T) { 169*333d2b36SAndroid Build Coastguard Worker runSimpleTest(t, 170*333d2b36SAndroid Build Coastguard Worker []string{"findme.txt"}, 171*333d2b36SAndroid Build Coastguard Worker []string{"findme.txt"}, 172*333d2b36SAndroid Build Coastguard Worker ) 173*333d2b36SAndroid Build Coastguard Worker} 174*333d2b36SAndroid Build Coastguard Worker 175*333d2b36SAndroid Build Coastguard Workerfunc TestIncludeFiles(t *testing.T) { 176*333d2b36SAndroid Build Coastguard Worker runSimpleTest(t, 177*333d2b36SAndroid Build Coastguard Worker []string{"findme.txt", "skipme.txt"}, 178*333d2b36SAndroid Build Coastguard Worker []string{"findme.txt"}, 179*333d2b36SAndroid Build Coastguard Worker ) 180*333d2b36SAndroid Build Coastguard Worker} 181*333d2b36SAndroid Build Coastguard Worker 182*333d2b36SAndroid Build Coastguard Workerfunc TestIncludeFilesAndSuffixes(t *testing.T) { 183*333d2b36SAndroid Build Coastguard Worker runTestWithSuffixes(t, 184*333d2b36SAndroid Build Coastguard Worker []string{"findme.txt", "skipme.txt", "alsome.findme_ext"}, 185*333d2b36SAndroid Build Coastguard Worker []string{"findme.txt", "alsome.findme_ext"}, 186*333d2b36SAndroid Build Coastguard Worker ) 187*333d2b36SAndroid Build Coastguard Worker} 188*333d2b36SAndroid Build Coastguard Worker 189*333d2b36SAndroid Build Coastguard Workerfunc TestNestedDirectories(t *testing.T) { 190*333d2b36SAndroid Build Coastguard Worker runSimpleTest(t, 191*333d2b36SAndroid Build Coastguard Worker []string{"findme.txt", "skipme.txt", "subdir/findme.txt", "subdir/skipme.txt"}, 192*333d2b36SAndroid Build Coastguard Worker []string{"findme.txt", "subdir/findme.txt"}, 193*333d2b36SAndroid Build Coastguard Worker ) 194*333d2b36SAndroid Build Coastguard Worker} 195*333d2b36SAndroid Build Coastguard Worker 196*333d2b36SAndroid Build Coastguard Workerfunc TestNestedDirectoriesWithSuffixes(t *testing.T) { 197*333d2b36SAndroid Build Coastguard Worker runTestWithSuffixes(t, 198*333d2b36SAndroid Build Coastguard Worker []string{"findme.txt", "skipme.txt", "subdir/findme.txt", "subdir/skipme.txt", "subdir/alsome.findme_ext"}, 199*333d2b36SAndroid Build Coastguard Worker []string{"findme.txt", "subdir/findme.txt", "subdir/alsome.findme_ext"}, 200*333d2b36SAndroid Build Coastguard Worker ) 201*333d2b36SAndroid Build Coastguard Worker} 202*333d2b36SAndroid Build Coastguard Worker 203*333d2b36SAndroid Build Coastguard Workerfunc TestEmptyDirectory(t *testing.T) { 204*333d2b36SAndroid Build Coastguard Worker runSimpleTest(t, 205*333d2b36SAndroid Build Coastguard Worker []string{}, 206*333d2b36SAndroid Build Coastguard Worker []string{}, 207*333d2b36SAndroid Build Coastguard Worker ) 208*333d2b36SAndroid Build Coastguard Worker} 209*333d2b36SAndroid Build Coastguard Worker 210*333d2b36SAndroid Build Coastguard Workerfunc TestEmptyPath(t *testing.T) { 211*333d2b36SAndroid Build Coastguard Worker filesystem := newFs() 212*333d2b36SAndroid Build Coastguard Worker root := "/tmp" 213*333d2b36SAndroid Build Coastguard Worker fs.Create(t, filepath.Join(root, "findme.txt"), filesystem) 214*333d2b36SAndroid Build Coastguard Worker 215*333d2b36SAndroid Build Coastguard Worker finder := newFinder( 216*333d2b36SAndroid Build Coastguard Worker t, 217*333d2b36SAndroid Build Coastguard Worker filesystem, 218*333d2b36SAndroid Build Coastguard Worker CacheParams{ 219*333d2b36SAndroid Build Coastguard Worker RootDirs: []string{root}, 220*333d2b36SAndroid Build Coastguard Worker IncludeFiles: []string{"findme.txt", "skipme.txt"}, 221*333d2b36SAndroid Build Coastguard Worker }, 222*333d2b36SAndroid Build Coastguard Worker ) 223*333d2b36SAndroid Build Coastguard Worker defer finder.Shutdown() 224*333d2b36SAndroid Build Coastguard Worker 225*333d2b36SAndroid Build Coastguard Worker foundPaths := finder.FindNamedAt("", "findme.txt") 226*333d2b36SAndroid Build Coastguard Worker 227*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, []string{}) 228*333d2b36SAndroid Build Coastguard Worker} 229*333d2b36SAndroid Build Coastguard Worker 230*333d2b36SAndroid Build Coastguard Workerfunc TestFilesystemRoot(t *testing.T) { 231*333d2b36SAndroid Build Coastguard Worker 232*333d2b36SAndroid Build Coastguard Worker testWithNumThreads := func(t *testing.T, numThreads int) { 233*333d2b36SAndroid Build Coastguard Worker filesystem := newFs() 234*333d2b36SAndroid Build Coastguard Worker root := "/" 235*333d2b36SAndroid Build Coastguard Worker createdPath := "/findme.txt" 236*333d2b36SAndroid Build Coastguard Worker fs.Create(t, createdPath, filesystem) 237*333d2b36SAndroid Build Coastguard Worker 238*333d2b36SAndroid Build Coastguard Worker finder := newFinderWithNumThreads( 239*333d2b36SAndroid Build Coastguard Worker t, 240*333d2b36SAndroid Build Coastguard Worker filesystem, 241*333d2b36SAndroid Build Coastguard Worker CacheParams{ 242*333d2b36SAndroid Build Coastguard Worker RootDirs: []string{root}, 243*333d2b36SAndroid Build Coastguard Worker IncludeFiles: []string{"findme.txt", "skipme.txt"}, 244*333d2b36SAndroid Build Coastguard Worker }, 245*333d2b36SAndroid Build Coastguard Worker numThreads, 246*333d2b36SAndroid Build Coastguard Worker ) 247*333d2b36SAndroid Build Coastguard Worker defer finder.Shutdown() 248*333d2b36SAndroid Build Coastguard Worker 249*333d2b36SAndroid Build Coastguard Worker foundPaths := finder.FindNamedAt(root, "findme.txt") 250*333d2b36SAndroid Build Coastguard Worker 251*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, []string{createdPath}) 252*333d2b36SAndroid Build Coastguard Worker } 253*333d2b36SAndroid Build Coastguard Worker 254*333d2b36SAndroid Build Coastguard Worker testAgainstSeveralThreadcounts(t, testWithNumThreads) 255*333d2b36SAndroid Build Coastguard Worker} 256*333d2b36SAndroid Build Coastguard Worker 257*333d2b36SAndroid Build Coastguard Workerfunc TestNonexistentDir(t *testing.T) { 258*333d2b36SAndroid Build Coastguard Worker filesystem := newFs() 259*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/findme.txt", filesystem) 260*333d2b36SAndroid Build Coastguard Worker 261*333d2b36SAndroid Build Coastguard Worker _, err := newFinderAndErr( 262*333d2b36SAndroid Build Coastguard Worker t, 263*333d2b36SAndroid Build Coastguard Worker filesystem, 264*333d2b36SAndroid Build Coastguard Worker CacheParams{ 265*333d2b36SAndroid Build Coastguard Worker RootDirs: []string{"/tmp/IDontExist"}, 266*333d2b36SAndroid Build Coastguard Worker IncludeFiles: []string{"findme.txt", "skipme.txt"}, 267*333d2b36SAndroid Build Coastguard Worker }, 268*333d2b36SAndroid Build Coastguard Worker 1, 269*333d2b36SAndroid Build Coastguard Worker ) 270*333d2b36SAndroid Build Coastguard Worker if err == nil { 271*333d2b36SAndroid Build Coastguard Worker t.Fatal("Did not fail when given a nonexistent root directory") 272*333d2b36SAndroid Build Coastguard Worker } 273*333d2b36SAndroid Build Coastguard Worker} 274*333d2b36SAndroid Build Coastguard Worker 275*333d2b36SAndroid Build Coastguard Workerfunc TestExcludeDirs(t *testing.T) { 276*333d2b36SAndroid Build Coastguard Worker filesystem := newFs() 277*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/exclude/findme.txt", filesystem) 278*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/exclude/subdir/findme.txt", filesystem) 279*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/subdir/exclude/findme.txt", filesystem) 280*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/subdir/subdir/findme.txt", filesystem) 281*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/subdir/findme.txt", filesystem) 282*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/findme.txt", filesystem) 283*333d2b36SAndroid Build Coastguard Worker 284*333d2b36SAndroid Build Coastguard Worker finder := newFinder( 285*333d2b36SAndroid Build Coastguard Worker t, 286*333d2b36SAndroid Build Coastguard Worker filesystem, 287*333d2b36SAndroid Build Coastguard Worker CacheParams{ 288*333d2b36SAndroid Build Coastguard Worker RootDirs: []string{"/tmp"}, 289*333d2b36SAndroid Build Coastguard Worker ExcludeDirs: []string{"exclude"}, 290*333d2b36SAndroid Build Coastguard Worker IncludeFiles: []string{"findme.txt", "skipme.txt"}, 291*333d2b36SAndroid Build Coastguard Worker }, 292*333d2b36SAndroid Build Coastguard Worker ) 293*333d2b36SAndroid Build Coastguard Worker defer finder.Shutdown() 294*333d2b36SAndroid Build Coastguard Worker 295*333d2b36SAndroid Build Coastguard Worker foundPaths := finder.FindNamedAt("/tmp", "findme.txt") 296*333d2b36SAndroid Build Coastguard Worker 297*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, 298*333d2b36SAndroid Build Coastguard Worker []string{"/tmp/findme.txt", 299*333d2b36SAndroid Build Coastguard Worker "/tmp/subdir/findme.txt", 300*333d2b36SAndroid Build Coastguard Worker "/tmp/subdir/subdir/findme.txt"}) 301*333d2b36SAndroid Build Coastguard Worker} 302*333d2b36SAndroid Build Coastguard Worker 303*333d2b36SAndroid Build Coastguard Workerfunc TestPruneFiles(t *testing.T) { 304*333d2b36SAndroid Build Coastguard Worker filesystem := newFs() 305*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/out/findme.txt", filesystem) 306*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/out/.ignore-out-dir", filesystem) 307*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/out/child/findme.txt", filesystem) 308*333d2b36SAndroid Build Coastguard Worker 309*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/out2/.ignore-out-dir", filesystem) 310*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/out2/sub/findme.txt", filesystem) 311*333d2b36SAndroid Build Coastguard Worker 312*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/findme.txt", filesystem) 313*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/include/findme.txt", filesystem) 314*333d2b36SAndroid Build Coastguard Worker 315*333d2b36SAndroid Build Coastguard Worker finder := newFinder( 316*333d2b36SAndroid Build Coastguard Worker t, 317*333d2b36SAndroid Build Coastguard Worker filesystem, 318*333d2b36SAndroid Build Coastguard Worker CacheParams{ 319*333d2b36SAndroid Build Coastguard Worker RootDirs: []string{"/tmp"}, 320*333d2b36SAndroid Build Coastguard Worker PruneFiles: []string{".ignore-out-dir"}, 321*333d2b36SAndroid Build Coastguard Worker IncludeFiles: []string{"findme.txt"}, 322*333d2b36SAndroid Build Coastguard Worker }, 323*333d2b36SAndroid Build Coastguard Worker ) 324*333d2b36SAndroid Build Coastguard Worker defer finder.Shutdown() 325*333d2b36SAndroid Build Coastguard Worker 326*333d2b36SAndroid Build Coastguard Worker foundPaths := finder.FindNamedAt("/tmp", "findme.txt") 327*333d2b36SAndroid Build Coastguard Worker 328*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, 329*333d2b36SAndroid Build Coastguard Worker []string{"/tmp/findme.txt", 330*333d2b36SAndroid Build Coastguard Worker "/tmp/include/findme.txt"}) 331*333d2b36SAndroid Build Coastguard Worker} 332*333d2b36SAndroid Build Coastguard Worker 333*333d2b36SAndroid Build Coastguard Worker// TestRootDir tests that the value of RootDirs is used 334*333d2b36SAndroid Build Coastguard Worker// tests of the filesystem root are in TestFilesystemRoot 335*333d2b36SAndroid Build Coastguard Workerfunc TestRootDir(t *testing.T) { 336*333d2b36SAndroid Build Coastguard Worker filesystem := newFs() 337*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/a/findme.txt", filesystem) 338*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/a/subdir/findme.txt", filesystem) 339*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/b/findme.txt", filesystem) 340*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/b/subdir/findme.txt", filesystem) 341*333d2b36SAndroid Build Coastguard Worker 342*333d2b36SAndroid Build Coastguard Worker finder := newFinder( 343*333d2b36SAndroid Build Coastguard Worker t, 344*333d2b36SAndroid Build Coastguard Worker filesystem, 345*333d2b36SAndroid Build Coastguard Worker CacheParams{ 346*333d2b36SAndroid Build Coastguard Worker RootDirs: []string{"/tmp/a"}, 347*333d2b36SAndroid Build Coastguard Worker IncludeFiles: []string{"findme.txt"}, 348*333d2b36SAndroid Build Coastguard Worker }, 349*333d2b36SAndroid Build Coastguard Worker ) 350*333d2b36SAndroid Build Coastguard Worker defer finder.Shutdown() 351*333d2b36SAndroid Build Coastguard Worker 352*333d2b36SAndroid Build Coastguard Worker foundPaths := finder.FindNamedAt("/tmp/a", "findme.txt") 353*333d2b36SAndroid Build Coastguard Worker 354*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, 355*333d2b36SAndroid Build Coastguard Worker []string{"/tmp/a/findme.txt", 356*333d2b36SAndroid Build Coastguard Worker "/tmp/a/subdir/findme.txt"}) 357*333d2b36SAndroid Build Coastguard Worker} 358*333d2b36SAndroid Build Coastguard Worker 359*333d2b36SAndroid Build Coastguard Workerfunc TestUncachedDir(t *testing.T) { 360*333d2b36SAndroid Build Coastguard Worker filesystem := newFs() 361*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/a/findme.txt", filesystem) 362*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/a/subdir/findme.txt", filesystem) 363*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/b/findme.txt", filesystem) 364*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/b/subdir/findme.txt", filesystem) 365*333d2b36SAndroid Build Coastguard Worker 366*333d2b36SAndroid Build Coastguard Worker finder := newFinder( 367*333d2b36SAndroid Build Coastguard Worker t, 368*333d2b36SAndroid Build Coastguard Worker filesystem, 369*333d2b36SAndroid Build Coastguard Worker CacheParams{ 370*333d2b36SAndroid Build Coastguard Worker RootDirs: []string{"/tmp/b"}, 371*333d2b36SAndroid Build Coastguard Worker IncludeFiles: []string{"findme.txt"}, 372*333d2b36SAndroid Build Coastguard Worker }, 373*333d2b36SAndroid Build Coastguard Worker ) 374*333d2b36SAndroid Build Coastguard Worker 375*333d2b36SAndroid Build Coastguard Worker foundPaths := finder.FindNamedAt("/tmp/a", "findme.txt") 376*333d2b36SAndroid Build Coastguard Worker // If the caller queries for a file that is in the cache, then computing the 377*333d2b36SAndroid Build Coastguard Worker // correct answer won't be fast, and it would be easy for the caller to 378*333d2b36SAndroid Build Coastguard Worker // fail to notice its slowness. Instead, we only ever search the cache for files 379*333d2b36SAndroid Build Coastguard Worker // to return, which enforces that we can determine which files will be 380*333d2b36SAndroid Build Coastguard Worker // interesting upfront. 381*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, []string{}) 382*333d2b36SAndroid Build Coastguard Worker 383*333d2b36SAndroid Build Coastguard Worker finder.Shutdown() 384*333d2b36SAndroid Build Coastguard Worker} 385*333d2b36SAndroid Build Coastguard Worker 386*333d2b36SAndroid Build Coastguard Workerfunc TestSearchingForFilesExcludedFromCache(t *testing.T) { 387*333d2b36SAndroid Build Coastguard Worker // setup filesystem 388*333d2b36SAndroid Build Coastguard Worker filesystem := newFs() 389*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/findme.txt", filesystem) 390*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/a/findme.txt", filesystem) 391*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/a/misc.txt", filesystem) 392*333d2b36SAndroid Build Coastguard Worker 393*333d2b36SAndroid Build Coastguard Worker // set up the finder and run it 394*333d2b36SAndroid Build Coastguard Worker finder := newFinder( 395*333d2b36SAndroid Build Coastguard Worker t, 396*333d2b36SAndroid Build Coastguard Worker filesystem, 397*333d2b36SAndroid Build Coastguard Worker CacheParams{ 398*333d2b36SAndroid Build Coastguard Worker RootDirs: []string{"/tmp"}, 399*333d2b36SAndroid Build Coastguard Worker IncludeFiles: []string{"findme.txt"}, 400*333d2b36SAndroid Build Coastguard Worker }, 401*333d2b36SAndroid Build Coastguard Worker ) 402*333d2b36SAndroid Build Coastguard Worker foundPaths := finder.FindNamedAt("/tmp", "misc.txt") 403*333d2b36SAndroid Build Coastguard Worker // If the caller queries for a file that is in the cache, then computing the 404*333d2b36SAndroid Build Coastguard Worker // correct answer won't be fast, and it would be easy for the caller to 405*333d2b36SAndroid Build Coastguard Worker // fail to notice its slowness. Instead, we only ever search the cache for files 406*333d2b36SAndroid Build Coastguard Worker // to return, which enforces that we can determine which files will be 407*333d2b36SAndroid Build Coastguard Worker // interesting upfront. 408*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, []string{}) 409*333d2b36SAndroid Build Coastguard Worker 410*333d2b36SAndroid Build Coastguard Worker finder.Shutdown() 411*333d2b36SAndroid Build Coastguard Worker} 412*333d2b36SAndroid Build Coastguard Worker 413*333d2b36SAndroid Build Coastguard Workerfunc TestRelativeFilePaths(t *testing.T) { 414*333d2b36SAndroid Build Coastguard Worker filesystem := newFs() 415*333d2b36SAndroid Build Coastguard Worker 416*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/ignore/hi.txt", filesystem) 417*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/include/hi.txt", filesystem) 418*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/cwd/hi.txt", filesystem) 419*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/cwd/a/hi.txt", filesystem) 420*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/cwd/a/a/hi.txt", filesystem) 421*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/rel/a/hi.txt", filesystem) 422*333d2b36SAndroid Build Coastguard Worker 423*333d2b36SAndroid Build Coastguard Worker finder := newFinder( 424*333d2b36SAndroid Build Coastguard Worker t, 425*333d2b36SAndroid Build Coastguard Worker filesystem, 426*333d2b36SAndroid Build Coastguard Worker CacheParams{ 427*333d2b36SAndroid Build Coastguard Worker RootDirs: []string{"/cwd", "../rel", "/tmp/include"}, 428*333d2b36SAndroid Build Coastguard Worker IncludeFiles: []string{"hi.txt"}, 429*333d2b36SAndroid Build Coastguard Worker }, 430*333d2b36SAndroid Build Coastguard Worker ) 431*333d2b36SAndroid Build Coastguard Worker defer finder.Shutdown() 432*333d2b36SAndroid Build Coastguard Worker 433*333d2b36SAndroid Build Coastguard Worker foundPaths := finder.FindNamedAt("a", "hi.txt") 434*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, 435*333d2b36SAndroid Build Coastguard Worker []string{"a/hi.txt", 436*333d2b36SAndroid Build Coastguard Worker "a/a/hi.txt"}) 437*333d2b36SAndroid Build Coastguard Worker 438*333d2b36SAndroid Build Coastguard Worker foundPaths = finder.FindNamedAt("/tmp/include", "hi.txt") 439*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, []string{"/tmp/include/hi.txt"}) 440*333d2b36SAndroid Build Coastguard Worker 441*333d2b36SAndroid Build Coastguard Worker foundPaths = finder.FindNamedAt(".", "hi.txt") 442*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, 443*333d2b36SAndroid Build Coastguard Worker []string{"hi.txt", 444*333d2b36SAndroid Build Coastguard Worker "a/hi.txt", 445*333d2b36SAndroid Build Coastguard Worker "a/a/hi.txt"}) 446*333d2b36SAndroid Build Coastguard Worker 447*333d2b36SAndroid Build Coastguard Worker foundPaths = finder.FindNamedAt("/rel", "hi.txt") 448*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, 449*333d2b36SAndroid Build Coastguard Worker []string{"/rel/a/hi.txt"}) 450*333d2b36SAndroid Build Coastguard Worker 451*333d2b36SAndroid Build Coastguard Worker foundPaths = finder.FindNamedAt("/tmp/include", "hi.txt") 452*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, []string{"/tmp/include/hi.txt"}) 453*333d2b36SAndroid Build Coastguard Worker} 454*333d2b36SAndroid Build Coastguard Worker 455*333d2b36SAndroid Build Coastguard Worker// have to run this test with the race-detector (`go test -race src/android/soong/finder/*.go`) 456*333d2b36SAndroid Build Coastguard Worker// for there to be much chance of the test actually detecting any error that may be present 457*333d2b36SAndroid Build Coastguard Workerfunc TestRootDirsContainedInOtherRootDirs(t *testing.T) { 458*333d2b36SAndroid Build Coastguard Worker filesystem := newFs() 459*333d2b36SAndroid Build Coastguard Worker 460*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/a/b/c/d/e/f/g/h/i/j/findme.txt", filesystem) 461*333d2b36SAndroid Build Coastguard Worker 462*333d2b36SAndroid Build Coastguard Worker finder := newFinder( 463*333d2b36SAndroid Build Coastguard Worker t, 464*333d2b36SAndroid Build Coastguard Worker filesystem, 465*333d2b36SAndroid Build Coastguard Worker CacheParams{ 466*333d2b36SAndroid Build Coastguard Worker RootDirs: []string{"/", "/tmp/a/b/c", "/tmp/a/b/c/d/e/f", "/tmp/a/b/c/d/e/f/g/h/i"}, 467*333d2b36SAndroid Build Coastguard Worker IncludeFiles: []string{"findme.txt"}, 468*333d2b36SAndroid Build Coastguard Worker }, 469*333d2b36SAndroid Build Coastguard Worker ) 470*333d2b36SAndroid Build Coastguard Worker defer finder.Shutdown() 471*333d2b36SAndroid Build Coastguard Worker 472*333d2b36SAndroid Build Coastguard Worker foundPaths := finder.FindNamedAt("/tmp/a", "findme.txt") 473*333d2b36SAndroid Build Coastguard Worker 474*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, 475*333d2b36SAndroid Build Coastguard Worker []string{"/tmp/a/b/c/d/e/f/g/h/i/j/findme.txt"}) 476*333d2b36SAndroid Build Coastguard Worker} 477*333d2b36SAndroid Build Coastguard Worker 478*333d2b36SAndroid Build Coastguard Workerfunc TestFindFirst(t *testing.T) { 479*333d2b36SAndroid Build Coastguard Worker filesystem := newFs() 480*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/a/hi.txt", filesystem) 481*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/b/hi.txt", filesystem) 482*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/b/a/hi.txt", filesystem) 483*333d2b36SAndroid Build Coastguard Worker 484*333d2b36SAndroid Build Coastguard Worker finder := newFinder( 485*333d2b36SAndroid Build Coastguard Worker t, 486*333d2b36SAndroid Build Coastguard Worker filesystem, 487*333d2b36SAndroid Build Coastguard Worker CacheParams{ 488*333d2b36SAndroid Build Coastguard Worker RootDirs: []string{"/tmp"}, 489*333d2b36SAndroid Build Coastguard Worker IncludeFiles: []string{"hi.txt"}, 490*333d2b36SAndroid Build Coastguard Worker }, 491*333d2b36SAndroid Build Coastguard Worker ) 492*333d2b36SAndroid Build Coastguard Worker defer finder.Shutdown() 493*333d2b36SAndroid Build Coastguard Worker 494*333d2b36SAndroid Build Coastguard Worker foundPaths := finder.FindFirstNamed("hi.txt") 495*333d2b36SAndroid Build Coastguard Worker 496*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, 497*333d2b36SAndroid Build Coastguard Worker []string{"/tmp/a/hi.txt", 498*333d2b36SAndroid Build Coastguard Worker "/tmp/b/hi.txt"}, 499*333d2b36SAndroid Build Coastguard Worker ) 500*333d2b36SAndroid Build Coastguard Worker} 501*333d2b36SAndroid Build Coastguard Worker 502*333d2b36SAndroid Build Coastguard Workerfunc TestConcurrentFindSameDirectory(t *testing.T) { 503*333d2b36SAndroid Build Coastguard Worker 504*333d2b36SAndroid Build Coastguard Worker testWithNumThreads := func(t *testing.T, numThreads int) { 505*333d2b36SAndroid Build Coastguard Worker filesystem := newFs() 506*333d2b36SAndroid Build Coastguard Worker 507*333d2b36SAndroid Build Coastguard Worker // create a bunch of files and directories 508*333d2b36SAndroid Build Coastguard Worker paths := []string{} 509*333d2b36SAndroid Build Coastguard Worker for i := 0; i < 10; i++ { 510*333d2b36SAndroid Build Coastguard Worker parentDir := fmt.Sprintf("/tmp/%v", i) 511*333d2b36SAndroid Build Coastguard Worker for j := 0; j < 10; j++ { 512*333d2b36SAndroid Build Coastguard Worker filePath := filepath.Join(parentDir, fmt.Sprintf("%v/findme.txt", j)) 513*333d2b36SAndroid Build Coastguard Worker paths = append(paths, filePath) 514*333d2b36SAndroid Build Coastguard Worker } 515*333d2b36SAndroid Build Coastguard Worker } 516*333d2b36SAndroid Build Coastguard Worker sort.Strings(paths) 517*333d2b36SAndroid Build Coastguard Worker for _, path := range paths { 518*333d2b36SAndroid Build Coastguard Worker fs.Create(t, path, filesystem) 519*333d2b36SAndroid Build Coastguard Worker } 520*333d2b36SAndroid Build Coastguard Worker 521*333d2b36SAndroid Build Coastguard Worker // set up a finder 522*333d2b36SAndroid Build Coastguard Worker finder := newFinderWithNumThreads( 523*333d2b36SAndroid Build Coastguard Worker t, 524*333d2b36SAndroid Build Coastguard Worker filesystem, 525*333d2b36SAndroid Build Coastguard Worker CacheParams{ 526*333d2b36SAndroid Build Coastguard Worker RootDirs: []string{"/tmp"}, 527*333d2b36SAndroid Build Coastguard Worker IncludeFiles: []string{"findme.txt"}, 528*333d2b36SAndroid Build Coastguard Worker }, 529*333d2b36SAndroid Build Coastguard Worker numThreads, 530*333d2b36SAndroid Build Coastguard Worker ) 531*333d2b36SAndroid Build Coastguard Worker defer finder.Shutdown() 532*333d2b36SAndroid Build Coastguard Worker 533*333d2b36SAndroid Build Coastguard Worker numTests := 20 534*333d2b36SAndroid Build Coastguard Worker results := make(chan []string, numTests) 535*333d2b36SAndroid Build Coastguard Worker // make several parallel calls to the finder 536*333d2b36SAndroid Build Coastguard Worker for i := 0; i < numTests; i++ { 537*333d2b36SAndroid Build Coastguard Worker go func() { 538*333d2b36SAndroid Build Coastguard Worker foundPaths := finder.FindNamedAt("/tmp", "findme.txt") 539*333d2b36SAndroid Build Coastguard Worker results <- foundPaths 540*333d2b36SAndroid Build Coastguard Worker }() 541*333d2b36SAndroid Build Coastguard Worker } 542*333d2b36SAndroid Build Coastguard Worker 543*333d2b36SAndroid Build Coastguard Worker // check that each response was correct 544*333d2b36SAndroid Build Coastguard Worker for i := 0; i < numTests; i++ { 545*333d2b36SAndroid Build Coastguard Worker foundPaths := <-results 546*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, paths) 547*333d2b36SAndroid Build Coastguard Worker } 548*333d2b36SAndroid Build Coastguard Worker } 549*333d2b36SAndroid Build Coastguard Worker 550*333d2b36SAndroid Build Coastguard Worker testAgainstSeveralThreadcounts(t, testWithNumThreads) 551*333d2b36SAndroid Build Coastguard Worker} 552*333d2b36SAndroid Build Coastguard Worker 553*333d2b36SAndroid Build Coastguard Workerfunc TestConcurrentFindDifferentDirectories(t *testing.T) { 554*333d2b36SAndroid Build Coastguard Worker filesystem := newFs() 555*333d2b36SAndroid Build Coastguard Worker 556*333d2b36SAndroid Build Coastguard Worker // create a bunch of files and directories 557*333d2b36SAndroid Build Coastguard Worker allFiles := []string{} 558*333d2b36SAndroid Build Coastguard Worker numSubdirs := 10 559*333d2b36SAndroid Build Coastguard Worker rootPaths := []string{} 560*333d2b36SAndroid Build Coastguard Worker queryAnswers := [][]string{} 561*333d2b36SAndroid Build Coastguard Worker for i := 0; i < numSubdirs; i++ { 562*333d2b36SAndroid Build Coastguard Worker parentDir := fmt.Sprintf("/tmp/%v", i) 563*333d2b36SAndroid Build Coastguard Worker rootPaths = append(rootPaths, parentDir) 564*333d2b36SAndroid Build Coastguard Worker queryAnswers = append(queryAnswers, []string{}) 565*333d2b36SAndroid Build Coastguard Worker for j := 0; j < 10; j++ { 566*333d2b36SAndroid Build Coastguard Worker filePath := filepath.Join(parentDir, fmt.Sprintf("%v/findme.txt", j)) 567*333d2b36SAndroid Build Coastguard Worker queryAnswers[i] = append(queryAnswers[i], filePath) 568*333d2b36SAndroid Build Coastguard Worker allFiles = append(allFiles, filePath) 569*333d2b36SAndroid Build Coastguard Worker } 570*333d2b36SAndroid Build Coastguard Worker sort.Strings(queryAnswers[i]) 571*333d2b36SAndroid Build Coastguard Worker } 572*333d2b36SAndroid Build Coastguard Worker sort.Strings(allFiles) 573*333d2b36SAndroid Build Coastguard Worker for _, path := range allFiles { 574*333d2b36SAndroid Build Coastguard Worker fs.Create(t, path, filesystem) 575*333d2b36SAndroid Build Coastguard Worker } 576*333d2b36SAndroid Build Coastguard Worker 577*333d2b36SAndroid Build Coastguard Worker // set up a finder 578*333d2b36SAndroid Build Coastguard Worker finder := newFinder( 579*333d2b36SAndroid Build Coastguard Worker t, 580*333d2b36SAndroid Build Coastguard Worker filesystem, 581*333d2b36SAndroid Build Coastguard Worker 582*333d2b36SAndroid Build Coastguard Worker CacheParams{ 583*333d2b36SAndroid Build Coastguard Worker RootDirs: []string{"/tmp"}, 584*333d2b36SAndroid Build Coastguard Worker IncludeFiles: []string{"findme.txt"}, 585*333d2b36SAndroid Build Coastguard Worker }, 586*333d2b36SAndroid Build Coastguard Worker ) 587*333d2b36SAndroid Build Coastguard Worker defer finder.Shutdown() 588*333d2b36SAndroid Build Coastguard Worker 589*333d2b36SAndroid Build Coastguard Worker type testRun struct { 590*333d2b36SAndroid Build Coastguard Worker path string 591*333d2b36SAndroid Build Coastguard Worker foundMatches []string 592*333d2b36SAndroid Build Coastguard Worker correctMatches []string 593*333d2b36SAndroid Build Coastguard Worker } 594*333d2b36SAndroid Build Coastguard Worker 595*333d2b36SAndroid Build Coastguard Worker numTests := numSubdirs + 1 596*333d2b36SAndroid Build Coastguard Worker testRuns := make(chan testRun, numTests) 597*333d2b36SAndroid Build Coastguard Worker 598*333d2b36SAndroid Build Coastguard Worker searchAt := func(path string, correctMatches []string) { 599*333d2b36SAndroid Build Coastguard Worker foundPaths := finder.FindNamedAt(path, "findme.txt") 600*333d2b36SAndroid Build Coastguard Worker testRuns <- testRun{path, foundPaths, correctMatches} 601*333d2b36SAndroid Build Coastguard Worker } 602*333d2b36SAndroid Build Coastguard Worker 603*333d2b36SAndroid Build Coastguard Worker // make several parallel calls to the finder 604*333d2b36SAndroid Build Coastguard Worker go searchAt("/tmp", allFiles) 605*333d2b36SAndroid Build Coastguard Worker for i := 0; i < len(rootPaths); i++ { 606*333d2b36SAndroid Build Coastguard Worker go searchAt(rootPaths[i], queryAnswers[i]) 607*333d2b36SAndroid Build Coastguard Worker } 608*333d2b36SAndroid Build Coastguard Worker 609*333d2b36SAndroid Build Coastguard Worker // check that each response was correct 610*333d2b36SAndroid Build Coastguard Worker for i := 0; i < numTests; i++ { 611*333d2b36SAndroid Build Coastguard Worker testRun := <-testRuns 612*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, testRun.foundMatches, testRun.correctMatches) 613*333d2b36SAndroid Build Coastguard Worker } 614*333d2b36SAndroid Build Coastguard Worker} 615*333d2b36SAndroid Build Coastguard Worker 616*333d2b36SAndroid Build Coastguard Workerfunc TestStrangelyFormattedPaths(t *testing.T) { 617*333d2b36SAndroid Build Coastguard Worker filesystem := newFs() 618*333d2b36SAndroid Build Coastguard Worker 619*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/findme.txt", filesystem) 620*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/a/findme.txt", filesystem) 621*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/b/findme.txt", filesystem) 622*333d2b36SAndroid Build Coastguard Worker 623*333d2b36SAndroid Build Coastguard Worker finder := newFinder( 624*333d2b36SAndroid Build Coastguard Worker t, 625*333d2b36SAndroid Build Coastguard Worker filesystem, 626*333d2b36SAndroid Build Coastguard Worker CacheParams{ 627*333d2b36SAndroid Build Coastguard Worker RootDirs: []string{"//tmp//a//.."}, 628*333d2b36SAndroid Build Coastguard Worker IncludeFiles: []string{"findme.txt"}, 629*333d2b36SAndroid Build Coastguard Worker }, 630*333d2b36SAndroid Build Coastguard Worker ) 631*333d2b36SAndroid Build Coastguard Worker defer finder.Shutdown() 632*333d2b36SAndroid Build Coastguard Worker 633*333d2b36SAndroid Build Coastguard Worker foundPaths := finder.FindNamedAt("//tmp//a//..", "findme.txt") 634*333d2b36SAndroid Build Coastguard Worker 635*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, 636*333d2b36SAndroid Build Coastguard Worker []string{"/tmp/a/findme.txt", 637*333d2b36SAndroid Build Coastguard Worker "/tmp/b/findme.txt", 638*333d2b36SAndroid Build Coastguard Worker "/tmp/findme.txt"}) 639*333d2b36SAndroid Build Coastguard Worker} 640*333d2b36SAndroid Build Coastguard Worker 641*333d2b36SAndroid Build Coastguard Workerfunc TestCorruptedCacheHeader(t *testing.T) { 642*333d2b36SAndroid Build Coastguard Worker filesystem := newFs() 643*333d2b36SAndroid Build Coastguard Worker 644*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/findme.txt", filesystem) 645*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/a/findme.txt", filesystem) 646*333d2b36SAndroid Build Coastguard Worker fs.Write(t, "/finder/finder-db", "sample header", filesystem) 647*333d2b36SAndroid Build Coastguard Worker 648*333d2b36SAndroid Build Coastguard Worker finder := newFinder( 649*333d2b36SAndroid Build Coastguard Worker t, 650*333d2b36SAndroid Build Coastguard Worker filesystem, 651*333d2b36SAndroid Build Coastguard Worker CacheParams{ 652*333d2b36SAndroid Build Coastguard Worker RootDirs: []string{"/tmp"}, 653*333d2b36SAndroid Build Coastguard Worker IncludeFiles: []string{"findme.txt"}, 654*333d2b36SAndroid Build Coastguard Worker }, 655*333d2b36SAndroid Build Coastguard Worker ) 656*333d2b36SAndroid Build Coastguard Worker defer finder.Shutdown() 657*333d2b36SAndroid Build Coastguard Worker 658*333d2b36SAndroid Build Coastguard Worker foundPaths := finder.FindNamedAt("/tmp", "findme.txt") 659*333d2b36SAndroid Build Coastguard Worker 660*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, 661*333d2b36SAndroid Build Coastguard Worker []string{"/tmp/a/findme.txt", 662*333d2b36SAndroid Build Coastguard Worker "/tmp/findme.txt"}) 663*333d2b36SAndroid Build Coastguard Worker} 664*333d2b36SAndroid Build Coastguard Worker 665*333d2b36SAndroid Build Coastguard Workerfunc TestCanUseCache(t *testing.T) { 666*333d2b36SAndroid Build Coastguard Worker // setup filesystem 667*333d2b36SAndroid Build Coastguard Worker filesystem := newFs() 668*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/findme.txt", filesystem) 669*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/a/findme.txt", filesystem) 670*333d2b36SAndroid Build Coastguard Worker 671*333d2b36SAndroid Build Coastguard Worker // run the first finder 672*333d2b36SAndroid Build Coastguard Worker finder := newFinder( 673*333d2b36SAndroid Build Coastguard Worker t, 674*333d2b36SAndroid Build Coastguard Worker filesystem, 675*333d2b36SAndroid Build Coastguard Worker CacheParams{ 676*333d2b36SAndroid Build Coastguard Worker RootDirs: []string{"/tmp"}, 677*333d2b36SAndroid Build Coastguard Worker IncludeFiles: []string{"findme.txt"}, 678*333d2b36SAndroid Build Coastguard Worker }, 679*333d2b36SAndroid Build Coastguard Worker ) 680*333d2b36SAndroid Build Coastguard Worker foundPaths := finder.FindNamedAt("/tmp", "findme.txt") 681*333d2b36SAndroid Build Coastguard Worker // check the response of the first finder 682*333d2b36SAndroid Build Coastguard Worker correctResponse := []string{"/tmp/a/findme.txt", 683*333d2b36SAndroid Build Coastguard Worker "/tmp/findme.txt"} 684*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, correctResponse) 685*333d2b36SAndroid Build Coastguard Worker finder.Shutdown() 686*333d2b36SAndroid Build Coastguard Worker 687*333d2b36SAndroid Build Coastguard Worker // check results 688*333d2b36SAndroid Build Coastguard Worker cacheText := fs.Read(t, finder.DbPath, filesystem) 689*333d2b36SAndroid Build Coastguard Worker if len(cacheText) < 1 { 690*333d2b36SAndroid Build Coastguard Worker t.Fatalf("saved cache db is empty\n") 691*333d2b36SAndroid Build Coastguard Worker } 692*333d2b36SAndroid Build Coastguard Worker if len(filesystem.StatCalls) == 0 { 693*333d2b36SAndroid Build Coastguard Worker t.Fatal("No Stat calls recorded by mock filesystem") 694*333d2b36SAndroid Build Coastguard Worker } 695*333d2b36SAndroid Build Coastguard Worker if len(filesystem.ReadDirCalls) == 0 { 696*333d2b36SAndroid Build Coastguard Worker t.Fatal("No ReadDir calls recorded by filesystem") 697*333d2b36SAndroid Build Coastguard Worker } 698*333d2b36SAndroid Build Coastguard Worker statCalls := filesystem.StatCalls 699*333d2b36SAndroid Build Coastguard Worker filesystem.ClearMetrics() 700*333d2b36SAndroid Build Coastguard Worker 701*333d2b36SAndroid Build Coastguard Worker // run the second finder 702*333d2b36SAndroid Build Coastguard Worker finder2 := finderWithSameParams(t, finder) 703*333d2b36SAndroid Build Coastguard Worker foundPaths = finder2.FindNamedAt("/tmp", "findme.txt") 704*333d2b36SAndroid Build Coastguard Worker // check results 705*333d2b36SAndroid Build Coastguard Worker fs.AssertSameReadDirCalls(t, filesystem.ReadDirCalls, []string{}) 706*333d2b36SAndroid Build Coastguard Worker fs.AssertSameReadDirCalls(t, filesystem.StatCalls, statCalls) 707*333d2b36SAndroid Build Coastguard Worker 708*333d2b36SAndroid Build Coastguard Worker finder2.Shutdown() 709*333d2b36SAndroid Build Coastguard Worker} 710*333d2b36SAndroid Build Coastguard Worker 711*333d2b36SAndroid Build Coastguard Workerfunc TestCorruptedCacheBody(t *testing.T) { 712*333d2b36SAndroid Build Coastguard Worker // setup filesystem 713*333d2b36SAndroid Build Coastguard Worker filesystem := newFs() 714*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/findme.txt", filesystem) 715*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/a/findme.txt", filesystem) 716*333d2b36SAndroid Build Coastguard Worker 717*333d2b36SAndroid Build Coastguard Worker // run the first finder 718*333d2b36SAndroid Build Coastguard Worker finder := newFinder( 719*333d2b36SAndroid Build Coastguard Worker t, 720*333d2b36SAndroid Build Coastguard Worker filesystem, 721*333d2b36SAndroid Build Coastguard Worker CacheParams{ 722*333d2b36SAndroid Build Coastguard Worker RootDirs: []string{"/tmp"}, 723*333d2b36SAndroid Build Coastguard Worker IncludeFiles: []string{"findme.txt"}, 724*333d2b36SAndroid Build Coastguard Worker }, 725*333d2b36SAndroid Build Coastguard Worker ) 726*333d2b36SAndroid Build Coastguard Worker foundPaths := finder.FindNamedAt("/tmp", "findme.txt") 727*333d2b36SAndroid Build Coastguard Worker finder.Shutdown() 728*333d2b36SAndroid Build Coastguard Worker 729*333d2b36SAndroid Build Coastguard Worker // check the response of the first finder 730*333d2b36SAndroid Build Coastguard Worker correctResponse := []string{"/tmp/a/findme.txt", 731*333d2b36SAndroid Build Coastguard Worker "/tmp/findme.txt"} 732*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, correctResponse) 733*333d2b36SAndroid Build Coastguard Worker numStatCalls := len(filesystem.StatCalls) 734*333d2b36SAndroid Build Coastguard Worker numReadDirCalls := len(filesystem.ReadDirCalls) 735*333d2b36SAndroid Build Coastguard Worker 736*333d2b36SAndroid Build Coastguard Worker // load the cache file, corrupt it, and save it 737*333d2b36SAndroid Build Coastguard Worker cacheReader, err := filesystem.Open(finder.DbPath) 738*333d2b36SAndroid Build Coastguard Worker if err != nil { 739*333d2b36SAndroid Build Coastguard Worker t.Fatal(err) 740*333d2b36SAndroid Build Coastguard Worker } 741*333d2b36SAndroid Build Coastguard Worker cacheData, err := ioutil.ReadAll(cacheReader) 742*333d2b36SAndroid Build Coastguard Worker if err != nil { 743*333d2b36SAndroid Build Coastguard Worker t.Fatal(err) 744*333d2b36SAndroid Build Coastguard Worker } 745*333d2b36SAndroid Build Coastguard Worker cacheData = append(cacheData, []byte("DontMindMe")...) 746*333d2b36SAndroid Build Coastguard Worker filesystem.WriteFile(finder.DbPath, cacheData, 0777) 747*333d2b36SAndroid Build Coastguard Worker filesystem.ClearMetrics() 748*333d2b36SAndroid Build Coastguard Worker 749*333d2b36SAndroid Build Coastguard Worker // run the second finder 750*333d2b36SAndroid Build Coastguard Worker finder2 := finderWithSameParams(t, finder) 751*333d2b36SAndroid Build Coastguard Worker foundPaths = finder2.FindNamedAt("/tmp", "findme.txt") 752*333d2b36SAndroid Build Coastguard Worker // check results 753*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, correctResponse) 754*333d2b36SAndroid Build Coastguard Worker numNewStatCalls := len(filesystem.StatCalls) 755*333d2b36SAndroid Build Coastguard Worker numNewReadDirCalls := len(filesystem.ReadDirCalls) 756*333d2b36SAndroid Build Coastguard Worker // It's permissable to make more Stat calls with a corrupted cache because 757*333d2b36SAndroid Build Coastguard Worker // the Finder may restart once it detects corruption. 758*333d2b36SAndroid Build Coastguard Worker // However, it may have already issued many Stat calls. 759*333d2b36SAndroid Build Coastguard Worker // Because a corrupted db is not expected to be a common (or even a supported case), 760*333d2b36SAndroid Build Coastguard Worker // we don't care to optimize it and don't cache the already-issued Stat calls 761*333d2b36SAndroid Build Coastguard Worker if numNewReadDirCalls < numReadDirCalls { 762*333d2b36SAndroid Build Coastguard Worker t.Fatalf( 763*333d2b36SAndroid Build Coastguard Worker "Finder made fewer ReadDir calls with a corrupted cache (%v calls) than with no cache"+ 764*333d2b36SAndroid Build Coastguard Worker " (%v calls)", 765*333d2b36SAndroid Build Coastguard Worker numNewReadDirCalls, numReadDirCalls) 766*333d2b36SAndroid Build Coastguard Worker } 767*333d2b36SAndroid Build Coastguard Worker if numNewStatCalls < numStatCalls { 768*333d2b36SAndroid Build Coastguard Worker t.Fatalf( 769*333d2b36SAndroid Build Coastguard Worker "Finder made fewer Stat calls with a corrupted cache (%v calls) than with no cache (%v calls)", 770*333d2b36SAndroid Build Coastguard Worker numNewStatCalls, numStatCalls) 771*333d2b36SAndroid Build Coastguard Worker } 772*333d2b36SAndroid Build Coastguard Worker finder2.Shutdown() 773*333d2b36SAndroid Build Coastguard Worker} 774*333d2b36SAndroid Build Coastguard Worker 775*333d2b36SAndroid Build Coastguard Workerfunc TestStatCalls(t *testing.T) { 776*333d2b36SAndroid Build Coastguard Worker // setup filesystem 777*333d2b36SAndroid Build Coastguard Worker filesystem := newFs() 778*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/a/findme.txt", filesystem) 779*333d2b36SAndroid Build Coastguard Worker 780*333d2b36SAndroid Build Coastguard Worker // run finder 781*333d2b36SAndroid Build Coastguard Worker finder := newFinder( 782*333d2b36SAndroid Build Coastguard Worker t, 783*333d2b36SAndroid Build Coastguard Worker filesystem, 784*333d2b36SAndroid Build Coastguard Worker CacheParams{ 785*333d2b36SAndroid Build Coastguard Worker RootDirs: []string{"/tmp"}, 786*333d2b36SAndroid Build Coastguard Worker IncludeFiles: []string{"findme.txt"}, 787*333d2b36SAndroid Build Coastguard Worker }, 788*333d2b36SAndroid Build Coastguard Worker ) 789*333d2b36SAndroid Build Coastguard Worker foundPaths := finder.FindNamedAt("/tmp", "findme.txt") 790*333d2b36SAndroid Build Coastguard Worker finder.Shutdown() 791*333d2b36SAndroid Build Coastguard Worker 792*333d2b36SAndroid Build Coastguard Worker // check response 793*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, []string{"/tmp/a/findme.txt"}) 794*333d2b36SAndroid Build Coastguard Worker fs.AssertSameStatCalls(t, filesystem.StatCalls, []string{"/tmp", "/tmp/a"}) 795*333d2b36SAndroid Build Coastguard Worker fs.AssertSameReadDirCalls(t, filesystem.ReadDirCalls, []string{"/tmp", "/tmp/a"}) 796*333d2b36SAndroid Build Coastguard Worker} 797*333d2b36SAndroid Build Coastguard Worker 798*333d2b36SAndroid Build Coastguard Workerfunc TestFileAdded(t *testing.T) { 799*333d2b36SAndroid Build Coastguard Worker // setup filesystem 800*333d2b36SAndroid Build Coastguard Worker filesystem := newFs() 801*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/ignoreme.txt", filesystem) 802*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/a/findme.txt", filesystem) 803*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/b/ignore.txt", filesystem) 804*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/b/c/nope.txt", filesystem) 805*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/b/c/d/irrelevant.txt", filesystem) 806*333d2b36SAndroid Build Coastguard Worker 807*333d2b36SAndroid Build Coastguard Worker // run the first finder 808*333d2b36SAndroid Build Coastguard Worker finder := newFinder( 809*333d2b36SAndroid Build Coastguard Worker t, 810*333d2b36SAndroid Build Coastguard Worker filesystem, 811*333d2b36SAndroid Build Coastguard Worker CacheParams{ 812*333d2b36SAndroid Build Coastguard Worker RootDirs: []string{"/tmp"}, 813*333d2b36SAndroid Build Coastguard Worker IncludeFiles: []string{"findme.txt"}, 814*333d2b36SAndroid Build Coastguard Worker }, 815*333d2b36SAndroid Build Coastguard Worker ) 816*333d2b36SAndroid Build Coastguard Worker finder.WaitForDbDump() 817*333d2b36SAndroid Build Coastguard Worker filesystem.Clock.Tick() 818*333d2b36SAndroid Build Coastguard Worker foundPaths := finder.FindNamedAt("/tmp", "findme.txt") 819*333d2b36SAndroid Build Coastguard Worker finder.Shutdown() 820*333d2b36SAndroid Build Coastguard Worker // check the response of the first finder 821*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, []string{"/tmp/a/findme.txt"}) 822*333d2b36SAndroid Build Coastguard Worker 823*333d2b36SAndroid Build Coastguard Worker // modify the filesystem 824*333d2b36SAndroid Build Coastguard Worker filesystem.Clock.Tick() 825*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/b/c/findme.txt", filesystem) 826*333d2b36SAndroid Build Coastguard Worker filesystem.Clock.Tick() 827*333d2b36SAndroid Build Coastguard Worker filesystem.ClearMetrics() 828*333d2b36SAndroid Build Coastguard Worker 829*333d2b36SAndroid Build Coastguard Worker // run the second finder 830*333d2b36SAndroid Build Coastguard Worker finder2 := finderWithSameParams(t, finder) 831*333d2b36SAndroid Build Coastguard Worker foundPaths = finder2.FindNamedAt("/tmp", "findme.txt") 832*333d2b36SAndroid Build Coastguard Worker 833*333d2b36SAndroid Build Coastguard Worker // check results 834*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, []string{"/tmp/a/findme.txt", "/tmp/b/c/findme.txt"}) 835*333d2b36SAndroid Build Coastguard Worker fs.AssertSameStatCalls(t, filesystem.StatCalls, []string{"/tmp", "/tmp/a", "/tmp/b", "/tmp/b/c", "/tmp/b/c/d"}) 836*333d2b36SAndroid Build Coastguard Worker fs.AssertSameReadDirCalls(t, filesystem.ReadDirCalls, []string{"/tmp/b/c"}) 837*333d2b36SAndroid Build Coastguard Worker finder2.Shutdown() 838*333d2b36SAndroid Build Coastguard Worker 839*333d2b36SAndroid Build Coastguard Worker} 840*333d2b36SAndroid Build Coastguard Worker 841*333d2b36SAndroid Build Coastguard Workerfunc TestDirectoriesAdded(t *testing.T) { 842*333d2b36SAndroid Build Coastguard Worker // setup filesystem 843*333d2b36SAndroid Build Coastguard Worker filesystem := newFs() 844*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/ignoreme.txt", filesystem) 845*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/a/findme.txt", filesystem) 846*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/b/ignore.txt", filesystem) 847*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/b/c/nope.txt", filesystem) 848*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/b/c/d/irrelevant.txt", filesystem) 849*333d2b36SAndroid Build Coastguard Worker 850*333d2b36SAndroid Build Coastguard Worker // run the first finder 851*333d2b36SAndroid Build Coastguard Worker finder := newFinder( 852*333d2b36SAndroid Build Coastguard Worker t, 853*333d2b36SAndroid Build Coastguard Worker filesystem, 854*333d2b36SAndroid Build Coastguard Worker CacheParams{ 855*333d2b36SAndroid Build Coastguard Worker RootDirs: []string{"/tmp"}, 856*333d2b36SAndroid Build Coastguard Worker IncludeFiles: []string{"findme.txt"}, 857*333d2b36SAndroid Build Coastguard Worker }, 858*333d2b36SAndroid Build Coastguard Worker ) 859*333d2b36SAndroid Build Coastguard Worker foundPaths := finder.FindNamedAt("/tmp", "findme.txt") 860*333d2b36SAndroid Build Coastguard Worker finder.Shutdown() 861*333d2b36SAndroid Build Coastguard Worker // check the response of the first finder 862*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, []string{"/tmp/a/findme.txt"}) 863*333d2b36SAndroid Build Coastguard Worker 864*333d2b36SAndroid Build Coastguard Worker // modify the filesystem 865*333d2b36SAndroid Build Coastguard Worker filesystem.Clock.Tick() 866*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/b/c/new/findme.txt", filesystem) 867*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/b/c/new/new2/findme.txt", filesystem) 868*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/b/c/new/new2/ignoreme.txt", filesystem) 869*333d2b36SAndroid Build Coastguard Worker filesystem.ClearMetrics() 870*333d2b36SAndroid Build Coastguard Worker 871*333d2b36SAndroid Build Coastguard Worker // run the second finder 872*333d2b36SAndroid Build Coastguard Worker finder2 := finderWithSameParams(t, finder) 873*333d2b36SAndroid Build Coastguard Worker foundPaths = finder2.FindNamedAt("/tmp", "findme.txt") 874*333d2b36SAndroid Build Coastguard Worker 875*333d2b36SAndroid Build Coastguard Worker // check results 876*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, 877*333d2b36SAndroid Build Coastguard Worker []string{"/tmp/a/findme.txt", "/tmp/b/c/new/findme.txt", "/tmp/b/c/new/new2/findme.txt"}) 878*333d2b36SAndroid Build Coastguard Worker fs.AssertSameStatCalls(t, filesystem.StatCalls, 879*333d2b36SAndroid Build Coastguard Worker []string{"/tmp", "/tmp/a", "/tmp/b", "/tmp/b/c", "/tmp/b/c/d", "/tmp/b/c/new", "/tmp/b/c/new/new2"}) 880*333d2b36SAndroid Build Coastguard Worker fs.AssertSameReadDirCalls(t, filesystem.ReadDirCalls, []string{"/tmp/b/c", "/tmp/b/c/new", "/tmp/b/c/new/new2"}) 881*333d2b36SAndroid Build Coastguard Worker 882*333d2b36SAndroid Build Coastguard Worker finder2.Shutdown() 883*333d2b36SAndroid Build Coastguard Worker} 884*333d2b36SAndroid Build Coastguard Worker 885*333d2b36SAndroid Build Coastguard Workerfunc TestDirectoryAndSubdirectoryBothUpdated(t *testing.T) { 886*333d2b36SAndroid Build Coastguard Worker // setup filesystem 887*333d2b36SAndroid Build Coastguard Worker filesystem := newFs() 888*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/hi1.txt", filesystem) 889*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/a/hi1.txt", filesystem) 890*333d2b36SAndroid Build Coastguard Worker 891*333d2b36SAndroid Build Coastguard Worker // run the first finder 892*333d2b36SAndroid Build Coastguard Worker finder := newFinder( 893*333d2b36SAndroid Build Coastguard Worker t, 894*333d2b36SAndroid Build Coastguard Worker filesystem, 895*333d2b36SAndroid Build Coastguard Worker CacheParams{ 896*333d2b36SAndroid Build Coastguard Worker RootDirs: []string{"/tmp"}, 897*333d2b36SAndroid Build Coastguard Worker IncludeFiles: []string{"hi1.txt", "hi2.txt"}, 898*333d2b36SAndroid Build Coastguard Worker }, 899*333d2b36SAndroid Build Coastguard Worker ) 900*333d2b36SAndroid Build Coastguard Worker foundPaths := finder.FindNamedAt("/tmp", "hi1.txt") 901*333d2b36SAndroid Build Coastguard Worker finder.Shutdown() 902*333d2b36SAndroid Build Coastguard Worker // check the response of the first finder 903*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, []string{"/tmp/hi1.txt", "/tmp/a/hi1.txt"}) 904*333d2b36SAndroid Build Coastguard Worker 905*333d2b36SAndroid Build Coastguard Worker // modify the filesystem 906*333d2b36SAndroid Build Coastguard Worker filesystem.Clock.Tick() 907*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/hi2.txt", filesystem) 908*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/a/hi2.txt", filesystem) 909*333d2b36SAndroid Build Coastguard Worker filesystem.ClearMetrics() 910*333d2b36SAndroid Build Coastguard Worker 911*333d2b36SAndroid Build Coastguard Worker // run the second finder 912*333d2b36SAndroid Build Coastguard Worker finder2 := finderWithSameParams(t, finder) 913*333d2b36SAndroid Build Coastguard Worker foundPaths = finder2.FindAll() 914*333d2b36SAndroid Build Coastguard Worker 915*333d2b36SAndroid Build Coastguard Worker // check results 916*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, 917*333d2b36SAndroid Build Coastguard Worker []string{"/tmp/hi1.txt", "/tmp/hi2.txt", "/tmp/a/hi1.txt", "/tmp/a/hi2.txt"}) 918*333d2b36SAndroid Build Coastguard Worker fs.AssertSameStatCalls(t, filesystem.StatCalls, 919*333d2b36SAndroid Build Coastguard Worker []string{"/tmp", "/tmp/a"}) 920*333d2b36SAndroid Build Coastguard Worker fs.AssertSameReadDirCalls(t, filesystem.ReadDirCalls, []string{"/tmp", "/tmp/a"}) 921*333d2b36SAndroid Build Coastguard Worker 922*333d2b36SAndroid Build Coastguard Worker finder2.Shutdown() 923*333d2b36SAndroid Build Coastguard Worker} 924*333d2b36SAndroid Build Coastguard Worker 925*333d2b36SAndroid Build Coastguard Workerfunc TestFileDeleted(t *testing.T) { 926*333d2b36SAndroid Build Coastguard Worker // setup filesystem 927*333d2b36SAndroid Build Coastguard Worker filesystem := newFs() 928*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/ignoreme.txt", filesystem) 929*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/a/findme.txt", filesystem) 930*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/b/findme.txt", filesystem) 931*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/b/c/nope.txt", filesystem) 932*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/b/c/d/irrelevant.txt", filesystem) 933*333d2b36SAndroid Build Coastguard Worker 934*333d2b36SAndroid Build Coastguard Worker // run the first finder 935*333d2b36SAndroid Build Coastguard Worker finder := newFinder( 936*333d2b36SAndroid Build Coastguard Worker t, 937*333d2b36SAndroid Build Coastguard Worker filesystem, 938*333d2b36SAndroid Build Coastguard Worker CacheParams{ 939*333d2b36SAndroid Build Coastguard Worker RootDirs: []string{"/tmp"}, 940*333d2b36SAndroid Build Coastguard Worker IncludeFiles: []string{"findme.txt"}, 941*333d2b36SAndroid Build Coastguard Worker }, 942*333d2b36SAndroid Build Coastguard Worker ) 943*333d2b36SAndroid Build Coastguard Worker foundPaths := finder.FindNamedAt("/tmp", "findme.txt") 944*333d2b36SAndroid Build Coastguard Worker finder.Shutdown() 945*333d2b36SAndroid Build Coastguard Worker // check the response of the first finder 946*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, []string{"/tmp/a/findme.txt", "/tmp/b/findme.txt"}) 947*333d2b36SAndroid Build Coastguard Worker 948*333d2b36SAndroid Build Coastguard Worker // modify the filesystem 949*333d2b36SAndroid Build Coastguard Worker filesystem.Clock.Tick() 950*333d2b36SAndroid Build Coastguard Worker fs.Delete(t, "/tmp/b/findme.txt", filesystem) 951*333d2b36SAndroid Build Coastguard Worker filesystem.ClearMetrics() 952*333d2b36SAndroid Build Coastguard Worker 953*333d2b36SAndroid Build Coastguard Worker // run the second finder 954*333d2b36SAndroid Build Coastguard Worker finder2 := finderWithSameParams(t, finder) 955*333d2b36SAndroid Build Coastguard Worker foundPaths = finder2.FindNamedAt("/tmp", "findme.txt") 956*333d2b36SAndroid Build Coastguard Worker 957*333d2b36SAndroid Build Coastguard Worker // check results 958*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, []string{"/tmp/a/findme.txt"}) 959*333d2b36SAndroid Build Coastguard Worker fs.AssertSameStatCalls(t, filesystem.StatCalls, []string{"/tmp", "/tmp/a", "/tmp/b", "/tmp/b/c", "/tmp/b/c/d"}) 960*333d2b36SAndroid Build Coastguard Worker fs.AssertSameReadDirCalls(t, filesystem.ReadDirCalls, []string{"/tmp/b"}) 961*333d2b36SAndroid Build Coastguard Worker 962*333d2b36SAndroid Build Coastguard Worker finder2.Shutdown() 963*333d2b36SAndroid Build Coastguard Worker} 964*333d2b36SAndroid Build Coastguard Worker 965*333d2b36SAndroid Build Coastguard Workerfunc TestDirectoriesDeleted(t *testing.T) { 966*333d2b36SAndroid Build Coastguard Worker // setup filesystem 967*333d2b36SAndroid Build Coastguard Worker filesystem := newFs() 968*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/findme.txt", filesystem) 969*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/a/findme.txt", filesystem) 970*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/a/1/findme.txt", filesystem) 971*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/a/1/2/findme.txt", filesystem) 972*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/b/findme.txt", filesystem) 973*333d2b36SAndroid Build Coastguard Worker 974*333d2b36SAndroid Build Coastguard Worker // run the first finder 975*333d2b36SAndroid Build Coastguard Worker finder := newFinder( 976*333d2b36SAndroid Build Coastguard Worker t, 977*333d2b36SAndroid Build Coastguard Worker filesystem, 978*333d2b36SAndroid Build Coastguard Worker CacheParams{ 979*333d2b36SAndroid Build Coastguard Worker RootDirs: []string{"/tmp"}, 980*333d2b36SAndroid Build Coastguard Worker IncludeFiles: []string{"findme.txt"}, 981*333d2b36SAndroid Build Coastguard Worker }, 982*333d2b36SAndroid Build Coastguard Worker ) 983*333d2b36SAndroid Build Coastguard Worker foundPaths := finder.FindNamedAt("/tmp", "findme.txt") 984*333d2b36SAndroid Build Coastguard Worker finder.Shutdown() 985*333d2b36SAndroid Build Coastguard Worker // check the response of the first finder 986*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, 987*333d2b36SAndroid Build Coastguard Worker []string{"/tmp/findme.txt", 988*333d2b36SAndroid Build Coastguard Worker "/tmp/a/findme.txt", 989*333d2b36SAndroid Build Coastguard Worker "/tmp/a/1/findme.txt", 990*333d2b36SAndroid Build Coastguard Worker "/tmp/a/1/2/findme.txt", 991*333d2b36SAndroid Build Coastguard Worker "/tmp/b/findme.txt"}) 992*333d2b36SAndroid Build Coastguard Worker 993*333d2b36SAndroid Build Coastguard Worker // modify the filesystem 994*333d2b36SAndroid Build Coastguard Worker filesystem.Clock.Tick() 995*333d2b36SAndroid Build Coastguard Worker fs.RemoveAll(t, "/tmp/a/1", filesystem) 996*333d2b36SAndroid Build Coastguard Worker filesystem.ClearMetrics() 997*333d2b36SAndroid Build Coastguard Worker 998*333d2b36SAndroid Build Coastguard Worker // run the second finder 999*333d2b36SAndroid Build Coastguard Worker finder2 := finderWithSameParams(t, finder) 1000*333d2b36SAndroid Build Coastguard Worker foundPaths = finder2.FindNamedAt("/tmp", "findme.txt") 1001*333d2b36SAndroid Build Coastguard Worker 1002*333d2b36SAndroid Build Coastguard Worker // check results 1003*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, 1004*333d2b36SAndroid Build Coastguard Worker []string{"/tmp/findme.txt", "/tmp/a/findme.txt", "/tmp/b/findme.txt"}) 1005*333d2b36SAndroid Build Coastguard Worker // Technically, we don't care whether /tmp/a/1/2 gets Statted or gets skipped 1006*333d2b36SAndroid Build Coastguard Worker // if the Finder detects the nonexistence of /tmp/a/1 1007*333d2b36SAndroid Build Coastguard Worker // However, when resuming from cache, we don't want the Finder to necessarily wait 1008*333d2b36SAndroid Build Coastguard Worker // to stat a directory until after statting its parent. 1009*333d2b36SAndroid Build Coastguard Worker // So here we just include /tmp/a/1/2 in the list. 1010*333d2b36SAndroid Build Coastguard Worker // The Finder is currently implemented to always restat every dir and 1011*333d2b36SAndroid Build Coastguard Worker // to not short-circuit due to nonexistence of parents (but it will remove 1012*333d2b36SAndroid Build Coastguard Worker // missing dirs from the cache for next time) 1013*333d2b36SAndroid Build Coastguard Worker fs.AssertSameStatCalls(t, filesystem.StatCalls, 1014*333d2b36SAndroid Build Coastguard Worker []string{"/tmp", "/tmp/a", "/tmp/a/1", "/tmp/a/1/2", "/tmp/b"}) 1015*333d2b36SAndroid Build Coastguard Worker fs.AssertSameReadDirCalls(t, filesystem.ReadDirCalls, []string{"/tmp/a"}) 1016*333d2b36SAndroid Build Coastguard Worker 1017*333d2b36SAndroid Build Coastguard Worker finder2.Shutdown() 1018*333d2b36SAndroid Build Coastguard Worker} 1019*333d2b36SAndroid Build Coastguard Worker 1020*333d2b36SAndroid Build Coastguard Workerfunc TestDirectoriesMoved(t *testing.T) { 1021*333d2b36SAndroid Build Coastguard Worker // setup filesystem 1022*333d2b36SAndroid Build Coastguard Worker filesystem := newFs() 1023*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/findme.txt", filesystem) 1024*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/a/findme.txt", filesystem) 1025*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/a/1/findme.txt", filesystem) 1026*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/a/1/2/findme.txt", filesystem) 1027*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/b/findme.txt", filesystem) 1028*333d2b36SAndroid Build Coastguard Worker 1029*333d2b36SAndroid Build Coastguard Worker // run the first finder 1030*333d2b36SAndroid Build Coastguard Worker finder := newFinder( 1031*333d2b36SAndroid Build Coastguard Worker t, 1032*333d2b36SAndroid Build Coastguard Worker filesystem, 1033*333d2b36SAndroid Build Coastguard Worker CacheParams{ 1034*333d2b36SAndroid Build Coastguard Worker RootDirs: []string{"/tmp"}, 1035*333d2b36SAndroid Build Coastguard Worker IncludeFiles: []string{"findme.txt"}, 1036*333d2b36SAndroid Build Coastguard Worker }, 1037*333d2b36SAndroid Build Coastguard Worker ) 1038*333d2b36SAndroid Build Coastguard Worker foundPaths := finder.FindNamedAt("/tmp", "findme.txt") 1039*333d2b36SAndroid Build Coastguard Worker finder.Shutdown() 1040*333d2b36SAndroid Build Coastguard Worker // check the response of the first finder 1041*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, 1042*333d2b36SAndroid Build Coastguard Worker []string{"/tmp/findme.txt", 1043*333d2b36SAndroid Build Coastguard Worker "/tmp/a/findme.txt", 1044*333d2b36SAndroid Build Coastguard Worker "/tmp/a/1/findme.txt", 1045*333d2b36SAndroid Build Coastguard Worker "/tmp/a/1/2/findme.txt", 1046*333d2b36SAndroid Build Coastguard Worker "/tmp/b/findme.txt"}) 1047*333d2b36SAndroid Build Coastguard Worker 1048*333d2b36SAndroid Build Coastguard Worker // modify the filesystem 1049*333d2b36SAndroid Build Coastguard Worker filesystem.Clock.Tick() 1050*333d2b36SAndroid Build Coastguard Worker fs.Move(t, "/tmp/a", "/tmp/c", filesystem) 1051*333d2b36SAndroid Build Coastguard Worker filesystem.ClearMetrics() 1052*333d2b36SAndroid Build Coastguard Worker 1053*333d2b36SAndroid Build Coastguard Worker // run the second finder 1054*333d2b36SAndroid Build Coastguard Worker finder2 := finderWithSameParams(t, finder) 1055*333d2b36SAndroid Build Coastguard Worker foundPaths = finder2.FindNamedAt("/tmp", "findme.txt") 1056*333d2b36SAndroid Build Coastguard Worker 1057*333d2b36SAndroid Build Coastguard Worker // check results 1058*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, 1059*333d2b36SAndroid Build Coastguard Worker []string{"/tmp/findme.txt", 1060*333d2b36SAndroid Build Coastguard Worker "/tmp/b/findme.txt", 1061*333d2b36SAndroid Build Coastguard Worker "/tmp/c/findme.txt", 1062*333d2b36SAndroid Build Coastguard Worker "/tmp/c/1/findme.txt", 1063*333d2b36SAndroid Build Coastguard Worker "/tmp/c/1/2/findme.txt"}) 1064*333d2b36SAndroid Build Coastguard Worker // Technically, we don't care whether /tmp/a/1/2 gets Statted or gets skipped 1065*333d2b36SAndroid Build Coastguard Worker // if the Finder detects the nonexistence of /tmp/a/1 1066*333d2b36SAndroid Build Coastguard Worker // However, when resuming from cache, we don't want the Finder to necessarily wait 1067*333d2b36SAndroid Build Coastguard Worker // to stat a directory until after statting its parent. 1068*333d2b36SAndroid Build Coastguard Worker // So here we just include /tmp/a/1/2 in the list. 1069*333d2b36SAndroid Build Coastguard Worker // The Finder is currently implemented to always restat every dir and 1070*333d2b36SAndroid Build Coastguard Worker // to not short-circuit due to nonexistence of parents (but it will remove 1071*333d2b36SAndroid Build Coastguard Worker // missing dirs from the cache for next time) 1072*333d2b36SAndroid Build Coastguard Worker fs.AssertSameStatCalls(t, filesystem.StatCalls, 1073*333d2b36SAndroid Build Coastguard Worker []string{"/tmp", "/tmp/a", "/tmp/a/1", "/tmp/a/1/2", "/tmp/b", "/tmp/c", "/tmp/c/1", "/tmp/c/1/2"}) 1074*333d2b36SAndroid Build Coastguard Worker fs.AssertSameReadDirCalls(t, filesystem.ReadDirCalls, []string{"/tmp", "/tmp/c", "/tmp/c/1", "/tmp/c/1/2"}) 1075*333d2b36SAndroid Build Coastguard Worker finder2.Shutdown() 1076*333d2b36SAndroid Build Coastguard Worker} 1077*333d2b36SAndroid Build Coastguard Worker 1078*333d2b36SAndroid Build Coastguard Workerfunc TestDirectoriesSwapped(t *testing.T) { 1079*333d2b36SAndroid Build Coastguard Worker // setup filesystem 1080*333d2b36SAndroid Build Coastguard Worker filesystem := newFs() 1081*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/findme.txt", filesystem) 1082*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/a/findme.txt", filesystem) 1083*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/a/1/findme.txt", filesystem) 1084*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/a/1/2/findme.txt", filesystem) 1085*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/b/findme.txt", filesystem) 1086*333d2b36SAndroid Build Coastguard Worker 1087*333d2b36SAndroid Build Coastguard Worker // run the first finder 1088*333d2b36SAndroid Build Coastguard Worker finder := newFinder( 1089*333d2b36SAndroid Build Coastguard Worker t, 1090*333d2b36SAndroid Build Coastguard Worker filesystem, 1091*333d2b36SAndroid Build Coastguard Worker CacheParams{ 1092*333d2b36SAndroid Build Coastguard Worker RootDirs: []string{"/tmp"}, 1093*333d2b36SAndroid Build Coastguard Worker IncludeFiles: []string{"findme.txt"}, 1094*333d2b36SAndroid Build Coastguard Worker }, 1095*333d2b36SAndroid Build Coastguard Worker ) 1096*333d2b36SAndroid Build Coastguard Worker foundPaths := finder.FindNamedAt("/tmp", "findme.txt") 1097*333d2b36SAndroid Build Coastguard Worker finder.Shutdown() 1098*333d2b36SAndroid Build Coastguard Worker // check the response of the first finder 1099*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, 1100*333d2b36SAndroid Build Coastguard Worker []string{"/tmp/findme.txt", 1101*333d2b36SAndroid Build Coastguard Worker "/tmp/a/findme.txt", 1102*333d2b36SAndroid Build Coastguard Worker "/tmp/a/1/findme.txt", 1103*333d2b36SAndroid Build Coastguard Worker "/tmp/a/1/2/findme.txt", 1104*333d2b36SAndroid Build Coastguard Worker "/tmp/b/findme.txt"}) 1105*333d2b36SAndroid Build Coastguard Worker 1106*333d2b36SAndroid Build Coastguard Worker // modify the filesystem 1107*333d2b36SAndroid Build Coastguard Worker filesystem.Clock.Tick() 1108*333d2b36SAndroid Build Coastguard Worker fs.Move(t, "/tmp/a", "/tmp/temp", filesystem) 1109*333d2b36SAndroid Build Coastguard Worker fs.Move(t, "/tmp/b", "/tmp/a", filesystem) 1110*333d2b36SAndroid Build Coastguard Worker fs.Move(t, "/tmp/temp", "/tmp/b", filesystem) 1111*333d2b36SAndroid Build Coastguard Worker filesystem.ClearMetrics() 1112*333d2b36SAndroid Build Coastguard Worker 1113*333d2b36SAndroid Build Coastguard Worker // run the second finder 1114*333d2b36SAndroid Build Coastguard Worker finder2 := finderWithSameParams(t, finder) 1115*333d2b36SAndroid Build Coastguard Worker foundPaths = finder2.FindNamedAt("/tmp", "findme.txt") 1116*333d2b36SAndroid Build Coastguard Worker 1117*333d2b36SAndroid Build Coastguard Worker // check results 1118*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, 1119*333d2b36SAndroid Build Coastguard Worker []string{"/tmp/findme.txt", 1120*333d2b36SAndroid Build Coastguard Worker "/tmp/a/findme.txt", 1121*333d2b36SAndroid Build Coastguard Worker "/tmp/b/findme.txt", 1122*333d2b36SAndroid Build Coastguard Worker "/tmp/b/1/findme.txt", 1123*333d2b36SAndroid Build Coastguard Worker "/tmp/b/1/2/findme.txt"}) 1124*333d2b36SAndroid Build Coastguard Worker // Technically, we don't care whether /tmp/a/1/2 gets Statted or gets skipped 1125*333d2b36SAndroid Build Coastguard Worker // if the Finder detects the nonexistence of /tmp/a/1 1126*333d2b36SAndroid Build Coastguard Worker // However, when resuming from cache, we don't want the Finder to necessarily wait 1127*333d2b36SAndroid Build Coastguard Worker // to stat a directory until after statting its parent. 1128*333d2b36SAndroid Build Coastguard Worker // So here we just include /tmp/a/1/2 in the list. 1129*333d2b36SAndroid Build Coastguard Worker // The Finder is currently implemented to always restat every dir and 1130*333d2b36SAndroid Build Coastguard Worker // to not short-circuit due to nonexistence of parents (but it will remove 1131*333d2b36SAndroid Build Coastguard Worker // missing dirs from the cache for next time) 1132*333d2b36SAndroid Build Coastguard Worker fs.AssertSameStatCalls(t, filesystem.StatCalls, 1133*333d2b36SAndroid Build Coastguard Worker []string{"/tmp", "/tmp/a", "/tmp/a/1", "/tmp/a/1/2", "/tmp/b", "/tmp/b/1", "/tmp/b/1/2"}) 1134*333d2b36SAndroid Build Coastguard Worker fs.AssertSameReadDirCalls(t, filesystem.ReadDirCalls, []string{"/tmp", "/tmp/a", "/tmp/b", "/tmp/b/1", "/tmp/b/1/2"}) 1135*333d2b36SAndroid Build Coastguard Worker finder2.Shutdown() 1136*333d2b36SAndroid Build Coastguard Worker} 1137*333d2b36SAndroid Build Coastguard Worker 1138*333d2b36SAndroid Build Coastguard Worker// runFsReplacementTest tests a change modifying properties of the filesystem itself: 1139*333d2b36SAndroid Build Coastguard Worker// runFsReplacementTest tests changing the user, the hostname, or the device number 1140*333d2b36SAndroid Build Coastguard Worker// runFsReplacementTest is a helper method called by other tests 1141*333d2b36SAndroid Build Coastguard Workerfunc runFsReplacementTest(t *testing.T, fs1 *fs.MockFs, fs2 *fs.MockFs) { 1142*333d2b36SAndroid Build Coastguard Worker // setup fs1 1143*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/findme.txt", fs1) 1144*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/a/findme.txt", fs1) 1145*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/a/a/findme.txt", fs1) 1146*333d2b36SAndroid Build Coastguard Worker 1147*333d2b36SAndroid Build Coastguard Worker // setup fs2 to have the same directories but different files 1148*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/findme.txt", fs2) 1149*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/a/findme.txt", fs2) 1150*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/a/a/ignoreme.txt", fs2) 1151*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/a/b/findme.txt", fs2) 1152*333d2b36SAndroid Build Coastguard Worker 1153*333d2b36SAndroid Build Coastguard Worker // run the first finder 1154*333d2b36SAndroid Build Coastguard Worker finder := newFinder( 1155*333d2b36SAndroid Build Coastguard Worker t, 1156*333d2b36SAndroid Build Coastguard Worker fs1, 1157*333d2b36SAndroid Build Coastguard Worker CacheParams{ 1158*333d2b36SAndroid Build Coastguard Worker RootDirs: []string{"/tmp"}, 1159*333d2b36SAndroid Build Coastguard Worker IncludeFiles: []string{"findme.txt"}, 1160*333d2b36SAndroid Build Coastguard Worker }, 1161*333d2b36SAndroid Build Coastguard Worker ) 1162*333d2b36SAndroid Build Coastguard Worker foundPaths := finder.FindNamedAt("/tmp", "findme.txt") 1163*333d2b36SAndroid Build Coastguard Worker finder.Shutdown() 1164*333d2b36SAndroid Build Coastguard Worker // check the response of the first finder 1165*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, 1166*333d2b36SAndroid Build Coastguard Worker []string{"/tmp/findme.txt", "/tmp/a/findme.txt", "/tmp/a/a/findme.txt"}) 1167*333d2b36SAndroid Build Coastguard Worker 1168*333d2b36SAndroid Build Coastguard Worker // copy the cache data from the first filesystem to the second 1169*333d2b36SAndroid Build Coastguard Worker cacheContent := fs.Read(t, finder.DbPath, fs1) 1170*333d2b36SAndroid Build Coastguard Worker fs.Write(t, finder.DbPath, cacheContent, fs2) 1171*333d2b36SAndroid Build Coastguard Worker 1172*333d2b36SAndroid Build Coastguard Worker // run the second finder, with the same config and same cache contents but a different filesystem 1173*333d2b36SAndroid Build Coastguard Worker finder2 := newFinder( 1174*333d2b36SAndroid Build Coastguard Worker t, 1175*333d2b36SAndroid Build Coastguard Worker fs2, 1176*333d2b36SAndroid Build Coastguard Worker CacheParams{ 1177*333d2b36SAndroid Build Coastguard Worker RootDirs: []string{"/tmp"}, 1178*333d2b36SAndroid Build Coastguard Worker IncludeFiles: []string{"findme.txt"}, 1179*333d2b36SAndroid Build Coastguard Worker }, 1180*333d2b36SAndroid Build Coastguard Worker ) 1181*333d2b36SAndroid Build Coastguard Worker foundPaths = finder2.FindNamedAt("/tmp", "findme.txt") 1182*333d2b36SAndroid Build Coastguard Worker 1183*333d2b36SAndroid Build Coastguard Worker // check results 1184*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, 1185*333d2b36SAndroid Build Coastguard Worker []string{"/tmp/findme.txt", "/tmp/a/findme.txt", "/tmp/a/b/findme.txt"}) 1186*333d2b36SAndroid Build Coastguard Worker fs.AssertSameStatCalls(t, fs2.StatCalls, 1187*333d2b36SAndroid Build Coastguard Worker []string{"/tmp", "/tmp/a", "/tmp/a/a", "/tmp/a/b"}) 1188*333d2b36SAndroid Build Coastguard Worker fs.AssertSameReadDirCalls(t, fs2.ReadDirCalls, 1189*333d2b36SAndroid Build Coastguard Worker []string{"/tmp", "/tmp/a", "/tmp/a/a", "/tmp/a/b"}) 1190*333d2b36SAndroid Build Coastguard Worker finder2.Shutdown() 1191*333d2b36SAndroid Build Coastguard Worker} 1192*333d2b36SAndroid Build Coastguard Worker 1193*333d2b36SAndroid Build Coastguard Workerfunc TestChangeOfDevice(t *testing.T) { 1194*333d2b36SAndroid Build Coastguard Worker fs1 := newFs() 1195*333d2b36SAndroid Build Coastguard Worker // not as fine-grained mounting controls as a real filesystem, but should be adequate 1196*333d2b36SAndroid Build Coastguard Worker fs1.SetDeviceNumber(0) 1197*333d2b36SAndroid Build Coastguard Worker 1198*333d2b36SAndroid Build Coastguard Worker fs2 := newFs() 1199*333d2b36SAndroid Build Coastguard Worker fs2.SetDeviceNumber(1) 1200*333d2b36SAndroid Build Coastguard Worker 1201*333d2b36SAndroid Build Coastguard Worker runFsReplacementTest(t, fs1, fs2) 1202*333d2b36SAndroid Build Coastguard Worker} 1203*333d2b36SAndroid Build Coastguard Worker 1204*333d2b36SAndroid Build Coastguard Workerfunc TestChangeOfUserOrHost(t *testing.T) { 1205*333d2b36SAndroid Build Coastguard Worker fs1 := newFs() 1206*333d2b36SAndroid Build Coastguard Worker fs1.SetViewId("me@here") 1207*333d2b36SAndroid Build Coastguard Worker 1208*333d2b36SAndroid Build Coastguard Worker fs2 := newFs() 1209*333d2b36SAndroid Build Coastguard Worker fs2.SetViewId("you@there") 1210*333d2b36SAndroid Build Coastguard Worker 1211*333d2b36SAndroid Build Coastguard Worker runFsReplacementTest(t, fs1, fs2) 1212*333d2b36SAndroid Build Coastguard Worker} 1213*333d2b36SAndroid Build Coastguard Worker 1214*333d2b36SAndroid Build Coastguard Workerfunc TestConsistentCacheOrdering(t *testing.T) { 1215*333d2b36SAndroid Build Coastguard Worker // setup filesystem 1216*333d2b36SAndroid Build Coastguard Worker filesystem := newFs() 1217*333d2b36SAndroid Build Coastguard Worker for i := 0; i < 5; i++ { 1218*333d2b36SAndroid Build Coastguard Worker fs.Create(t, fmt.Sprintf("/tmp/%v/findme.txt", i), filesystem) 1219*333d2b36SAndroid Build Coastguard Worker } 1220*333d2b36SAndroid Build Coastguard Worker 1221*333d2b36SAndroid Build Coastguard Worker // run the first finder 1222*333d2b36SAndroid Build Coastguard Worker finder := newFinder( 1223*333d2b36SAndroid Build Coastguard Worker t, 1224*333d2b36SAndroid Build Coastguard Worker filesystem, 1225*333d2b36SAndroid Build Coastguard Worker CacheParams{ 1226*333d2b36SAndroid Build Coastguard Worker RootDirs: []string{"/tmp"}, 1227*333d2b36SAndroid Build Coastguard Worker IncludeFiles: []string{"findme.txt"}, 1228*333d2b36SAndroid Build Coastguard Worker }, 1229*333d2b36SAndroid Build Coastguard Worker ) 1230*333d2b36SAndroid Build Coastguard Worker finder.FindNamedAt("/tmp", "findme.txt") 1231*333d2b36SAndroid Build Coastguard Worker finder.Shutdown() 1232*333d2b36SAndroid Build Coastguard Worker 1233*333d2b36SAndroid Build Coastguard Worker // read db file 1234*333d2b36SAndroid Build Coastguard Worker string1 := fs.Read(t, finder.DbPath, filesystem) 1235*333d2b36SAndroid Build Coastguard Worker 1236*333d2b36SAndroid Build Coastguard Worker err := filesystem.Remove(finder.DbPath) 1237*333d2b36SAndroid Build Coastguard Worker if err != nil { 1238*333d2b36SAndroid Build Coastguard Worker t.Fatal(err) 1239*333d2b36SAndroid Build Coastguard Worker } 1240*333d2b36SAndroid Build Coastguard Worker 1241*333d2b36SAndroid Build Coastguard Worker // run another finder 1242*333d2b36SAndroid Build Coastguard Worker finder2 := finderWithSameParams(t, finder) 1243*333d2b36SAndroid Build Coastguard Worker finder2.FindNamedAt("/tmp", "findme.txt") 1244*333d2b36SAndroid Build Coastguard Worker finder2.Shutdown() 1245*333d2b36SAndroid Build Coastguard Worker 1246*333d2b36SAndroid Build Coastguard Worker string2 := fs.Read(t, finder.DbPath, filesystem) 1247*333d2b36SAndroid Build Coastguard Worker 1248*333d2b36SAndroid Build Coastguard Worker if string1 != string2 { 1249*333d2b36SAndroid Build Coastguard Worker t.Errorf("Running Finder twice generated two dbs not having identical contents.\n"+ 1250*333d2b36SAndroid Build Coastguard Worker "Content of first file:\n"+ 1251*333d2b36SAndroid Build Coastguard Worker "\n"+ 1252*333d2b36SAndroid Build Coastguard Worker "%v"+ 1253*333d2b36SAndroid Build Coastguard Worker "\n"+ 1254*333d2b36SAndroid Build Coastguard Worker "\n"+ 1255*333d2b36SAndroid Build Coastguard Worker "Content of second file:\n"+ 1256*333d2b36SAndroid Build Coastguard Worker "\n"+ 1257*333d2b36SAndroid Build Coastguard Worker "%v\n"+ 1258*333d2b36SAndroid Build Coastguard Worker "\n", 1259*333d2b36SAndroid Build Coastguard Worker string1, 1260*333d2b36SAndroid Build Coastguard Worker string2, 1261*333d2b36SAndroid Build Coastguard Worker ) 1262*333d2b36SAndroid Build Coastguard Worker } 1263*333d2b36SAndroid Build Coastguard Worker 1264*333d2b36SAndroid Build Coastguard Worker} 1265*333d2b36SAndroid Build Coastguard Worker 1266*333d2b36SAndroid Build Coastguard Workerfunc TestNumSyscallsOfSecondFind(t *testing.T) { 1267*333d2b36SAndroid Build Coastguard Worker // setup filesystem 1268*333d2b36SAndroid Build Coastguard Worker filesystem := newFs() 1269*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/findme.txt", filesystem) 1270*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/a/findme.txt", filesystem) 1271*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/a/misc.txt", filesystem) 1272*333d2b36SAndroid Build Coastguard Worker 1273*333d2b36SAndroid Build Coastguard Worker // set up the finder and run it once 1274*333d2b36SAndroid Build Coastguard Worker finder := newFinder( 1275*333d2b36SAndroid Build Coastguard Worker t, 1276*333d2b36SAndroid Build Coastguard Worker filesystem, 1277*333d2b36SAndroid Build Coastguard Worker CacheParams{ 1278*333d2b36SAndroid Build Coastguard Worker RootDirs: []string{"/tmp"}, 1279*333d2b36SAndroid Build Coastguard Worker IncludeFiles: []string{"findme.txt"}, 1280*333d2b36SAndroid Build Coastguard Worker }, 1281*333d2b36SAndroid Build Coastguard Worker ) 1282*333d2b36SAndroid Build Coastguard Worker foundPaths := finder.FindNamedAt("/tmp", "findme.txt") 1283*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, []string{"/tmp/findme.txt", "/tmp/a/findme.txt"}) 1284*333d2b36SAndroid Build Coastguard Worker 1285*333d2b36SAndroid Build Coastguard Worker filesystem.ClearMetrics() 1286*333d2b36SAndroid Build Coastguard Worker 1287*333d2b36SAndroid Build Coastguard Worker // run the finder again and confirm it doesn't check the filesystem 1288*333d2b36SAndroid Build Coastguard Worker refoundPaths := finder.FindNamedAt("/tmp", "findme.txt") 1289*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, refoundPaths, foundPaths) 1290*333d2b36SAndroid Build Coastguard Worker fs.AssertSameStatCalls(t, filesystem.StatCalls, []string{}) 1291*333d2b36SAndroid Build Coastguard Worker fs.AssertSameReadDirCalls(t, filesystem.ReadDirCalls, []string{}) 1292*333d2b36SAndroid Build Coastguard Worker 1293*333d2b36SAndroid Build Coastguard Worker finder.Shutdown() 1294*333d2b36SAndroid Build Coastguard Worker} 1295*333d2b36SAndroid Build Coastguard Worker 1296*333d2b36SAndroid Build Coastguard Workerfunc TestChangingParamsOfSecondFind(t *testing.T) { 1297*333d2b36SAndroid Build Coastguard Worker // setup filesystem 1298*333d2b36SAndroid Build Coastguard Worker filesystem := newFs() 1299*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/findme.txt", filesystem) 1300*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/a/findme.txt", filesystem) 1301*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/a/metoo.txt", filesystem) 1302*333d2b36SAndroid Build Coastguard Worker 1303*333d2b36SAndroid Build Coastguard Worker // set up the finder and run it once 1304*333d2b36SAndroid Build Coastguard Worker finder := newFinder( 1305*333d2b36SAndroid Build Coastguard Worker t, 1306*333d2b36SAndroid Build Coastguard Worker filesystem, 1307*333d2b36SAndroid Build Coastguard Worker CacheParams{ 1308*333d2b36SAndroid Build Coastguard Worker RootDirs: []string{"/tmp"}, 1309*333d2b36SAndroid Build Coastguard Worker IncludeFiles: []string{"findme.txt", "metoo.txt"}, 1310*333d2b36SAndroid Build Coastguard Worker }, 1311*333d2b36SAndroid Build Coastguard Worker ) 1312*333d2b36SAndroid Build Coastguard Worker foundPaths := finder.FindNamedAt("/tmp", "findme.txt") 1313*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, []string{"/tmp/findme.txt", "/tmp/a/findme.txt"}) 1314*333d2b36SAndroid Build Coastguard Worker 1315*333d2b36SAndroid Build Coastguard Worker filesystem.ClearMetrics() 1316*333d2b36SAndroid Build Coastguard Worker 1317*333d2b36SAndroid Build Coastguard Worker // run the finder again and confirm it gets the right answer without asking the filesystem 1318*333d2b36SAndroid Build Coastguard Worker refoundPaths := finder.FindNamedAt("/tmp", "metoo.txt") 1319*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, refoundPaths, []string{"/tmp/a/metoo.txt"}) 1320*333d2b36SAndroid Build Coastguard Worker fs.AssertSameStatCalls(t, filesystem.StatCalls, []string{}) 1321*333d2b36SAndroid Build Coastguard Worker fs.AssertSameReadDirCalls(t, filesystem.ReadDirCalls, []string{}) 1322*333d2b36SAndroid Build Coastguard Worker 1323*333d2b36SAndroid Build Coastguard Worker finder.Shutdown() 1324*333d2b36SAndroid Build Coastguard Worker} 1325*333d2b36SAndroid Build Coastguard Worker 1326*333d2b36SAndroid Build Coastguard Workerfunc TestSymlinkPointingToFile(t *testing.T) { 1327*333d2b36SAndroid Build Coastguard Worker // setup filesystem 1328*333d2b36SAndroid Build Coastguard Worker filesystem := newFs() 1329*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/a/hi.txt", filesystem) 1330*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/a/ignoreme.txt", filesystem) 1331*333d2b36SAndroid Build Coastguard Worker fs.Link(t, "/tmp/hi.txt", "a/hi.txt", filesystem) 1332*333d2b36SAndroid Build Coastguard Worker fs.Link(t, "/tmp/b/hi.txt", "../a/hi.txt", filesystem) 1333*333d2b36SAndroid Build Coastguard Worker fs.Link(t, "/tmp/c/hi.txt", "/tmp/hi.txt", filesystem) 1334*333d2b36SAndroid Build Coastguard Worker fs.Link(t, "/tmp/d/hi.txt", "../a/bye.txt", filesystem) 1335*333d2b36SAndroid Build Coastguard Worker fs.Link(t, "/tmp/d/bye.txt", "../a/hi.txt", filesystem) 1336*333d2b36SAndroid Build Coastguard Worker fs.Link(t, "/tmp/e/bye.txt", "../a/bye.txt", filesystem) 1337*333d2b36SAndroid Build Coastguard Worker fs.Link(t, "/tmp/f/hi.txt", "somethingThatDoesntExist", filesystem) 1338*333d2b36SAndroid Build Coastguard Worker 1339*333d2b36SAndroid Build Coastguard Worker // set up the finder and run it once 1340*333d2b36SAndroid Build Coastguard Worker finder := newFinder( 1341*333d2b36SAndroid Build Coastguard Worker t, 1342*333d2b36SAndroid Build Coastguard Worker filesystem, 1343*333d2b36SAndroid Build Coastguard Worker CacheParams{ 1344*333d2b36SAndroid Build Coastguard Worker RootDirs: []string{"/tmp"}, 1345*333d2b36SAndroid Build Coastguard Worker IncludeFiles: []string{"hi.txt"}, 1346*333d2b36SAndroid Build Coastguard Worker }, 1347*333d2b36SAndroid Build Coastguard Worker ) 1348*333d2b36SAndroid Build Coastguard Worker foundPaths := finder.FindNamedAt("/tmp", "hi.txt") 1349*333d2b36SAndroid Build Coastguard Worker // should search based on the name of the link rather than the destination or validity of the link 1350*333d2b36SAndroid Build Coastguard Worker correctResponse := []string{ 1351*333d2b36SAndroid Build Coastguard Worker "/tmp/a/hi.txt", 1352*333d2b36SAndroid Build Coastguard Worker "/tmp/hi.txt", 1353*333d2b36SAndroid Build Coastguard Worker "/tmp/b/hi.txt", 1354*333d2b36SAndroid Build Coastguard Worker "/tmp/c/hi.txt", 1355*333d2b36SAndroid Build Coastguard Worker "/tmp/d/hi.txt", 1356*333d2b36SAndroid Build Coastguard Worker "/tmp/f/hi.txt", 1357*333d2b36SAndroid Build Coastguard Worker } 1358*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, correctResponse) 1359*333d2b36SAndroid Build Coastguard Worker 1360*333d2b36SAndroid Build Coastguard Worker} 1361*333d2b36SAndroid Build Coastguard Worker 1362*333d2b36SAndroid Build Coastguard Workerfunc TestSymlinkPointingToDirectory(t *testing.T) { 1363*333d2b36SAndroid Build Coastguard Worker // setup filesystem 1364*333d2b36SAndroid Build Coastguard Worker filesystem := newFs() 1365*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/dir/hi.txt", filesystem) 1366*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/dir/ignoreme.txt", filesystem) 1367*333d2b36SAndroid Build Coastguard Worker 1368*333d2b36SAndroid Build Coastguard Worker fs.Link(t, "/tmp/links/dir", "../dir", filesystem) 1369*333d2b36SAndroid Build Coastguard Worker fs.Link(t, "/tmp/links/link", "../dir", filesystem) 1370*333d2b36SAndroid Build Coastguard Worker fs.Link(t, "/tmp/links/hi.txt", "../dir", filesystem) 1371*333d2b36SAndroid Build Coastguard Worker fs.Link(t, "/tmp/links/broken", "nothingHere", filesystem) 1372*333d2b36SAndroid Build Coastguard Worker fs.Link(t, "/tmp/links/recursive", "recursive", filesystem) 1373*333d2b36SAndroid Build Coastguard Worker 1374*333d2b36SAndroid Build Coastguard Worker // set up the finder and run it once 1375*333d2b36SAndroid Build Coastguard Worker finder := newFinder( 1376*333d2b36SAndroid Build Coastguard Worker t, 1377*333d2b36SAndroid Build Coastguard Worker filesystem, 1378*333d2b36SAndroid Build Coastguard Worker CacheParams{ 1379*333d2b36SAndroid Build Coastguard Worker RootDirs: []string{"/tmp"}, 1380*333d2b36SAndroid Build Coastguard Worker IncludeFiles: []string{"hi.txt"}, 1381*333d2b36SAndroid Build Coastguard Worker }, 1382*333d2b36SAndroid Build Coastguard Worker ) 1383*333d2b36SAndroid Build Coastguard Worker 1384*333d2b36SAndroid Build Coastguard Worker foundPaths := finder.FindNamedAt("/tmp", "hi.txt") 1385*333d2b36SAndroid Build Coastguard Worker 1386*333d2b36SAndroid Build Coastguard Worker // should completely ignore symlinks that point to directories 1387*333d2b36SAndroid Build Coastguard Worker correctResponse := []string{ 1388*333d2b36SAndroid Build Coastguard Worker "/tmp/dir/hi.txt", 1389*333d2b36SAndroid Build Coastguard Worker } 1390*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, correctResponse) 1391*333d2b36SAndroid Build Coastguard Worker 1392*333d2b36SAndroid Build Coastguard Worker} 1393*333d2b36SAndroid Build Coastguard Worker 1394*333d2b36SAndroid Build Coastguard Worker// TestAddPruneFile confirms that adding a prune-file (into a directory for which we 1395*333d2b36SAndroid Build Coastguard Worker// already had a cache) causes the directory to be ignored 1396*333d2b36SAndroid Build Coastguard Workerfunc TestAddPruneFile(t *testing.T) { 1397*333d2b36SAndroid Build Coastguard Worker // setup filesystem 1398*333d2b36SAndroid Build Coastguard Worker filesystem := newFs() 1399*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/out/hi.txt", filesystem) 1400*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/out/a/hi.txt", filesystem) 1401*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/hi.txt", filesystem) 1402*333d2b36SAndroid Build Coastguard Worker 1403*333d2b36SAndroid Build Coastguard Worker // do find 1404*333d2b36SAndroid Build Coastguard Worker finder := newFinder( 1405*333d2b36SAndroid Build Coastguard Worker t, 1406*333d2b36SAndroid Build Coastguard Worker filesystem, 1407*333d2b36SAndroid Build Coastguard Worker CacheParams{ 1408*333d2b36SAndroid Build Coastguard Worker RootDirs: []string{"/tmp"}, 1409*333d2b36SAndroid Build Coastguard Worker PruneFiles: []string{".ignore-out-dir"}, 1410*333d2b36SAndroid Build Coastguard Worker IncludeFiles: []string{"hi.txt"}, 1411*333d2b36SAndroid Build Coastguard Worker }, 1412*333d2b36SAndroid Build Coastguard Worker ) 1413*333d2b36SAndroid Build Coastguard Worker 1414*333d2b36SAndroid Build Coastguard Worker foundPaths := finder.FindNamedAt("/tmp", "hi.txt") 1415*333d2b36SAndroid Build Coastguard Worker 1416*333d2b36SAndroid Build Coastguard Worker // check result 1417*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, 1418*333d2b36SAndroid Build Coastguard Worker []string{"/tmp/hi.txt", 1419*333d2b36SAndroid Build Coastguard Worker "/tmp/out/hi.txt", 1420*333d2b36SAndroid Build Coastguard Worker "/tmp/out/a/hi.txt"}, 1421*333d2b36SAndroid Build Coastguard Worker ) 1422*333d2b36SAndroid Build Coastguard Worker finder.Shutdown() 1423*333d2b36SAndroid Build Coastguard Worker 1424*333d2b36SAndroid Build Coastguard Worker // modify filesystem 1425*333d2b36SAndroid Build Coastguard Worker filesystem.Clock.Tick() 1426*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/out/.ignore-out-dir", filesystem) 1427*333d2b36SAndroid Build Coastguard Worker // run another find and check its result 1428*333d2b36SAndroid Build Coastguard Worker finder2 := finderWithSameParams(t, finder) 1429*333d2b36SAndroid Build Coastguard Worker foundPaths = finder2.FindNamedAt("/tmp", "hi.txt") 1430*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, []string{"/tmp/hi.txt"}) 1431*333d2b36SAndroid Build Coastguard Worker finder2.Shutdown() 1432*333d2b36SAndroid Build Coastguard Worker} 1433*333d2b36SAndroid Build Coastguard Worker 1434*333d2b36SAndroid Build Coastguard Workerfunc TestUpdatingDbIffChanged(t *testing.T) { 1435*333d2b36SAndroid Build Coastguard Worker // setup filesystem 1436*333d2b36SAndroid Build Coastguard Worker filesystem := newFs() 1437*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/a/hi.txt", filesystem) 1438*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/b/bye.txt", filesystem) 1439*333d2b36SAndroid Build Coastguard Worker 1440*333d2b36SAndroid Build Coastguard Worker // run the first finder 1441*333d2b36SAndroid Build Coastguard Worker finder := newFinder( 1442*333d2b36SAndroid Build Coastguard Worker t, 1443*333d2b36SAndroid Build Coastguard Worker filesystem, 1444*333d2b36SAndroid Build Coastguard Worker CacheParams{ 1445*333d2b36SAndroid Build Coastguard Worker RootDirs: []string{"/tmp"}, 1446*333d2b36SAndroid Build Coastguard Worker IncludeFiles: []string{"hi.txt"}, 1447*333d2b36SAndroid Build Coastguard Worker }, 1448*333d2b36SAndroid Build Coastguard Worker ) 1449*333d2b36SAndroid Build Coastguard Worker finder.WaitForDbDump() 1450*333d2b36SAndroid Build Coastguard Worker filesystem.Clock.Tick() 1451*333d2b36SAndroid Build Coastguard Worker foundPaths := finder.FindAll() 1452*333d2b36SAndroid Build Coastguard Worker finder.Shutdown() 1453*333d2b36SAndroid Build Coastguard Worker // check results 1454*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, []string{"/tmp/a/hi.txt"}) 1455*333d2b36SAndroid Build Coastguard Worker 1456*333d2b36SAndroid Build Coastguard Worker // modify the filesystem 1457*333d2b36SAndroid Build Coastguard Worker filesystem.Clock.Tick() 1458*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/b/hi.txt", filesystem) 1459*333d2b36SAndroid Build Coastguard Worker filesystem.Clock.Tick() 1460*333d2b36SAndroid Build Coastguard Worker filesystem.ClearMetrics() 1461*333d2b36SAndroid Build Coastguard Worker 1462*333d2b36SAndroid Build Coastguard Worker // run the second finder 1463*333d2b36SAndroid Build Coastguard Worker finder2 := finderWithSameParams(t, finder) 1464*333d2b36SAndroid Build Coastguard Worker foundPaths = finder2.FindAll() 1465*333d2b36SAndroid Build Coastguard Worker finder2.Shutdown() 1466*333d2b36SAndroid Build Coastguard Worker // check results 1467*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, []string{"/tmp/a/hi.txt", "/tmp/b/hi.txt"}) 1468*333d2b36SAndroid Build Coastguard Worker fs.AssertSameReadDirCalls(t, filesystem.ReadDirCalls, []string{"/tmp/b"}) 1469*333d2b36SAndroid Build Coastguard Worker expectedDbWriteTime := filesystem.Clock.Time() 1470*333d2b36SAndroid Build Coastguard Worker actualDbWriteTime := fs.ModTime(t, finder2.DbPath, filesystem) 1471*333d2b36SAndroid Build Coastguard Worker if actualDbWriteTime != expectedDbWriteTime { 1472*333d2b36SAndroid Build Coastguard Worker t.Fatalf("Expected to write db at %v, actually wrote db at %v\n", 1473*333d2b36SAndroid Build Coastguard Worker expectedDbWriteTime, actualDbWriteTime) 1474*333d2b36SAndroid Build Coastguard Worker } 1475*333d2b36SAndroid Build Coastguard Worker 1476*333d2b36SAndroid Build Coastguard Worker // reset metrics 1477*333d2b36SAndroid Build Coastguard Worker filesystem.ClearMetrics() 1478*333d2b36SAndroid Build Coastguard Worker 1479*333d2b36SAndroid Build Coastguard Worker // run the third finder 1480*333d2b36SAndroid Build Coastguard Worker finder3 := finderWithSameParams(t, finder2) 1481*333d2b36SAndroid Build Coastguard Worker foundPaths = finder3.FindAll() 1482*333d2b36SAndroid Build Coastguard Worker 1483*333d2b36SAndroid Build Coastguard Worker // check results 1484*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, []string{"/tmp/a/hi.txt", "/tmp/b/hi.txt"}) 1485*333d2b36SAndroid Build Coastguard Worker fs.AssertSameReadDirCalls(t, filesystem.ReadDirCalls, []string{}) 1486*333d2b36SAndroid Build Coastguard Worker finder3.Shutdown() 1487*333d2b36SAndroid Build Coastguard Worker actualDbWriteTime = fs.ModTime(t, finder3.DbPath, filesystem) 1488*333d2b36SAndroid Build Coastguard Worker if actualDbWriteTime != expectedDbWriteTime { 1489*333d2b36SAndroid Build Coastguard Worker t.Fatalf("Re-wrote db even when contents did not change") 1490*333d2b36SAndroid Build Coastguard Worker } 1491*333d2b36SAndroid Build Coastguard Worker 1492*333d2b36SAndroid Build Coastguard Worker} 1493*333d2b36SAndroid Build Coastguard Worker 1494*333d2b36SAndroid Build Coastguard Workerfunc TestDirectoryNotPermitted(t *testing.T) { 1495*333d2b36SAndroid Build Coastguard Worker // setup filesystem 1496*333d2b36SAndroid Build Coastguard Worker filesystem := newFs() 1497*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/hi.txt", filesystem) 1498*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/a/hi.txt", filesystem) 1499*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/a/a/hi.txt", filesystem) 1500*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/b/hi.txt", filesystem) 1501*333d2b36SAndroid Build Coastguard Worker 1502*333d2b36SAndroid Build Coastguard Worker // run the first finder 1503*333d2b36SAndroid Build Coastguard Worker finder := newFinder( 1504*333d2b36SAndroid Build Coastguard Worker t, 1505*333d2b36SAndroid Build Coastguard Worker filesystem, 1506*333d2b36SAndroid Build Coastguard Worker CacheParams{ 1507*333d2b36SAndroid Build Coastguard Worker RootDirs: []string{"/tmp"}, 1508*333d2b36SAndroid Build Coastguard Worker IncludeFiles: []string{"hi.txt"}, 1509*333d2b36SAndroid Build Coastguard Worker }, 1510*333d2b36SAndroid Build Coastguard Worker ) 1511*333d2b36SAndroid Build Coastguard Worker finder.WaitForDbDump() 1512*333d2b36SAndroid Build Coastguard Worker filesystem.Clock.Tick() 1513*333d2b36SAndroid Build Coastguard Worker foundPaths := finder.FindAll() 1514*333d2b36SAndroid Build Coastguard Worker finder.Shutdown() 1515*333d2b36SAndroid Build Coastguard Worker allPaths := []string{"/tmp/hi.txt", "/tmp/a/hi.txt", "/tmp/a/a/hi.txt", "/tmp/b/hi.txt"} 1516*333d2b36SAndroid Build Coastguard Worker // check results 1517*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, allPaths) 1518*333d2b36SAndroid Build Coastguard Worker 1519*333d2b36SAndroid Build Coastguard Worker // modify the filesystem 1520*333d2b36SAndroid Build Coastguard Worker filesystem.Clock.Tick() 1521*333d2b36SAndroid Build Coastguard Worker 1522*333d2b36SAndroid Build Coastguard Worker fs.SetReadable(t, "/tmp/a", false, filesystem) 1523*333d2b36SAndroid Build Coastguard Worker filesystem.Clock.Tick() 1524*333d2b36SAndroid Build Coastguard Worker 1525*333d2b36SAndroid Build Coastguard Worker // run the second finder 1526*333d2b36SAndroid Build Coastguard Worker finder2 := finderWithSameParams(t, finder) 1527*333d2b36SAndroid Build Coastguard Worker foundPaths = finder2.FindAll() 1528*333d2b36SAndroid Build Coastguard Worker finder2.Shutdown() 1529*333d2b36SAndroid Build Coastguard Worker // check results 1530*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, []string{"/tmp/hi.txt", "/tmp/b/hi.txt"}) 1531*333d2b36SAndroid Build Coastguard Worker 1532*333d2b36SAndroid Build Coastguard Worker // modify the filesystem back 1533*333d2b36SAndroid Build Coastguard Worker fs.SetReadable(t, "/tmp/a", true, filesystem) 1534*333d2b36SAndroid Build Coastguard Worker 1535*333d2b36SAndroid Build Coastguard Worker // run the third finder 1536*333d2b36SAndroid Build Coastguard Worker finder3 := finderWithSameParams(t, finder2) 1537*333d2b36SAndroid Build Coastguard Worker foundPaths = finder3.FindAll() 1538*333d2b36SAndroid Build Coastguard Worker finder3.Shutdown() 1539*333d2b36SAndroid Build Coastguard Worker // check results 1540*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, allPaths) 1541*333d2b36SAndroid Build Coastguard Worker} 1542*333d2b36SAndroid Build Coastguard Worker 1543*333d2b36SAndroid Build Coastguard Workerfunc TestFileNotPermitted(t *testing.T) { 1544*333d2b36SAndroid Build Coastguard Worker // setup filesystem 1545*333d2b36SAndroid Build Coastguard Worker filesystem := newFs() 1546*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/hi.txt", filesystem) 1547*333d2b36SAndroid Build Coastguard Worker fs.SetReadable(t, "/tmp/hi.txt", false, filesystem) 1548*333d2b36SAndroid Build Coastguard Worker 1549*333d2b36SAndroid Build Coastguard Worker // run the first finder 1550*333d2b36SAndroid Build Coastguard Worker finder := newFinder( 1551*333d2b36SAndroid Build Coastguard Worker t, 1552*333d2b36SAndroid Build Coastguard Worker filesystem, 1553*333d2b36SAndroid Build Coastguard Worker CacheParams{ 1554*333d2b36SAndroid Build Coastguard Worker RootDirs: []string{"/tmp"}, 1555*333d2b36SAndroid Build Coastguard Worker IncludeFiles: []string{"hi.txt"}, 1556*333d2b36SAndroid Build Coastguard Worker }, 1557*333d2b36SAndroid Build Coastguard Worker ) 1558*333d2b36SAndroid Build Coastguard Worker finder.WaitForDbDump() 1559*333d2b36SAndroid Build Coastguard Worker filesystem.Clock.Tick() 1560*333d2b36SAndroid Build Coastguard Worker foundPaths := finder.FindAll() 1561*333d2b36SAndroid Build Coastguard Worker finder.Shutdown() 1562*333d2b36SAndroid Build Coastguard Worker // check results 1563*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, []string{"/tmp/hi.txt"}) 1564*333d2b36SAndroid Build Coastguard Worker} 1565*333d2b36SAndroid Build Coastguard Worker 1566*333d2b36SAndroid Build Coastguard Workerfunc TestCacheEntryPathUnexpectedError(t *testing.T) { 1567*333d2b36SAndroid Build Coastguard Worker // setup filesystem 1568*333d2b36SAndroid Build Coastguard Worker filesystem := newFs() 1569*333d2b36SAndroid Build Coastguard Worker fs.Create(t, "/tmp/a/hi.txt", filesystem) 1570*333d2b36SAndroid Build Coastguard Worker 1571*333d2b36SAndroid Build Coastguard Worker // run the first finder 1572*333d2b36SAndroid Build Coastguard Worker finder := newFinder( 1573*333d2b36SAndroid Build Coastguard Worker t, 1574*333d2b36SAndroid Build Coastguard Worker filesystem, 1575*333d2b36SAndroid Build Coastguard Worker CacheParams{ 1576*333d2b36SAndroid Build Coastguard Worker RootDirs: []string{"/tmp"}, 1577*333d2b36SAndroid Build Coastguard Worker IncludeFiles: []string{"hi.txt"}, 1578*333d2b36SAndroid Build Coastguard Worker }, 1579*333d2b36SAndroid Build Coastguard Worker ) 1580*333d2b36SAndroid Build Coastguard Worker finder.WaitForDbDump() 1581*333d2b36SAndroid Build Coastguard Worker filesystem.Clock.Tick() 1582*333d2b36SAndroid Build Coastguard Worker foundPaths := finder.FindAll() 1583*333d2b36SAndroid Build Coastguard Worker finder.Shutdown() 1584*333d2b36SAndroid Build Coastguard Worker // check results 1585*333d2b36SAndroid Build Coastguard Worker fs.AssertSameResponse(t, foundPaths, []string{"/tmp/a/hi.txt"}) 1586*333d2b36SAndroid Build Coastguard Worker 1587*333d2b36SAndroid Build Coastguard Worker // make the directory not readable 1588*333d2b36SAndroid Build Coastguard Worker fs.SetReadErr(t, "/tmp/a", os.ErrInvalid, filesystem) 1589*333d2b36SAndroid Build Coastguard Worker 1590*333d2b36SAndroid Build Coastguard Worker // run the second finder 1591*333d2b36SAndroid Build Coastguard Worker _, err := finderAndErrorWithSameParams(t, finder) 1592*333d2b36SAndroid Build Coastguard Worker if err == nil { 1593*333d2b36SAndroid Build Coastguard Worker t.Fatal("Failed to detect unexpected filesystem error") 1594*333d2b36SAndroid Build Coastguard Worker } 1595*333d2b36SAndroid Build Coastguard Worker} 1596