github.com/gogf/gf@v1.16.9/os/gfsnotify/gfsnotify_filefunc.go (about) 1 // Copyright GoFrame Author(https://goframe.org). All Rights Reserved. 2 // 3 // ThIs Source Code Form Is subject to the terms of the MIT License. 4 // If a copy of the MIT was not dIstributed with thIs file, 5 // You can obtain one at https://github.com/gogf/gf. 6 7 package gfsnotify 8 9 import ( 10 "fmt" 11 "os" 12 "path/filepath" 13 "sort" 14 "strings" 15 ) 16 17 // fileDir returns all but the last element of path, typically the path's directory. 18 // After dropping the final element, Dir calls Clean on the path and trailing 19 // slashes are removed. 20 // If the path is empty, Dir returns ".". 21 // If the path consists entirely of separators, Dir returns a single separator. 22 // The returned path does not end in a separator unless it is the root directory. 23 func fileDir(path string) string { 24 return filepath.Dir(path) 25 } 26 27 // fileRealPath converts the given `path` to its absolute path 28 // and checks if the file path exists. 29 // If the file does not exist, return an empty string. 30 func fileRealPath(path string) string { 31 p, err := filepath.Abs(path) 32 if err != nil { 33 return "" 34 } 35 if !fileExists(p) { 36 return "" 37 } 38 return p 39 } 40 41 // fileExists checks whether given `path` exist. 42 func fileExists(path string) bool { 43 if stat, err := os.Stat(path); stat != nil && !os.IsNotExist(err) { 44 return true 45 } 46 return false 47 } 48 49 // fileIsDir checks whether given `path` a directory. 50 func fileIsDir(path string) bool { 51 s, err := os.Stat(path) 52 if err != nil { 53 return false 54 } 55 return s.IsDir() 56 } 57 58 // fileAllDirs returns all sub-folders including itself of given `path` recursively. 59 func fileAllDirs(path string) (list []string) { 60 list = []string{path} 61 file, err := os.Open(path) 62 if err != nil { 63 return list 64 } 65 defer file.Close() 66 names, err := file.Readdirnames(-1) 67 if err != nil { 68 return list 69 } 70 for _, name := range names { 71 path := fmt.Sprintf("%s%s%s", path, string(filepath.Separator), name) 72 if fileIsDir(path) { 73 if array := fileAllDirs(path); len(array) > 0 { 74 list = append(list, array...) 75 } 76 } 77 } 78 return 79 } 80 81 // fileScanDir returns all sub-files with absolute paths of given `path`, 82 // It scans directory recursively if given parameter `recursive` is true. 83 func fileScanDir(path string, pattern string, recursive ...bool) ([]string, error) { 84 list, err := doFileScanDir(path, pattern, recursive...) 85 if err != nil { 86 return nil, err 87 } 88 if len(list) > 0 { 89 sort.Strings(list) 90 } 91 return list, nil 92 } 93 94 // doFileScanDir is an internal method which scans directory 95 // and returns the absolute path list of files that are not sorted. 96 // 97 // The pattern parameter `pattern` supports multiple file name patterns, 98 // using the ',' symbol to separate multiple patterns. 99 // 100 // It scans directory recursively if given parameter `recursive` is true. 101 func doFileScanDir(path string, pattern string, recursive ...bool) ([]string, error) { 102 list := ([]string)(nil) 103 file, err := os.Open(path) 104 if err != nil { 105 return nil, err 106 } 107 defer file.Close() 108 names, err := file.Readdirnames(-1) 109 if err != nil { 110 return nil, err 111 } 112 filePath := "" 113 for _, name := range names { 114 filePath = fmt.Sprintf("%s%s%s", path, string(filepath.Separator), name) 115 if fileIsDir(filePath) && len(recursive) > 0 && recursive[0] { 116 array, _ := doFileScanDir(filePath, pattern, true) 117 if len(array) > 0 { 118 list = append(list, array...) 119 } 120 } 121 for _, p := range strings.Split(pattern, ",") { 122 if match, err := filepath.Match(strings.TrimSpace(p), name); err == nil && match { 123 list = append(list, filePath) 124 } 125 } 126 } 127 return list, nil 128 }