github.com/mattn/go-zglob@v0.0.5-0.20230108120541-9c2404f90757/zglob_test.go (about)

     1  package zglob
     2  
     3  import (
     4  	"errors"
     5  	"io/ioutil"
     6  	"os"
     7  	"path"
     8  	"path/filepath"
     9  	"reflect"
    10  	"sort"
    11  	"testing"
    12  )
    13  
    14  func check(got []string, expected []string) bool {
    15  	sort.Strings(got)
    16  	sort.Strings(expected)
    17  	return reflect.DeepEqual(expected, got)
    18  }
    19  
    20  type testZGlob struct {
    21  	pattern  string
    22  	expected []string
    23  	err      error
    24  }
    25  
    26  var testGlobs = []testZGlob{
    27  	{`fo*`, []string{`foo`}, nil},
    28  	{`foo`, []string{`foo`}, nil},
    29  	{`foo/*`, []string{`foo/bar`, `foo/baz`}, nil},
    30  	{`foo/**`, []string{`foo/bar`, `foo/baz`}, nil},
    31  	{`f*o/**`, []string{`foo/bar`, `foo/baz`}, nil},
    32  	{`*oo/**`, []string{`foo/bar`, `foo/baz`, `hoo/bar`}, nil},
    33  	{`*oo/b*`, []string{`foo/bar`, `foo/baz`, `hoo/bar`}, nil},
    34  	{`*oo/bar`, []string{`foo/bar`, `hoo/bar`}, nil},
    35  	{`*oo/*z`, []string{`foo/baz`}, nil},
    36  	{`foo/**/*`, []string{`foo/bar`, `foo/bar/baz`, `foo/bar/baz.txt`, `foo/bar/baz/noo.txt`, `foo/baz`}, nil},
    37  	{`*oo/**/*`, []string{`foo/bar`, `foo/bar/baz`, `foo/bar/baz.txt`, `foo/bar/baz/noo.txt`, `foo/baz`, `hoo/bar`}, nil},
    38  	{`*oo/*.txt`, []string{}, nil},
    39  	{`*oo/*/*.txt`, []string{`foo/bar/baz.txt`}, nil},
    40  	{`*oo/**/*.txt`, []string{`foo/bar/baz.txt`, `foo/bar/baz/noo.txt`}, nil},
    41  	{`doo`, nil, os.ErrNotExist},
    42  	{`./f*`, []string{`foo`}, nil},
    43  	{`**/bar/**/*.txt`, []string{`foo/bar/baz.txt`, `foo/bar/baz/noo.txt`}, nil},
    44  	{`**/bar/**/*.{jpg,png}`, []string{`zzz/bar/baz/joo.png`, `zzz/bar/baz/zoo.jpg`}, nil},
    45  	{`zzz/bar/baz/zoo.{jpg,png}`, []string{`zzz/bar/baz/zoo.jpg`}, nil},
    46  	{`zzz/bar/{baz,z}/zoo.jpg`, []string{`zzz/bar/baz/zoo.jpg`}, nil},
    47  	{`zzz/nar/\{noo,x\}/joo.png`, []string{`zzz/nar/{noo,x}/joo.png`}, nil},
    48  }
    49  
    50  func fatalIf(err error) {
    51  	if err != nil {
    52  		panic(err.Error())
    53  	}
    54  }
    55  
    56  func setup(t *testing.T) string {
    57  	tmpdir, err := ioutil.TempDir("", "zglob")
    58  	if err != nil {
    59  		t.Fatal(err)
    60  	}
    61  
    62  	fatalIf(os.MkdirAll(filepath.Join(tmpdir, "foo/baz"), 0755))
    63  	fatalIf(os.MkdirAll(filepath.Join(tmpdir, "foo/bar"), 0755))
    64  	fatalIf(ioutil.WriteFile(filepath.Join(tmpdir, "foo/bar/baz.txt"), []byte{}, 0644))
    65  	fatalIf(os.MkdirAll(filepath.Join(tmpdir, "foo/bar/baz"), 0755))
    66  	fatalIf(ioutil.WriteFile(filepath.Join(tmpdir, "foo/bar/baz/noo.txt"), []byte{}, 0644))
    67  	fatalIf(os.MkdirAll(filepath.Join(tmpdir, "hoo/bar"), 0755))
    68  	fatalIf(ioutil.WriteFile(filepath.Join(tmpdir, "foo/bar/baz.txt"), []byte{}, 0644))
    69  	fatalIf(os.MkdirAll(filepath.Join(tmpdir, "zzz/bar/baz"), 0755))
    70  	fatalIf(ioutil.WriteFile(filepath.Join(tmpdir, "zzz/bar/baz/zoo.jpg"), []byte{}, 0644))
    71  	fatalIf(ioutil.WriteFile(filepath.Join(tmpdir, "zzz/bar/baz/joo.png"), []byte{}, 0644))
    72  	fatalIf(os.MkdirAll(filepath.Join(tmpdir, "zzz/nar/{noo,x}"), 0755))
    73  	fatalIf(ioutil.WriteFile(filepath.Join(tmpdir, "zzz/nar/{noo,x}/joo.png"), []byte{}, 0644))
    74  
    75  	return tmpdir
    76  }
    77  
    78  func TestGlob(t *testing.T) {
    79  	tmpdir := setup(t)
    80  	defer os.RemoveAll(tmpdir)
    81  
    82  	curdir, err := os.Getwd()
    83  	if err != nil {
    84  		t.Fatal(err)
    85  	}
    86  	err = os.Chdir(tmpdir)
    87  	if err != nil {
    88  		t.Fatal(err)
    89  	}
    90  	defer os.Chdir(curdir)
    91  
    92  	tmpdir = "."
    93  	for _, test := range testGlobs {
    94  		expected := make([]string, len(test.expected))
    95  		for i, e := range test.expected {
    96  			expected[i] = e
    97  		}
    98  		got, err := Glob(test.pattern)
    99  		if err != nil {
   100  			if test.err != err {
   101  				t.Error(err)
   102  			}
   103  			continue
   104  		}
   105  		if !check(expected, got) {
   106  			t.Errorf(`zglob failed: pattern %q(%q): expected %v but got %v`, test.pattern, tmpdir, expected, got)
   107  		}
   108  	}
   109  }
   110  
   111  func TestGlobAbs(t *testing.T) {
   112  	tmpdir := setup(t)
   113  	defer os.RemoveAll(tmpdir)
   114  
   115  	curdir, err := os.Getwd()
   116  	if err != nil {
   117  		t.Fatal(err)
   118  	}
   119  	err = os.Chdir(tmpdir)
   120  	if err != nil {
   121  		t.Fatal(err)
   122  	}
   123  	defer os.Chdir(curdir)
   124  
   125  	for _, test := range testGlobs {
   126  		pattern := toSlash(path.Join(tmpdir, test.pattern))
   127  		expected := make([]string, len(test.expected))
   128  		for i, e := range test.expected {
   129  			expected[i] = filepath.ToSlash(filepath.Join(tmpdir, e))
   130  		}
   131  		got, err := Glob(pattern)
   132  		if err != nil {
   133  			if test.err != err {
   134  				t.Error(err)
   135  			}
   136  			continue
   137  		}
   138  		if !check(expected, got) {
   139  			t.Errorf(`zglob failed: pattern %q(%q): expected %v but got %v`, pattern, tmpdir, expected, got)
   140  		}
   141  	}
   142  }
   143  
   144  func TestMatch(t *testing.T) {
   145  	for _, test := range testGlobs {
   146  		for _, f := range test.expected {
   147  			got, err := Match(test.pattern, f)
   148  			if err != nil {
   149  				t.Error(err)
   150  				continue
   151  			}
   152  			if !got {
   153  				t.Errorf("%q should match with %q", f, test.pattern)
   154  			}
   155  		}
   156  	}
   157  }
   158  
   159  func TestFollowSymlinks(t *testing.T) {
   160  	tmpdir, err := ioutil.TempDir("", "zglob")
   161  	if err != nil {
   162  		t.Fatal(err)
   163  	}
   164  
   165  	os.MkdirAll(filepath.Join(tmpdir, "foo"), 0755)
   166  	ioutil.WriteFile(filepath.Join(tmpdir, "foo/baz.txt"), []byte{}, 0644)
   167  	defer os.RemoveAll(tmpdir)
   168  
   169  	err = os.Symlink(filepath.Join(tmpdir, "foo"), filepath.Join(tmpdir, "bar"))
   170  	if err != nil {
   171  		t.Skip(err.Error())
   172  	}
   173  
   174  	curdir, err := os.Getwd()
   175  	if err != nil {
   176  		t.Fatal(err)
   177  	}
   178  	err = os.Chdir(tmpdir)
   179  	if err != nil {
   180  		t.Fatal(err)
   181  	}
   182  	defer os.Chdir(curdir)
   183  
   184  	got, err := GlobFollowSymlinks("**/*")
   185  	if err != nil {
   186  		t.Fatal(err)
   187  	}
   188  	expected := []string{"foo", "foo/baz.txt", "bar/baz.txt"}
   189  
   190  	if !check(expected, got) {
   191  		t.Errorf(`zglob failed: expected %v but got %v`, expected, got)
   192  	}
   193  }
   194  
   195  func TestGlobError(t *testing.T) {
   196  	tmpdir, err := ioutil.TempDir("", "zglob")
   197  	if err != nil {
   198  		t.Fatal(err)
   199  	}
   200  	defer os.RemoveAll(tmpdir)
   201  
   202  	err = os.MkdirAll(filepath.Join(tmpdir, "foo"), 0222)
   203  	if err != nil {
   204  		t.Fatal(err)
   205  	}
   206  
   207  	curdir, err := os.Getwd()
   208  	if err != nil {
   209  		t.Fatal(err)
   210  	}
   211  	err = os.Chdir(tmpdir)
   212  	if err != nil {
   213  		t.Fatal(err)
   214  	}
   215  	defer os.Chdir(curdir)
   216  
   217  	got, err := Glob("**/*")
   218  	if !errors.Is(err, os.ErrPermission) {
   219  		t.Errorf(`zglob failed: expected %v but got %v`, os.ErrPermission, err)
   220  	}
   221  	if !check(nil, got) {
   222  		t.Errorf(`zglob failed: expected %v but got %v`, nil, got)
   223  	}
   224  }