<commit_before>// Package handler is the handler collection of the logger.
package handler

import (
	"errors"
	"fmt"
	"os"
	"sync"

	"github.com/xgfone/go-tools/file"
	"github.com/xgfone/go-tools/function"
)

// FileMode is the mode to open the log file.
const FileMode = os.O_APPEND | os.O_CREATE | os.O_WRONLY

// FilePerm is the default permission to open the log file.
var FilePerm os.FileMode = 0644

// ErrFileNotOpen is the error to open the log file.
var ErrFileNotOpen = errors.New("The file is not opened")

// SizedRotatingFile is a rotating logging handler based on the size.
type SizedRotatingFile struct {
	sync.Mutex
	w *WriteCloser

	filename    string
	maxSize     int
	backupCount int
	nbytes      int
	buffer      bool
}

// NewSizedRotatingFile returns a new RotatingFile.
func NewSizedRotatingFile(filename string, size, count int) *SizedRotatingFile {
	r := &SizedRotatingFile{
		filename:    filename,
		maxSize:     size,
		backupCount: count,
		buffer:      true,
	}

	if err := r.open(); err != nil {
		panic(err)
	}
	return r
}

// DisableBuffer disables the buffer, which writes the log into the file
// immediately.
func (r *SizedRotatingFile) DisableBuffer() {
	r.buffer = false
}

// Write implements the interface io.Writer.
func (r *SizedRotatingFile) Write(data []byte) (n int, err error) {
	return r.WriteString(string(data))
}

// WriteString writes the string.
func (r *SizedRotatingFile) WriteString(data string) (n int, err error) {
	r.Lock()
	defer r.Unlock()

	if r.w == nil || r.w.Closed() {
		err = ErrFileNotOpen
		return
	}

	if r.nbytes+len(data) > r.maxSize {
		if err = r.doRollover(); err != nil {
			return
		}<commit_msg>fix: add the lock for SizedRotatingFile.DisableBuffer()<commit_after>// Package handler is the handler collection of the logger.
package handler

import (
	"errors"
	"fmt"
	"os"
	"sync"

	"github.com/xgfone/go-tools/file"
	"github.com/xgfone/go-tools/function"
)

// FileMode is the mode to open the log file.
const FileMode = os.O_APPEND | os.O_CREATE | os.O_WRONLY

// FilePerm is the default permission to open the log file.
var FilePerm os.FileMode = 0644

// ErrFileNotOpen is the error to open the log file.
var ErrFileNotOpen = errors.New("The file is not opened")

// SizedRotatingFile is a rotating logging handler based on the size.
type SizedRotatingFile struct {
	sync.Mutex
	w *WriteCloser

	filename    string
	maxSize     int
	backupCount int
	nbytes      int
	buffer      bool
}

// NewSizedRotatingFile returns a new RotatingFile.
func NewSizedRotatingFile(filename string, size, count int) *SizedRotatingFile {
	r := &SizedRotatingFile{
		filename:    filename,
		maxSize:     size,
		backupCount: count,
		buffer:      true,
	}

	if err := r.open(); err != nil {
		panic(err)
	}
	return r
}

// DisableBuffer disables the buffer, which writes the log into the file
// immediately.
func (r *SizedRotatingFile) DisableBuffer() {
	r.Lock()
	r.buffer = false
	r.Unlock()
}

// Write implements the interface io.Writer.
func (r *SizedRotatingFile) Write(data []byte) (n int, err error) {
	return r.WriteString(string(data))
}

// WriteString writes the string.
func (r *SizedRotatingFile) WriteString(data string) (n int, err error) {
	r.Lock()
	defer r.Unlock()

	if r.w == nil || r.w.Closed() {
		err = ErrFileNotOpen
		return
	}

	if r.nbytes+len(data) > r.maxSize {
		if err = r.doRollover(); err != nil {
			return
		}
{'fraction_non_alphanumeric': 0.10674486803519062, 'fraction_numerical': 0.002346041055718475, 'mean_word_length': 3.494071146245059, 'pattern_counts': {'":': 0, '<': 3, '<?xml version=': 0, '>': 5, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '3273972', 'n_tokens_mistral': 1219, 'n_tokens_neox': 1169, 'n_words': 377}