mirror of
https://github.com/duke-git/lancet.git
synced 2026-02-15 02:02:27 +08:00
feat: add support for seeking and read one line at a time from file (#158)
* feat: add support for seeking and read one line at a time from file * feat: add support for calculating folder total size --------- Co-authored-by: Suacrbah <5744580+Suacrbah@user.noreply.gitee.com>
This commit is contained in:
@@ -25,6 +25,61 @@ import (
|
||||
"github.com/duke-git/lancet/v2/validator"
|
||||
)
|
||||
|
||||
// FileReader is a reader supporting offset seeking and reading one
|
||||
// line at a time, this is especially useful for large files
|
||||
type FileReader struct {
|
||||
*bufio.Reader
|
||||
file *os.File
|
||||
offset int64
|
||||
}
|
||||
|
||||
// NewFileReader creates the FileReader struct for reading
|
||||
func NewFileReader(path string) (*FileReader, error) {
|
||||
f, err := os.Open(path)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
return &FileReader{
|
||||
file: f,
|
||||
Reader: bufio.NewReader(f),
|
||||
offset: 0,
|
||||
}, nil
|
||||
}
|
||||
|
||||
// ReadLine reads and returns one line at a time excluding the trailing '\r' and '\n'
|
||||
func (f *FileReader) ReadLine() (string, error) {
|
||||
data, err := f.Reader.ReadBytes('\n')
|
||||
f.offset += int64(len(data))
|
||||
if err == nil || err == io.EOF {
|
||||
for len(data) > 0 && (data[len(data)-1] == '\r' || data[len(data)-1] == '\n') {
|
||||
data = data[:len(data)-1]
|
||||
}
|
||||
return string(data), err
|
||||
}
|
||||
return "", err
|
||||
}
|
||||
|
||||
// Offset returns the current offset of the file
|
||||
func (f *FileReader) Offset() int64 {
|
||||
return f.offset
|
||||
}
|
||||
|
||||
// Seek sets the current offset of the reading
|
||||
func (f *FileReader) Seek(offset int64) error {
|
||||
_, err := f.file.Seek(offset, 0)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
f.Reader = bufio.NewReader(f.file)
|
||||
f.offset = offset
|
||||
return nil
|
||||
}
|
||||
|
||||
// Close takes care of the opened file
|
||||
func (f *FileReader) Close() error {
|
||||
return f.file.Close()
|
||||
}
|
||||
|
||||
// IsExist checks if a file or directory exists.
|
||||
// Play: https://go.dev/play/p/nKKXt8ZQbmh
|
||||
func IsExist(path string) bool {
|
||||
@@ -508,6 +563,25 @@ func FileSize(path string) (int64, error) {
|
||||
return f.Size(), nil
|
||||
}
|
||||
|
||||
// DirSize walks the folder recursively and returns folder size in bytes.
|
||||
func DirSize(path string) (int64, error) {
|
||||
var size int64
|
||||
err := filepath.WalkDir(path, func(_ string, d os.DirEntry, err error) error {
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
if !d.IsDir() {
|
||||
info, err := d.Info()
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
size += info.Size()
|
||||
}
|
||||
return err
|
||||
})
|
||||
return size, err
|
||||
}
|
||||
|
||||
// MTime returns file modified time.
|
||||
// Play: https://go.dev/play/p/s_Tl7lZoAaY
|
||||
func MTime(filepath string) (int64, error) {
|
||||
|
||||
Reference in New Issue
Block a user