package filepath
import (
"os"
"sort"
"strings"
)
func Glob(pattern string) (matches []string, err error) {
if !hasMeta(pattern) {
if _, err = os.Lstat(pattern); err != nil {
return nil, nil
}
return []string{pattern}, nil
}
dir, file := Split(pattern)
dir = cleanGlobPath(dir)
if !hasMeta(dir) {
return glob(dir, file, nil)
}
var m []string
m, err = Glob(dir)
if err != nil {
return
}
for _, d := range m {
matches, err = glob(d, file, matches)
if err != nil {
return
}
}
return
}
func cleanGlobPath(path string) string {
switch path {
case "":
return "."
case string(os.PathSeparator):
return path
default:
return path[:len(path)-1]
}
}
func glob(dir, pattern string, matches []string) ([]string, error) {
fi, err := os.Stat(dir)
if err != nil {
return matches, nil
}
if !fi.IsDir() {
return matches, nil
}
d, err := os.Open(dir)
if err != nil {
return matches, nil
}
defer d.Close()
names, _ := d.Readdirnames(-1)
sort.Strings(names)
for _, n := range names {
matched, err := Match(pattern, n)
if err != nil {
return matches, err
}
if matched {
matches = append(matches, Join(dir, n))
}
}
return matches, nil
}
func hasMeta(path string) bool {
magicChars := "*?["
return strings.ContainsAny(path, magicChars)
}
样例源码:github.com/morganxf/ex…