diff --git a/TODO.MD b/TODO.MD index 82e852f79..a94dd76e7 100644 --- a/TODO.MD +++ b/TODO.MD @@ -40,9 +40,9 @@ - https://github.com/namreg/godown - https://github.com/Masterminds/sprig 1. gform参考 https://gohouse.github.io/gorose/dist/index.html 进行改进 -1. 模板引擎增加对象的支持(参考https://segmentfault.com/q/1010000016829214); - - +1. 模板引擎增加对对象的支持(参考https://segmentfault.com/q/1010000016829214); +1. 由于系统对inotify实例数量(`fs.inotify.max_user_instances`)以及队列大小(`fs.inotify.max_user_watches`)有限制,需要改进`gfsnotify`; +1. 改进gfpool在文件指针变化时的更新; # DONE diff --git a/g/os/gfile/gfile_contents.go b/g/os/gfile/gfile_contents.go index bca02e2c6..87738a114 100644 --- a/g/os/gfile/gfile_contents.go +++ b/g/os/gfile/gfile_contents.go @@ -7,7 +7,6 @@ package gfile import ( - "gitee.com/johng/gf/g/os/gfpool" "io" "io/ioutil" "os" @@ -35,7 +34,7 @@ func GetBinContents(path string) []byte { } // 写入文件内容 -func putContents(path string, data []byte, flag int, perm os.FileMode) error { +func putContents(path string, data []byte, flag int, perm int) error { // 支持目录递归创建 dir := Dir(path) if !Exists(dir) { @@ -43,8 +42,8 @@ func putContents(path string, data []byte, flag int, perm os.FileMode) error { return err } } - // 创建/打开文件,使用文件指针池,默认60秒 - f, err := gfpool.OpenFile(path, flag, perm, gFILE_POOL_EXPIRE*1000) + // 创建/打开文件 + f, err := OpenWithFlagPerm(path, flag, perm) if err != nil { return err } @@ -103,11 +102,11 @@ func GetNextCharOffset(file *os.File, char byte, start int64) int64 { // 获得文件内容下一个指定字节的位置 func GetNextCharOffsetByPath(path string, char byte, start int64) int64 { - if f, err := gfpool.Open(path, os.O_RDONLY, gDEFAULT_PERM, gFILE_POOL_EXPIRE*1000); err == nil { + if f, err := OpenWithFlagPerm(path, os.O_RDONLY, gDEFAULT_PERM); err == nil { defer f.Close() - return GetNextCharOffset(&f.File, char, start) + return GetNextCharOffset(f, char, start) } else { - // panic(err) + panic(err) } return -1 } @@ -122,11 +121,11 @@ func GetBinContentsTilChar(file *os.File, char byte, start int64) ([]byte, int64 // 获得文件内容直到下一个指定字节的位置(返回值包含该位置字符内容) func GetBinContentsTilCharByPath(path string, char byte, start int64) ([]byte, int64) { - if f, err := gfpool.Open(path, os.O_RDONLY, gDEFAULT_PERM, gFILE_POOL_EXPIRE*1000); err == nil { + if f, err := OpenWithFlagPerm(path, os.O_RDONLY, gDEFAULT_PERM); err == nil { defer f.Close() - return GetBinContentsTilChar(&f.File, char, start) + return GetBinContentsTilChar(f, char, start) } else { - // panic(err) + panic(err) } return nil, -1 } @@ -142,11 +141,11 @@ func GetBinContentsByTwoOffsets(file *os.File, start int64, end int64) []byte { // 获得文件内容中两个offset之间的内容 [start, end) func GetBinContentsByTwoOffsetsByPath(path string, start int64, end int64) []byte { - if f, err := gfpool.Open(path, os.O_RDONLY, gDEFAULT_PERM, gFILE_POOL_EXPIRE*1000); err == nil { + if f, err := OpenWithFlagPerm(path, os.O_RDONLY, gDEFAULT_PERM); err == nil { defer f.Close() - return GetBinContentsByTwoOffsets(&f.File, start, end) + return GetBinContentsByTwoOffsets(f, start, end) } else { - // panic(err) + panic(err) } return nil } \ No newline at end of file diff --git a/g/os/gfpool/gfpool.go b/g/os/gfpool/gfpool.go index 143c902ce..2f1544f2a 100644 --- a/g/os/gfpool/gfpool.go +++ b/g/os/gfpool/gfpool.go @@ -42,24 +42,32 @@ type File struct { var pools = gmap.NewStringInterfaceMap() // 获得文件对象,并自动创建指针池(过期时间单位:毫秒) -func Open(path string, flag int, perm os.FileMode, expire...int) (*File, error) { +func Open(path string, flag int, perm os.FileMode, expire...int) (file *File, err error) { fpExpire := 0 if len(expire) > 0 { fpExpire = expire[0] } pool := pools.GetOrSetFuncLock(fmt.Sprintf("%s&%d&%d&%d", path, flag, expire, perm), func() interface{} { - return New(path, flag, perm, fpExpire) + if p, e := New(path, flag, perm, fpExpire); e == nil { + return p + } else { + err = e + } + return nil }).(*Pool) + if pool == nil { + return nil, err + } return pool.File() } -func OpenFile(path string, flag int, perm os.FileMode, expire...int) (*File, error) { +func OpenFile(path string, flag int, perm os.FileMode, expire...int) (file *File, err error) { return Open(path, flag, perm, expire...) } // 创建一个文件指针池,expire = 0表示不过期,expire < 0表示使用完立即回收,expire > 0表示超时回收,默认值为0不过期 // 过期时间单位:毫秒 -func New(path string, flag int, perm os.FileMode, expire...int) *Pool { +func New(path string, flag int, perm os.FileMode, expire...int) (*Pool, error) { fpExpire := 0 if len(expire) > 0 { fpExpire = expire[0] @@ -74,9 +82,9 @@ func New(path string, flag int, perm os.FileMode, expire...int) *Pool { if watcher, err := fsnotify.NewWatcher(); err == nil { p.watcher = watcher } else { - return nil + return nil, err } - return p + return p, nil } // 创建文件指针池 diff --git a/g/os/glog/glog_logger.go b/g/os/glog/glog_logger.go index fce9a5a18..66e3fce16 100644 --- a/g/os/glog/glog_logger.go +++ b/g/os/glog/glog_logger.go @@ -8,19 +8,18 @@ package glog import ( - "os" - "io" - "time" "fmt" - "strings" - "runtime" - "gitee.com/johng/gf/g/os/gfile" - "gitee.com/johng/gf/g/util/gregex" "gitee.com/johng/gf/g/container/gtype" + "gitee.com/johng/gf/g/os/gfile" "gitee.com/johng/gf/g/os/gmlock" - "gitee.com/johng/gf/g/os/gfpool" - "sync" "gitee.com/johng/gf/g/os/gtime" + "gitee.com/johng/gf/g/util/gregex" + "io" + "os" + "runtime" + "strings" + "sync" + "time" ) type Logger struct { @@ -128,14 +127,14 @@ func (l *Logger) GetWriter() io.Writer { } // 获取默认的文件IO -func (l *Logger) getFilePointer() *gfpool.File { +func (l *Logger) getFilePointer() *os.File { if path := l.path.Val(); path != "" { // 文件名称中使用"{}"包含的内容使用gtime格式化 file, _ := gregex.ReplaceStringFunc(`{.+?}`, l.file.Val(), func(s string) string { return gtime.Now().Format(strings.Trim(s, "{}")) }) fpath := path + gfile.Separator + file - if fp, err := gfpool.Open(fpath, gDEFAULT_FILE_POOL_FLAGS, 0666); err == nil { + if fp, err := gfile.OpenWithFlagPerm(fpath, gDEFAULT_FILE_POOL_FLAGS, 0666); err == nil { return fp } else { fmt.Fprintln(os.Stderr, err) @@ -249,20 +248,20 @@ func (l *Logger) GetBacktrace(skip...int) string { from := 0 // 首先定位业务文件开始位置 for i := 0; i < 10; i++ { - if _, cfile, _, ok := runtime.Caller(i); ok { - if !gregex.IsMatchString("/g/os/glog/glog.+$", cfile) { + if _, file, _, ok := runtime.Caller(i); ok { + if !gregex.IsMatchString("/g/os/glog/glog.+$", file) { from = i break } } } // 从业务文件开始位置根据自定义的skip开始backtrace - goroot := runtime.GOROOT() + goRoot := runtime.GOROOT() for i := from + customSkip + l.btSkip.Val(); i < 10000; i++ { - if _, cfile, cline, ok := runtime.Caller(i); ok && cfile != "" { + if _, file, cline, ok := runtime.Caller(i); ok && file != "" { // 不打印出go源码路径及glog包文件路径,日志打印必须从业务源码文件开始,且从glog包文件开始检索 - if (goroot == "" || !gregex.IsMatchString("^" + goroot, cfile)) && !gregex.IsMatchString(``, cfile) { - backtrace += fmt.Sprintf(`%d. %s:%d%s`, index, cfile, cline, ln) + if (goRoot == "" || !gregex.IsMatchString("^" + goRoot, file)) && !gregex.IsMatchString(``, file) { + backtrace += fmt.Sprintf(`%d. %s:%d%s`, index, file, cline, ln) index++ } } else { diff --git a/geg/other/test.go b/geg/other/test.go index d14d8b912..31222b2fa 100644 --- a/geg/other/test.go +++ b/geg/other/test.go @@ -1,21 +1,17 @@ package main import ( - "html/template" - "log" - "os" + "fmt" + "gitee.com/johng/gf/g/os/gtime" + "gitee.com/johng/gf/third/github.com/fsnotify/fsnotify" ) -type Person string - -func (p Person) Label() string { - return "This is " + string(p) -} - func main() { - tmpl, err := template.New("").Parse(`{{sum 1 2 3}}`) - if err != nil { - log.Fatalf("Parse: %v", err) + if w, err := fsnotify.NewWatcher(); err != nil { + fmt.Println(err) + } else { + fmt.Println(gtime.Now().String()) + w.Add("/tmp/test") } - tmpl.Execute(os.Stdout, nil) + } \ No newline at end of file diff --git a/geg/other/test2.go b/geg/other/test2.go index cc4c3f73b..eac8f2d78 100644 --- a/geg/other/test2.go +++ b/geg/other/test2.go @@ -1,12 +1,11 @@ package main import ( - "fmt" - "gitee.com/johng/gf/g/util/gregex" + "gitee.com/johng/gf/g/container/garray" ) func main() { - s := `[0-9][0-9]/Jan/[0-9][0-9][0-9][0-9]:[0-9][0-9]:[0-9][0-9]:[0-9][0-9] \+[0-9][0-9][0-9][0-9]` - s,_ = gregex.ReplaceString(`[A-Za-z]`, `[A-Za-z]`, s) - fmt.Println(s) + a := garray.NewSortedIntArray(0) + a.Add(1) + a.Remove(0) } \ No newline at end of file