From: Chris Howey Date: Sat, 28 Apr 2012 15:51:46 +0000 (-0500) Subject: BSD - Added fake symlink test X-Git-Tag: v1.7.2~433 X-Git-Url: https://go.fuhry.dev/?a=commitdiff_plain;h=7729ff885a35b9224ca35864317fbdf1d3024d24;p=fsnotify.git BSD - Added fake symlink test --- diff --git a/README b/README index 57128bf..afe1e82 100644 --- a/README +++ b/README @@ -7,14 +7,12 @@ BSD OSX Example: +// Note that it is possible for Watch() to send errors over the Error channel. watcher, err := fsnotify.NewWatcher() if err != nil { log.Fatal(err) } - err = watcher.Watch("/tmp") - if err != nil { - log.Fatal(err) - } + for { select { case ev := <-watcher.Event: @@ -24,6 +22,11 @@ Example: } } + err = watcher.Watch("/tmp") + if err != nil { + log.Fatal(err) + } + Notifications: IsCreate() IsDelete() diff --git a/example_test.go b/example_test.go index 74dd759..95ba62a 100644 --- a/example_test.go +++ b/example_test.go @@ -10,10 +10,7 @@ func ExampleNewWatcher() { if err != nil { log.Fatal(err) } - err = watcher.Watch("/tmp") - if err != nil { - log.Fatal(err) - } + for { select { case ev := <-watcher.Event: @@ -22,4 +19,9 @@ func ExampleNewWatcher() { log.Println("error:", err) } } + + err = watcher.Watch("/tmp") + if err != nil { + log.Fatal(err) + } } diff --git a/fsnotify_bsd.go b/fsnotify_bsd.go index 320323c..e06dfc1 100644 --- a/fsnotify_bsd.go +++ b/fsnotify_bsd.go @@ -98,6 +98,24 @@ func (w *Watcher) addWatch(path string, flags uint32) error { watchfd, found := w.watches[path] if !found { + fi, errstat := os.Lstat(path) + if errstat != nil { + return errstat + } + + // Follow Symlinks + for fi.Mode()&os.ModeSymlink == os.ModeSymlink { + path, errstat = os.Readlink(path) + if errstat != nil { + return errstat + } + + fi, errstat = os.Lstat(path) + if errstat != nil { + return errstat + } + } + fd, errno := syscall.Open(path, syscall.O_NONBLOCK|syscall.O_RDONLY, 0700) if fd == -1 { return errno @@ -107,7 +125,6 @@ func (w *Watcher) addWatch(path string, flags uint32) error { w.watches[path] = watchfd w.paths[watchfd] = path - fi, _ := os.Stat(path) w.finfo[watchfd] = fi if fi.IsDir() { w.watchDirectoryFiles(path) diff --git a/fsnotify_test.go b/fsnotify_test.go index 3561599..55220ba 100644 --- a/fsnotify_test.go +++ b/fsnotify_test.go @@ -217,6 +217,51 @@ func TestFsnotifyRename(t *testing.T) { os.Remove(testFileRenamed) } +func TestFsnotifyFakeSymlink(t *testing.T) { + // Create an fsnotify watcher instance and initialize it + watcher, err := NewWatcher() + if err != nil { + t.Fatalf("NewWatcher() failed: %s", err) + } + + const testDir string = "_test" + + // Create directory to watch + if os.Mkdir(testDir, 0777) != nil { + t.Fatalf("Failed to create test directory: %s", err) + } + defer os.RemoveAll(testDir) + + if os.Symlink("_test/zzz", "_test/zzznew") != nil { + t.Fatalf("Failed to create bogus symlink: %s", err) + } + t.Logf("Created bogus symlink") + + var errorsReceived = 0 + // Receive errors on the error channel on a separate goroutine + go func() { + for errors := range watcher.Error { + t.Logf("Received error: %s", errors) + errorsReceived++ + } + }() + + // Add a watch for testDir + err = watcher.Watch(testDir) + if err != nil { + t.Fatalf("Watcher.Watch() failed: %s", err) + } + + // We expect this event to be received immediately, as they happen during Watch() call + if errorsReceived == 0 { + t.Fatal("fsnotify errors have not been received.") + } + + // Try closing the fsnotify instance + t.Log("calling Close()") + watcher.Close() +} + func TestFsnotifyAttrib(t *testing.T) { // Create an fsnotify watcher instance and initialize it watcher, err := NewWatcher()