一、使用库介绍
fsnotify 是 Go 语言中的一个库,用于监听文件系统的变更事件。它允许程序注册对文件系统事件的兴趣,并在这些事件发生时接收通知。fsnotify 主要用来监控目录下的文件变化,如创建、删除或修改等。
使用 fsnotify
安装 fsnotify 库。可以通过以下命令来安装:
go get -u github.com/fsnotify/fsnotify
二、简单使用
1.建立监听实例,fsnotidy.newWatcher()
2.设置监听目录,watcher.Add("dir")
3.监听事件,常见的事件有CREATE,RENAME ,CHMOD,WRITE
最简单的demo:
点击查看代码
package main
import (
"fmt"
"log"
"github.com/fsnotify/fsnotify"
)
func main() {
//建立实例
watcher, _ := fsnotify.NewWatcher()
//设置监听目录
watcher.Add(".")
defer watcher.Close()
done :=make(chan bool)
//开始监听
go func() {
for {
select{
case event :=<-watcher.Events:
log.Println(event,"op:",event.Op,"name:",event.Name,"Op string():",event.Op.String(),"even.op.has:::",event.Op.Has(event.Op))
case <-watcher.Errors:
fmt.Println("err")
}
}
}()
<-done
}
三、完整功能实现
main.go
点击查看代码
package main
import (
"flag"
"log"
"os"
)
// 日志记录
func init() {
Logfile, err := os.OpenFile("event_watch.log", os.O_CREATE|os.O_APPEND|os.O_WRONLY, 0666)
if err != nil {
log.Println("log file err:", err)
return
}
log.SetOutput(Logfile)
}
func main() {
deafult_path,_ := os.Getwd()
watch_path :=flag.String("dir",deafult_path,"监听的目录,默认为程序所在目录")
flag.Parse()
WatcherStart(*watch_path)
}
watch.go
点击查看代码
package main
import (
"log"
"os"
"path/filepath"
"time"
"github.com/fsnotify/fsnotify"
)
// 启动监听主函数
func WatcherStart(watch_path string) {
//开启一个监听实例
watcher, err := fsnotify.NewWatcher()
if err != nil {
log.Fatal("watcher erro:", err)
}
//添加监听的目录,使用一个函数实现动态监听目录。
AddWatchDir(watcher,watch_path)
//开始监听
for {
select {
case event := <-watcher.Events:
//有事件发生就触发事件处理
EventHandle(event, watcher)
case err_ :=<-watcher.Errors:
log.Println(err_)
}
}
}
// 添加监听目录
func AddWatchDir(watcher *fsnotify.Watcher, dir string) error {
err := watcher.Add(dir)
if err != nil {
log.Fatal("watcher add dir erro:", err)
return err
}
//递归监控子目录,
err = filepath.Walk(dir, func(path string, info os.FileInfo, err error) error {
if err != nil {
return err
}
if info.IsDir() {
log.Printf("监控文件夹: %s\n", path)
err = watcher.Add(path)
if err != nil {
return err
}
}
return nil
})
return err
}
// 监听处理函数,检测文件或目录的上传,移动,删除
func EventHandle(event fsnotify.Event, watcher *fsnotify.Watcher) {
var eventinfo EventInfo
file_path := event.Name //获取事件文件路径
file_name := filepath.Base(file_path) //获取事件文件名
eventTime := time.Now().String()
eventinfo.FileName = file_name
eventinfo.FilePath = file_path
eventinfo.Time = eventTime
if file_name == "event_watch.log"{
return
}
switch {
//创建事件处理,是目录就添加进监听,文件就处理
case event.Op&fsnotify.Create == fsnotify.Create:
file_info, _ := os.Stat(file_path)
if file_info.IsDir() {
log.Println("目录创建")
err := AddWatchDir(watcher, file_path)
if err != nil {
log.Fatal("Event handle watcher add dir erro:", err)
}
} else {
//处理文件添加事件
log.Printf("文件创建:%s\n", file_name)
eventinfo.Event = "Created"
SendEventinfo(eventinfo)
//文件处理
file_creat()
}
// 文件修改事件
case event.Op&fsnotify.Write == fsnotify.Write:
log.Printf("修改文件: %s\n", file_name)
eventinfo.Event = "Write"
SendEventinfo(eventinfo)
// 文件删除事件
case event.Op&fsnotify.Remove == fsnotify.Remove:
log.Printf("删除文件/目录: %s\n", file_name)
eventinfo.Event = "Remove"
SendEventinfo(eventinfo)
// 文件重命名/移动事件
case event.Op&fsnotify.Rename == fsnotify.Rename:
log.Printf("重命名文件: %s\n", file_name)
eventinfo.Event = "Rename"
SendEventinfo(eventinfo)
}
}
event.go
点击查看代码
package main
type EventInfo struct {
FileName string `json:"file_name"`
FilePath string `json:"file_path"`
Event string `json:"event"`
Time string `json:"time"`
}
eventfuncHandel.go
点击查看代码
package main
import "fmt"
//测试函数
func SendEventinfo(eventinfo EventInfo){
fmt.Printf("%v\n",eventinfo)
}
//文件创建处理
func file_creat(){
fmt.Println("这是文件需要处理的函数。例如上传到服务器")
}
//文件修改处理
func file_write(){
}
//文件删除处理
func file_delet(){
}
//文件重命名或移动
func file_rename(){
}