diff --git a/archive.go b/archive.go index ac4139e..29bdc8a 100644 --- a/archive.go +++ b/archive.go @@ -6,8 +6,6 @@ import ( "path/filepath" "time" - "b612.me/staros" - "b612.me/starmap" ) @@ -18,11 +16,12 @@ func init() { } type Archive interface { - ShouldArchiveNow(string, os.FileInfo) bool - NextLogFilePath(string, os.FileInfo) string + ShouldArchiveNow(*StarLogger, string, os.FileInfo) bool + NextLogFilePath(*StarLogger, string, os.FileInfo) string + ArchiveLogFilePath(*StarLogger, string, os.FileInfo) string Interval() int64 - HookBeforArchive() func(string, os.FileInfo) error - HookAfterArchive() func(string, string, os.FileInfo) error + HookBeforArchive() func(*StarLogger, string, string, os.FileInfo) error //archivePath;currentPath + HookAfterArchive() func(*StarLogger, string, string, os.FileInfo) error //archivePath;currentPath } type logfileinfo struct { @@ -41,7 +40,7 @@ func SetLogFile(path string, logger *StarLogger, appendMode bool) error { if err != nil { return err } - if !appendMode && staros.Exists(fullpath) { + if !appendMode && Exists(fullpath) { os.Remove(fullpath) } fp, err := os.OpenFile(fullpath, fileMode, 0644) @@ -119,7 +118,7 @@ func StartArchive(logger *StarLogger, arch Archive) error { select { case <-stopChan: return - case <-time.After(time.Second * time.Duration(arch.Interval())): + case <-time.After(time.Millisecond * time.Duration(1000*arch.Interval())): } fileinfo, err := GetLogFileInfo(logger) if err != nil { @@ -131,21 +130,30 @@ func StartArchive(logger *StarLogger, arch Archive) error { continue } fullpath := archMap.MustGet(logger.logcore.id).(logfileinfo).fullpath - if !arch.ShouldArchiveNow(fullpath, fileinfo) { + if !arch.ShouldArchiveNow(logger, fullpath, fileinfo) { continue } - newLogPath := arch.NextLogFilePath(fullpath, fileinfo) + newLogPath := arch.NextLogFilePath(logger, fullpath, fileinfo) + archiveLogPath := arch.ArchiveLogFilePath(logger, fullpath, fileinfo) if arch.HookBeforArchive() != nil { - if err := arch.HookBeforArchive()(fullpath, fileinfo); err != nil { + if err := arch.HookBeforArchive()(logger, archiveLogPath, fullpath, fileinfo); err != nil { logger.Errorf("error occur while executing hook before archive,detail is %v\n", err) continue } } + err = CloseWithSwitching(logger) + if err != nil { + continue + } + err = os.Rename(fullpath, archiveLogPath) + if err != nil { + continue + } if err := SetLogFile(newLogPath, logger, false); err != nil { logger.Errorf("error occur while executing coverting new log file,detail is %v\n", err) continue } else { - logger.Debugln("Set Log Success") + logger.Debugln("Archive Log Success") } fileinfo, err = GetLogFileInfo(logger) if err != nil { @@ -153,7 +161,7 @@ func StartArchive(logger *StarLogger, arch Archive) error { continue } if arch.HookAfterArchive() != nil { - if err := arch.HookAfterArchive()(fullpath, newLogPath, fileinfo); err != nil { + if err := arch.HookAfterArchive()(logger, archiveLogPath, newLogPath, fileinfo); err != nil { logger.Errorf("error occur while executing hook after archive,detail is %v\n", err) continue } @@ -178,23 +186,47 @@ func StopArchive(logger *StarLogger) { } type ArchiveByDate struct { - interval int64 - checkInterval int64 - newFileNameStyle string - hookBefor func(string, os.FileInfo) error - hookAfter func(string, string, os.FileInfo) error + interval int64 + checkInterval int64 + baseFileStyle string + archiveStyle string + lastSwitchTime time.Time + changeArchiveName bool + hookBefore func(*StarLogger, string, string, os.FileInfo) error + hookAfter func(*StarLogger, string, string, os.FileInfo) error } -func (abd *ArchiveByDate) ShouldArchiveNow(fullpath string, info os.FileInfo) bool { - if time.Now().Unix()-staros.GetFileCreationTime(info).Unix() > abd.interval { +func (abd *ArchiveByDate) ShouldArchiveNow(l *StarLogger, fullpath string, info os.FileInfo) bool { + if abd.lastSwitchTime.IsZero() { + abd.lastSwitchTime = GetFileCreationTime(info) + } + sub := time.Now().Unix() - abd.lastSwitchTime.Unix() + if sub >= abd.interval || abd.interval-sub <= abd.checkInterval/2 { return true } + return false } -func (abd *ArchiveByDate) NextLogFilePath(oldpath string, info os.FileInfo) string { +func (abd *ArchiveByDate) NextLogFilePath(l *StarLogger, oldpath string, info os.FileInfo) string { + var newName string dir := filepath.Dir(oldpath) - newName := time.Now().Format(abd.newFileNameStyle) + if !abd.changeArchiveName { + newName = abd.baseFileStyle + time.Now().Format(abd.archiveStyle) + } else { + newName = abd.baseFileStyle + } + return filepath.Join(dir, newName) +} + +func (abd *ArchiveByDate) ArchiveLogFilePath(l *StarLogger, oldpath string, info os.FileInfo) string { + var newName string + dir := filepath.Dir(oldpath) + if abd.changeArchiveName { + newName = filepath.Base(abd.baseFileStyle) + time.Now().Format(abd.archiveStyle) + } else { + newName = abd.baseFileStyle + } return filepath.Join(dir, newName) } @@ -202,52 +234,77 @@ func (abd *ArchiveByDate) Interval() int64 { return abd.checkInterval } -func (abd *ArchiveByDate) HookBeforArchive() func(string, os.FileInfo) error { +func (abd *ArchiveByDate) HookBeforArchive() func(*StarLogger, string, string, os.FileInfo) error { - return abd.hookBefor + return abd.hookBefore } -func (abd *ArchiveByDate) HookAfterArchive() func(string, string, os.FileInfo) error { - return abd.hookAfter +func (abd *ArchiveByDate) HookAfterArchive() func(*StarLogger, string, string, os.FileInfo) error { + return func(logger *StarLogger, s string, s2 string, info os.FileInfo) error { + abd.lastSwitchTime = time.Now() + if abd.hookAfter != nil { + return abd.hookAfter(logger, s, s2, info) + } + return nil + } } -func (abd *ArchiveByDate) SetHookBeforArchive(f func(string, os.FileInfo) error) { - - abd.hookBefor = f +func (abd *ArchiveByDate) SetHookBeforArchive(f func(*StarLogger, string, string, os.FileInfo) error) { + abd.hookBefore = f } -func (abd *ArchiveByDate) SetHookAfterArchive(f func(string, string, os.FileInfo) error) { +func (abd *ArchiveByDate) SetHookAfterArchive(f func(*StarLogger, string, string, os.FileInfo) error) { abd.hookAfter = f } -func NewArchiveByDate(archInterval int64, checkInterval int64, fileStyle string, hookbefor func(string, os.FileInfo) error, hookafter func(string, string, os.FileInfo) error) *ArchiveByDate { +func NewArchiveByDate(archInterval int64, checkInterval int64, baseFileName string, archiveFileName string, changeArchiveName bool, hookbefore func(*StarLogger, string, string, os.FileInfo) error, hookafter func(*StarLogger, string, string, os.FileInfo) error) *ArchiveByDate { return &ArchiveByDate{ - interval: archInterval, - checkInterval: checkInterval, - newFileNameStyle: fileStyle, - hookBefor: hookbefor, - hookAfter: hookafter, + interval: archInterval, + checkInterval: checkInterval, + changeArchiveName: changeArchiveName, + baseFileStyle: baseFileName, + archiveStyle: archiveFileName, + hookBefore: hookbefore, + hookAfter: hookafter, } } type ArchiveBySize struct { - size int64 - checkInterval int64 - newFileNameStyle string - hookBefor func(string, os.FileInfo) error - hookAfter func(string, string, os.FileInfo) error + size int64 + checkInterval int64 + changeArchiveName bool + baseFileStyle string + archiveStyle string + hookBefore func(*StarLogger, string, string, os.FileInfo) error + hookAfter func(*StarLogger, string, string, os.FileInfo) error } -func (abd *ArchiveBySize) ShouldArchiveNow(fullpath string, info os.FileInfo) bool { +func (abd *ArchiveBySize) ShouldArchiveNow(l *StarLogger, fullpath string, info os.FileInfo) bool { if info.Size() > abd.size { return true } return false } -func (abd *ArchiveBySize) NextLogFilePath(oldpath string, info os.FileInfo) string { +func (abd *ArchiveBySize) NextLogFilePath(l *StarLogger, oldpath string, info os.FileInfo) string { + var newName string + dir := filepath.Dir(oldpath) + if !abd.changeArchiveName { + newName = abd.baseFileStyle + time.Now().Format(abd.archiveStyle) + } else { + newName = abd.baseFileStyle + } + return filepath.Join(dir, newName) +} + +func (abd *ArchiveBySize) ArchiveLogFilePath(l *StarLogger, oldpath string, info os.FileInfo) string { + var newName string dir := filepath.Dir(oldpath) - newName := time.Now().Format(abd.newFileNameStyle) + if abd.changeArchiveName { + newName = filepath.Base(abd.baseFileStyle) + time.Now().Format(abd.archiveStyle) + } else { + newName = abd.baseFileStyle + } return filepath.Join(dir, newName) } @@ -255,30 +312,117 @@ func (abd *ArchiveBySize) Interval() int64 { return abd.checkInterval } -func (abd *ArchiveBySize) HookBeforArchive() func(string, os.FileInfo) error { - - return abd.hookBefor +func (abd *ArchiveBySize) HookBeforArchive() func(*StarLogger, string, string, os.FileInfo) error { + return abd.hookBefore } -func (abd *ArchiveBySize) HookAfterArchive() func(string, string, os.FileInfo) error { +func (abd *ArchiveBySize) HookAfterArchive() func(*StarLogger, string, string, os.FileInfo) error { return abd.hookAfter } -func (abd *ArchiveBySize) SetHookBeforArchive(f func(string, os.FileInfo) error) { - - abd.hookBefor = f +func (abd *ArchiveBySize) SetHookBeforArchive(f func(*StarLogger, string, string, os.FileInfo) error) { + abd.hookBefore = f } -func (abd *ArchiveBySize) SetHookAfterArchive(f func(string, string, os.FileInfo) error) { +func (abd *ArchiveBySize) SetHookAfterArchive(f func(*StarLogger, string, string, os.FileInfo) error) { abd.hookAfter = f } -func NewArchiveBySize(size int64, checkInterval int64, fileStyle string, hookbefor func(string, os.FileInfo) error, hookafter func(string, string, os.FileInfo) error) *ArchiveBySize { +func NewArchiveBySize(size int64, checkInterval int64, baseFileStyle, archiveFileStyle string, changeArchiveFileName bool, hookbefore func(*StarLogger, string, string, os.FileInfo) error, hookafter func(*StarLogger, string, string, os.FileInfo) error) *ArchiveBySize { return &ArchiveBySize{ - size: size, - checkInterval: checkInterval, - newFileNameStyle: fileStyle, - hookBefor: hookbefor, - hookAfter: hookafter, + size: size, + checkInterval: checkInterval, + baseFileStyle: baseFileStyle, + archiveStyle: archiveFileStyle, + hookBefore: hookbefore, + hookAfter: hookafter, + changeArchiveName: changeArchiveFileName, + } +} + +type ArchiveByDateSize struct { + interval int64 + size int64 + checkInterval int64 + changeArchiveName bool + lastSwitchTime time.Time + baseFileStyle string + archiveStyle string + hookBefore func(*StarLogger, string, string, os.FileInfo) error + hookAfter func(*StarLogger, string, string, os.FileInfo) error +} + +func (abd *ArchiveByDateSize) ShouldArchiveNow(l *StarLogger, fullpath string, info os.FileInfo) bool { + if abd.lastSwitchTime.IsZero() { + abd.lastSwitchTime = GetFileCreationTime(info) + } + if info.Size() > abd.size { + return true + } + sub := time.Now().Unix() - abd.lastSwitchTime.Unix() + if sub >= abd.interval || abd.interval-sub <= abd.checkInterval/2 { + return true + } + return false +} + +func (abd *ArchiveByDateSize) NextLogFilePath(l *StarLogger, oldpath string, info os.FileInfo) string { + var newName string + dir := filepath.Dir(oldpath) + if !abd.changeArchiveName { + newName = abd.baseFileStyle + time.Now().Format(abd.archiveStyle) + } else { + newName = abd.baseFileStyle + } + return filepath.Join(dir, newName) +} + +func (abd *ArchiveByDateSize) ArchiveLogFilePath(l *StarLogger, oldpath string, info os.FileInfo) string { + var newName string + dir := filepath.Dir(oldpath) + if abd.changeArchiveName { + newName = filepath.Base(abd.baseFileStyle) + time.Now().Format(abd.archiveStyle) + } else { + newName = abd.baseFileStyle + } + return filepath.Join(dir, newName) +} + +func (abd *ArchiveByDateSize) Interval() int64 { + return abd.checkInterval +} + +func (abd *ArchiveByDateSize) HookBeforArchive() func(*StarLogger, string, string, os.FileInfo) error { + return abd.hookBefore +} + +func (abd *ArchiveByDateSize) HookAfterArchive() func(*StarLogger, string, string, os.FileInfo) error { + return func(logger *StarLogger, s string, s2 string, info os.FileInfo) error { + abd.lastSwitchTime = time.Now() + if abd.hookAfter != nil { + return abd.hookAfter(logger, s, s2, info) + } + return nil + } +} + +func (abd *ArchiveByDateSize) SetHookBeforArchive(f func(*StarLogger, string, string, os.FileInfo) error) { + abd.hookBefore = f +} + +func (abd *ArchiveByDateSize) SetHookAfterArchive(f func(*StarLogger, string, string, os.FileInfo) error) { + abd.hookAfter = f +} + +func NewArchiveByDateSize(size int64, interval int64, checkInterval int64, baseFileStyle, archiveFileStyle string, changeArchiveFileName bool, hookbefore func(*StarLogger, string, string, os.FileInfo) error, hookafter func(*StarLogger, string, string, os.FileInfo) error) *ArchiveByDateSize { + return &ArchiveByDateSize{ + size: size, + interval: interval, + checkInterval: checkInterval, + baseFileStyle: baseFileStyle, + archiveStyle: archiveFileStyle, + hookBefore: hookbefore, + hookAfter: hookafter, + changeArchiveName: changeArchiveFileName, } } diff --git a/archive_test.go b/archive_test.go index 77a7a39..e6d59f5 100644 --- a/archive_test.go +++ b/archive_test.go @@ -1 +1,17 @@ package starlog + +import ( + "testing" + "time" +) + +func TestArchiveByDate(t *testing.T) { + l := Std + SetLogFile("test.log", l, true) + StartArchive(l, NewArchiveByDateSize(4096, 24, 2, "test.log", + "_2006_01_02_15_04_05.log", true, nil, nil)) + for { + time.Sleep(time.Second) + l.Infoln("hahaha", time.Now()) + } +} diff --git a/files.go b/files.go index ba0b51b..3d449d0 100644 --- a/files.go +++ b/files.go @@ -1,19 +1,9 @@ -package staros +package starlog import ( - "errors" "os" ) -var ERR_ALREADY_LOCKED = errors.New("ALREADY LOCKED") -var ERR_TIMEOUT = errors.New("TIME OUT") - -func NewFileLock(filepath string) FileLock { - return FileLock{ - filepath: filepath, - } -} - // 检测文件/文件夹是否存在 func Exists(path string) bool { _, err := os.Stat(path) @@ -24,7 +14,7 @@ func Exists(path string) bool { } // IsFile 返回给定文件地址是否是一个文件, -//True为是一个文件,False为不是文件或路径无效 +// True为是一个文件,False为不是文件或路径无效 func IsFile(fpath string) bool { s, err := os.Stat(fpath) if err != nil { @@ -34,7 +24,7 @@ func IsFile(fpath string) bool { } // IsFolder 返回给定文件地址是否是一个文件夹, -//True为是一个文件夹,False为不是文件夹或路径无效 +// True为是一个文件夹,False为不是文件夹或路径无效 func IsFolder(fpath string) bool { s, err := os.Stat(fpath) if err != nil { diff --git a/files_darwin.go b/files_darwin.go index 919dcee..362a5a7 100644 --- a/files_darwin.go +++ b/files_darwin.go @@ -1,83 +1,14 @@ -//+build darwin +//go:build darwin +// +build darwin -package staros +package starlog import ( - "b612.me/stario" "os" "syscall" "time" ) -type FileLock struct { - fd int - filepath string -} - -func (f *FileLock) openFileForLock() error { - fd, err := syscall.Open(f.filepath, syscall.O_CREAT|syscall.O_RDONLY, 0600) - if err != nil { - return err - } - f.filepath = f.filepath - f.fd = fd - return nil -} - -func (f *FileLock) Lock(Exclusive bool) error { - var lockType int - if Exclusive { - lockType = syscall.LOCK_EX - } else { - lockType = syscall.LOCK_SH - } - if err := f.openFileForLock(); err != nil { - return err - } - return syscall.Flock(f.fd, lockType) -} - -func (f *FileLock) LockNoBlocking(Exclusive bool) error { - var lockType int - if Exclusive { - lockType = syscall.LOCK_EX - } else { - lockType = syscall.LOCK_SH - } - if err := f.openFileForLock(); err != nil { - return err - } - err := syscall.Flock(f.fd, lockType|syscall.LOCK_NB) - if err != nil { - syscall.Close(f.fd) - if err == syscall.EWOULDBLOCK { - return ERR_ALREADY_LOCKED - } - } - return err -} - -func (f *FileLock) Unlock() error { - err := syscall.Flock(f.fd, syscall.LOCK_UN) - if err != nil { - return err - } - return syscall.Close(f.fd) -} - -func (f *FileLock) LockWithTimeout(tm time.Duration, Exclusive bool) error { - return stario.WaitUntilTimeout(tm, func(tmout chan struct{}) error { - err := f.Lock(Exclusive) - select { - case <-tmout: - f.Unlock() - return nil - default: - } - return err - }) -} - func timespecToTime(ts syscall.Timespec) time.Time { return time.Unix(int64(ts.Sec), int64(ts.Nsec)) } diff --git a/files_unix.go b/files_unix.go index 132abcd..a2d495b 100644 --- a/files_unix.go +++ b/files_unix.go @@ -1,19 +1,14 @@ -//+build linux +//go:build linux +// +build linux -package staros +package starlog import ( - "b612.me/stario" "os" "syscall" "time" ) -type FileLock struct { - fd int - filepath string -} - func timespecToTime(ts syscall.Timespec) time.Time { return time.Unix(int64(ts.Sec), int64(ts.Nsec)) } @@ -25,67 +20,3 @@ func GetFileCreationTime(fileinfo os.FileInfo) time.Time { func GetFileAccessTime(fileinfo os.FileInfo) time.Time { return timespecToTime(fileinfo.Sys().(*syscall.Stat_t).Atim) } - -func (f *FileLock) openFileForLock() error { - fd, err := syscall.Open(f.filepath, syscall.O_CREAT|syscall.O_RDONLY, 0600) - if err != nil { - return err - } - f.filepath = f.filepath - f.fd = fd - return nil -} - -func (f *FileLock) Lock(Exclusive bool) error { - var lockType int - if Exclusive { - lockType = syscall.LOCK_EX - } else { - lockType = syscall.LOCK_SH - } - if err := f.openFileForLock(); err != nil { - return err - } - return syscall.Flock(f.fd, lockType) -} - -func (f *FileLock) LockNoBlocking(Exclusive bool) error { - var lockType int - if Exclusive { - lockType = syscall.LOCK_EX - } else { - lockType = syscall.LOCK_SH - } - if err := f.openFileForLock(); err != nil { - return err - } - err := syscall.Flock(f.fd, lockType|syscall.LOCK_NB) - if err != nil { - syscall.Close(f.fd) - if err == syscall.EWOULDBLOCK { - return ERR_ALREADY_LOCKED - } - } - return err -} - -func (f *FileLock) Unlock() error { - err := syscall.Flock(f.fd, syscall.LOCK_UN) - if err != nil { - return err - } - return syscall.Close(f.fd) -} - -func (f *FileLock) LockWithTimeout(tm time.Duration, Exclusive bool) error { - return stario.WaitUntilTimeout(tm, func(tmout chan struct{}) error { - err := f.Lock(Exclusive) - select { - case <-tmout: - f.Unlock() - return nil - default: - } - return err - }) -} diff --git a/files_windows.go b/files_windows.go index 6ca87d9..5ae4071 100644 --- a/files_windows.go +++ b/files_windows.go @@ -1,19 +1,14 @@ +//go:build windows // +build windows -package staros +package starlog import ( - "b612.me/win32api" "os" "syscall" "time" ) -type FileLock struct { - filepath string - handle win32api.HANDLE -} - func GetFileCreationTime(fileinfo os.FileInfo) time.Time { d := fileinfo.Sys().(*syscall.Win32FileAttributeData) return time.Unix(0, d.CreationTime.Nanoseconds()) @@ -23,101 +18,3 @@ func GetFileAccessTime(fileinfo os.FileInfo) time.Time { d := fileinfo.Sys().(*syscall.Win32FileAttributeData) return time.Unix(0, d.LastAccessTime.Nanoseconds()) } - -func SetFileTimes(file *os.File, info os.FileInfo) { - -} - -func SetFileTimesbyTime(file *os.File) { - -} - -func (f *FileLock) openFileForLock() error { - name, err := syscall.UTF16PtrFromString(f.filepath) - if err != nil { - return err - } - handle, err := syscall.CreateFile( - name, - syscall.GENERIC_READ, - syscall.FILE_SHARE_READ, - nil, - syscall.OPEN_ALWAYS, - syscall.FILE_FLAG_OVERLAPPED|0x00000080, - 0) - if err != nil { - return err - } - f.handle = win32api.HANDLE(handle) - return nil -} - -func (f *FileLock) lockForTimeout(timeout time.Duration, lockType win32api.DWORD) error { - var err error - if err = f.openFileForLock(); err != nil { - return err - } - event, err := win32api.CreateEventW(nil, true, false, nil) - if err != nil { - return err - } - myEvent := &syscall.Overlapped{HEvent: syscall.Handle(event)} - defer syscall.CloseHandle(myEvent.HEvent) - _, err = win32api.LockFileEx(f.handle, lockType, 0, 1, 0, myEvent) - if err == nil { - return nil - } - if err != syscall.ERROR_IO_PENDING { - return err - } - millis := uint32(syscall.INFINITE) - if timeout >= 0 { - millis = uint32(timeout.Nanoseconds() / 1000000) - } - s, err := syscall.WaitForSingleObject(myEvent.HEvent, millis) - switch s { - case syscall.WAIT_OBJECT_0: - // success! - return nil - case syscall.WAIT_TIMEOUT: - f.Unlock() - return ERR_TIMEOUT - default: - f.Unlock() - return err - } -} - -func (f *FileLock) Lock(Exclusive bool) error { - var lockType win32api.DWORD - if Exclusive { - lockType = win32api.LOCKFILE_EXCLUSIVE_LOCK - } else { - lockType = 0 - } - return f.lockForTimeout(0, lockType) -} - -func (f *FileLock) LockWithTimeout(tm time.Duration, Exclusive bool) error { - var lockType win32api.DWORD - if Exclusive { - lockType = win32api.LOCKFILE_EXCLUSIVE_LOCK - } else { - lockType = 0 - } - return f.lockForTimeout(tm, lockType) -} - -func (f *FileLock) LockNoBlocking(Exclusive bool) error { - var lockType win32api.DWORD - if Exclusive { - lockType = win32api.LOCKFILE_EXCLUSIVE_LOCK - } else { - lockType = 0 - } - return f.lockForTimeout(0, lockType|win32api.LOCKFILE_FAIL_IMMEDIATELY) -} - -func (f *FileLock) Unlock() error { - return syscall.Close(syscall.Handle(f.handle)) -} diff --git a/go.mod b/go.mod index a9c224e..9e82564 100644 --- a/go.mod +++ b/go.mod @@ -3,7 +3,6 @@ module b612.me/starlog go 1.16 require ( - b612.me/starmap v1.2.3 - b612.me/staros v1.1.6 - golang.org/x/sys v0.0.0-20220319134239-a9b59b0215f8 + b612.me/starmap v1.2.4 + golang.org/x/sys v0.18.0 ) diff --git a/go.sum b/go.sum index 78d5ef6..80908db 100644 --- a/go.sum +++ b/go.sum @@ -1,32 +1,55 @@ -b612.me/notify v1.2.4 h1:cjP80V9FeM+ib1DztZdykusakcbjNI4dAB1pXE8U6bo= -b612.me/notify v1.2.4/go.mod h1:SlCrG1kPRVhYUrIkwY/j0zAwCU4VeTHubcZoQXW8Anw= -b612.me/starcrypto v0.0.2 h1:aRf1HcqK8GqHYxLAhWfFC4W/EqQLEFNEmxsBu3wG30o= -b612.me/starcrypto v0.0.2/go.mod h1:hz0xRnfWNpYOlVrIPoGrQOWPibq4YiUZ7qN5tsQbzPo= -b612.me/stario v0.0.7/go.mod h1:or4ssWcxQSjMeu+hRKEgtp0X517b3zdlEOAms8Qscvw= -b612.me/stario v0.0.8 h1:kaA4pszAKLZJm2D9JmiuYSpgjTeE3VaO74vm+H0vBGM= -b612.me/stario v0.0.8/go.mod h1:or4ssWcxQSjMeu+hRKEgtp0X517b3zdlEOAms8Qscvw= -b612.me/starmap v1.2.3 h1:+ao++KgbSGMA4UzcHm/EXJoukbUudk8t5ac7rjwV9KA= -b612.me/starmap v1.2.3/go.mod h1:K+exTSWg8i/taoUyGR6DPW6Ja0k6aIdpcniqByOf4O0= -b612.me/starnet v0.1.7 h1:k3CUfYNRolC/xw5Ekus2NVWHlqeykSyAH8USGTPKA5o= -b612.me/starnet v0.1.7/go.mod h1:DNC4i/ezgVLlmxnquf8AeljsL4mQ5vAyxh8vGPQqsys= -b612.me/staros v1.1.6 h1:m3QaEmPyvPcJVomjWs8cDeauDYFNKv7cLHTiOHClKqM= -b612.me/staros v1.1.6/go.mod h1:O657LC3qag4VSsHNmt5RM8gKJvzoEGq8IF8WegcRgq0= -b612.me/win32api v0.0.1 h1:vLFB1xhO6pd9+zB2EyaapKB459Urv3v+C1YwgwOFEWo= -b612.me/win32api v0.0.1/go.mod h1:MHu0JBQjzxQ2yxpZPUBbn5un45o67eF5iWKa4Q9e0yE= -b612.me/wincmd v0.0.2 h1:Ub1WtelVT6a3vD4B6zDYo3UPO/t9ymnI3x1dQPJcrGw= -b612.me/wincmd v0.0.2/go.mod h1:bwpyCKfSDY8scSMo3Lrd0Qnqvpz7/CILL7oodfG0wgo= -golang.org/x/crypto v0.0.0-20220313003712-b769efc7c000/go.mod h1:IxCIyHEi3zRg3s0A5j5BB6A9Jmi73HwBIUl50j+osU4= -golang.org/x/crypto v0.0.0-20220321153916-2c7772ba3064 h1:S25/rfnfsMVgORT4/J61MJ7rdyseOZOyvLIrZEZ7s6s= -golang.org/x/crypto v0.0.0-20220321153916-2c7772ba3064/go.mod h1:IxCIyHEi3zRg3s0A5j5BB6A9Jmi73HwBIUl50j+osU4= -golang.org/x/net v0.0.0-20211112202133-69e39bad7dc2/go.mod h1:9nx3DQGgdP8bBQD5qxJ1jj9UTztislL4KSBs9R2vV5Y= +b612.me/notify v1.2.5 h1:fASpzi8YAo78g6jKnefzfbsQz0nGNYFbClB2Bylj+MA= +b612.me/notify v1.2.5/go.mod h1:GTnAdC6v9krGxtC8Gkn8TcyUsYnHSiHjRAXsONPiLpI= +b612.me/starcrypto v0.0.3 h1:lBGtz0kBdsV198BDQ72zBgOXYKBCb47R9tCWP/PFIwA= +b612.me/starcrypto v0.0.3/go.mod h1:pF5A16p8r/h1G0x7ZNmmAF6K1sdIMpbCUxn2WGC8gZ0= +b612.me/stario v0.0.9 h1:bFDlejUJMwZ12a09snZJspQsOlkqpDAl9qKPEYOGWCk= +b612.me/stario v0.0.9/go.mod h1:x4D/x8zA5SC0pj/uJAi4FyG5p4j5UZoMEZfvuRR6VNw= +b612.me/starmap v1.2.4 h1:gfAyBtzW3KKCIyI14I2pEqGsR/u2E+3tkH0xRqtWb4E= +b612.me/starmap v1.2.4/go.mod h1:EhOUzkItc5IcyBmr1C7/vmZBbW3GgCWs63hGn7WhuMc= +b612.me/starnet v0.1.8 h1:sTNytUFP38i2BFR9nha3lTSLYb7El3tvKpZplYCrhZk= +b612.me/starnet v0.1.8/go.mod h1:k862Kf8DiVWTqdX6PHTFb6NoT+3G3Y74n8NCyNhuP0Y= +github.com/yuin/goldmark v1.4.13/go.mod h1:6yULJ656Px+3vBD8DxQVa3kxgyrAnzto9xy5taEt/CY= +golang.org/x/crypto v0.0.0-20190308221718-c2843e01d9a2/go.mod h1:djNgcEr1/C05ACkg1iLfiJU5Ep61QUkGW8qpdssI0+w= +golang.org/x/crypto v0.0.0-20210921155107-089bfa567519/go.mod h1:GvvjBRRGRdwPK5ydBHafDWAxML/pGHZbMvKqRZ5+Abc= +golang.org/x/crypto v0.19.0/go.mod h1:Iy9bg/ha4yyC70EfRS8jz+B6ybOBKMaSxLj6P6oBDfU= +golang.org/x/crypto v0.21.0 h1:X31++rzVUdKhX5sWmSOFZxx8UW/ldWx55cbf08iNAMA= +golang.org/x/crypto v0.21.0/go.mod h1:0BP7YvVV9gBbVKyeTG0Gyn+gZm94bibOW5BjDEYAOMs= +golang.org/x/mod v0.6.0-dev.0.20220419223038-86c51ed26bb4/go.mod h1:jJ57K6gSWd91VN4djpZkiMVwK6gcyfeH4XE8wZrZaV4= +golang.org/x/mod v0.8.0/go.mod h1:iBbtSCu2XBx23ZKBPSOrRkjjQPZFPuis4dIYUhu/chs= +golang.org/x/net v0.0.0-20190620200207-3b0461eec859/go.mod h1:z5CRVTTTmAJ677TzLLGU+0bjPO0LkuOLi4/5GtJWs/s= +golang.org/x/net v0.0.0-20210226172049-e18ecbb05110/go.mod h1:m0MpNAwzfU5UDzcl9v0D8zg8gWTRqZa9RBIspLL5mdg= +golang.org/x/net v0.0.0-20220722155237-a158d28d115b/go.mod h1:XRhObCWvk6IyKnWLug+ECip1KBveYUHfp+8e9klMJ9c= +golang.org/x/net v0.6.0/go.mod h1:2Tu9+aMcznHK/AK1HMvgo6xiTLG5rD5rZLDS+rp2Bjs= +golang.org/x/net v0.10.0/go.mod h1:0qNGK6F8kojg2nk9dLZ2mShWaEBan6FAoqfSigmmuDg= +golang.org/x/net v0.21.0/go.mod h1:bIjVDfnllIU7BJ2DNgfnXvpSvtn8VRwhlsaeUTyUS44= +golang.org/x/sync v0.0.0-20190423024810-112230192c58/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= +golang.org/x/sync v0.0.0-20220722155255-886fb9371eb4/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= +golang.org/x/sync v0.1.0/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= +golang.org/x/sys v0.0.0-20190215142949-d0b11bdaac8a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= golang.org/x/sys v0.0.0-20201119102817-f84b799fce68/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.0.0-20210423082822-04245dca01da/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.0.0-20210615035016-665e8c7367d1/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= -golang.org/x/sys v0.0.0-20220310020820-b874c991c1a5/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= -golang.org/x/sys v0.0.0-20220319134239-a9b59b0215f8 h1:OH54vjqzRWmbJ62fjuhxy7AxFFgoHN0/DPc/UrL8cAs= -golang.org/x/sys v0.0.0-20220319134239-a9b59b0215f8/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20220520151302-bc2c85ada10a/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.0.0-20220722155257-8c9f86f7a55f/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.5.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.8.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.17.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA= +golang.org/x/sys v0.18.0 h1:DBdB3niSjOA/O0blCZBqDefyWNYveAYMNF1Wum0DYQ4= +golang.org/x/sys v0.18.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA= golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo= -golang.org/x/term v0.0.0-20210927222741-03fcf44c2211 h1:JGgROgKl9N8DuW20oFS5gxc+lE67/N3FcwmBPMe7ArY= golang.org/x/term v0.0.0-20210927222741-03fcf44c2211/go.mod h1:jbD1KX2456YbFQfuXm/mYQcufACuNUgVhRMnK/tPxf8= -golang.org/x/text v0.3.6/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= +golang.org/x/term v0.5.0/go.mod h1:jMB1sMXY+tzblOD4FWmEbocvup2/aLOaQEp7JmGp78k= +golang.org/x/term v0.8.0/go.mod h1:xPskH00ivmX89bAKVGSKKtLOWNx2+17Eiy94tnKShWo= +golang.org/x/term v0.17.0/go.mod h1:lLRBjIVuehSbZlaOtGMbcMncT+aqLLLmKrsjNrUguwk= +golang.org/x/term v0.18.0 h1:FcHjZXDMxI8mM3nwhX9HlKop4C0YQvCVCdwYl2wOtE8= +golang.org/x/term v0.18.0/go.mod h1:ILwASektA3OnRv7amZ1xhE/KTR+u50pbXfZ03+6Nx58= +golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= +golang.org/x/text v0.3.3/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= +golang.org/x/text v0.3.7/go.mod h1:u+2+/6zg+i71rQMx5EYifcz6MCKuco9NR6JIITiCfzQ= +golang.org/x/text v0.7.0/go.mod h1:mrYo+phRRbMaCq/xk9113O4dZlRixOauAjOtrjsXDZ8= +golang.org/x/text v0.9.0/go.mod h1:e1OnstbJyHTd6l/uOt8jFFHp6TRDWZR/bV3emEE/zU8= +golang.org/x/text v0.14.0/go.mod h1:18ZOQIKpY8NJVqYksKHtTdi31H5itFRjB5/qKTNYzSU= golang.org/x/tools v0.0.0-20180917221912-90fa682c2a6e/go.mod h1:n7NCudcB/nEzxVGmLbDWY5pfWTLqBcC2KZ6jyYvM4mQ= +golang.org/x/tools v0.0.0-20191119224855-298f0cb1881e/go.mod h1:b+2E5dAYhXwXZwtnZ6UAqBI28+e2cm9otk0dWdXHAEo= +golang.org/x/tools v0.1.12/go.mod h1:hNGJHUnrk76NpqgfD5Aqm5Crs+Hm0VOH/i9J2+nxYbc= +golang.org/x/tools v0.6.0/go.mod h1:Xwgl3UAJ/d3gWutnCtw505GrjyAbvKui8lOU390QaIU= +golang.org/x/xerrors v0.0.0-20190717185122-a985d3407aa7/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=