<commit_before>// Copyright 2017 The go-vgo Project Developers. See the COPYRIGHT
// file at the top-level directory of this distribution and at
// https://github.com/go-vgo/gt/blob/master/LICENSE
//
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
// option. This file may not be copied, modified, or distributed
// except according to those terms.

package zlog

import (
	// "errors"
	"fmt"
	"log"
	"os"
	"path/filepath"
	"strings"
	"time"

	"github.com/go-vgo/gt/conf"
	"go.uber.org/zap"
	"go.uber.org/zap/zapcore"
	"gopkg.in/natefinch/lumberjack.v2"
)

// Zlog zlog
type Zlog struct {
	// log.Logger
}

var (
	logger, errLogger *zap.Logger
	sugar, errSugar   *zap.SugaredLogger
	zErr              error
	zlogTime          zapcore.Field = zap.String("time", time.Now().Format("2006-01-02 15:04:05"))
)

type logConfig struct {
	Mode    string
	Path    string
	Name    string
	MaxDays int64 `toml:"max_days"`
	// Srv  Server     `toml:"server"`
}

var config logConfig

// Init log
func Init(tpath string) {
	// if _, err := toml.DecodeFile(tpath, &config); err != nil {
	// 	fmt.Println(err)
	// 	return
	// }
	conf.Init(tpath, &config)
	go conf.NewWatcher(tpath, &config)

	go deleteOldLog()

	if config.Mode == "dev" {
		InitDev()
		zlogTime = zap.Error(nil)
	} else {
		InitLog()
		// InitErrLog()
		go InitErrLog()
	}
}

func deleteOldLog() {
	fileDir, _ := confp()
	var maxDays int64 = 28

	if config.MaxDays != 0 {
		maxDays = config.MaxDays
	}

	filepath.Walk(fileDir, func(path string, info os.FileInfo, err error) (returnErr error) {
		defer func() {
			if r := recover(); r != nil {
				returnErr = fmt.Errorf("Unable to delete old log '%s', error: %+v", path, r)
			}
		}()

		if info.IsDir() && info.ModTime().Unix() < (time.Now().Unix()-60*60*24*maxDays) {

			if strings.HasPrefix(filepath.Base(path), filepath.Base(fileDir)) {
				// if err := os.Remove(path); err != nil {
				if err := os.RemoveAll(path); err != nil {
					returnErr = fmt.Errorf("Failed to remove %s: %v", path, err)
				}
			}
		}
		return returnErr
	})
}

// InitDev init dev mode
func InitDev() {
	// logger, _ = zap.NewProduction()
	logCfg := zap.NewDevelopmentConfig()
	logCfg.Sampling = nil
	logger, zErr = logCfg.Build()
	if zErr != nil {
		log.Fatal("NewDevelopmentConfig ERR:", zErr)
	}

	errLogger = logger

	defer logger.Sync() // flushes buffer, if any
	sugar = logger.Sugar()
	errSugar = sugar
}

func confp() (string, string) {
	// var lpath, name string
	var lpath, name string = "./log", "log"

	if config.Path != "" {
		lpath = config.Path
	}

	if config.Name != "" {
		name = config.Name
	}

	return lpath, name
}

// InitLog init log
func InitLog() {
	lpath, name := confp()

	logTime := time.Now().Format("2006-01-02")
	logPath := lpath + "/" + logTime + "/" + name + ".json"
	ws := zapcore.AddSync(&lumberjack.Logger{
		Filename:   logPath,
		MaxSize:    500, // megabytes
		MaxBackups: 3,
		MaxAge:     28, // days
	})
	core := zapcore.NewCore(
		zapcore.NewJSONEncoder(zap.NewProductionEncoderConfig()),
		ws,
		zap.InfoLevel,
	)
	// logger = zap.New(core).WithOptions(zap.AddCaller())
	logger = zap.New(core).WithOptions(zap.AddStacktrace(zap.InfoLevel))

	defer logger.Sync() // flushes buffer, if any
	sugar = logger.Sugar()
}

// InitErrLog init error log
func InitErrLog() {
	// lumberjack.Logger is already safe for concurrent use, so we don't need to
	// lock it.
	lpath, name := confp()

	logTime := time.Now().Format("2006-01-02")
	logPath := lpath + "/" + logTime + "/" + name + "_err.json"
	ws := zapcore.AddSync(&lumberjack.Logger{
		Filename:   logPath,
		MaxSize:    500, // megabytes
		MaxBackups: 3,
		MaxAge:     28, // days
	})

	highPriority := zap.LevelEnablerFunc(func(lvl zapcore.Level) bool {
		return lvl >= zapcore.ErrorLevel
	})

	core := zapcore.NewCore(
		zapcore.NewJSONEncoder(zap.NewProductionEncoderConfig()),
		ws,
		// zap.ErrorLevel,
		highPriority,
	)
<commit_msg>Update log<commit_after>// Copyright 2017 The go-vgo Project Developers. See the COPYRIGHT
// file at the top-level directory of this distribution and at
// https://github.com/go-vgo/gt/blob/master/LICENSE
//
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
// option. This file may not be copied, modified, or distributed
// except according to those terms.

package zlog

import (
	// "errors"
	"fmt"
	"log"
	"os"
	"path/filepath"
	"strings"
	"time"

	"github.com/go-vgo/gt/conf"
	"go.uber.org/zap"
	"go.uber.org/zap/zapcore"
	"gopkg.in/natefinch/lumberjack.v2"
)

// Zlog zlog
type Zlog struct {
	// log.Logger
}

var (
	logger, errLogger *zap.Logger
	sugar, errSugar   *zap.SugaredLogger
	zErr              error
	zlogTime          zapcore.Field = zap.String("time", time.Now().Format("2006-01-02 15:04:05"))
)

type logConfig struct {
	Mode    string
	Path    string
	Name    string
	MaxDays int64 `toml:"max_days"`
	// Srv  Server     `toml:"server"`
}

var config logConfig

// Init log
func Init(tpath string) {
	// if _, err := toml.DecodeFile(tpath, &config); err != nil {
	// 	fmt.Println(err)
	// 	return
	// }
	conf.Init(tpath, &config)
	go conf.NewWatcher(tpath, &config)

	go deleteOldLog()

	if config.Mode == "dev" {
		InitDev()
		zlogTime = zap.Error(nil)
	} else {
		InitLog()
		// InitErrLog()
		go InitErrLog()
	}
}

func deleteOldLog() {
	fileDir, _ := confp()
	var maxDays int64 = 28

	if config.MaxDays != 0 {
		maxDays = config.MaxDays
	}

	filepath.Walk(fileDir, func(path string, info os.FileInfo, err error) (returnErr error) {
		defer func() {
			if r := recover(); r != nil {
				returnErr = fmt.Errorf("Unable to delete old log '%s', error: %+v", path, r)
			}
		}()

		if info.IsDir() && info.ModTime().Unix() < (time.Now().Unix()-60*60*24*maxDays) {

			if strings.HasPrefix(filepath.Base(path), filepath.Base(fileDir)) {
				// if err := os.Remove(path); err != nil {
				if err := os.RemoveAll(path); err != nil {
					returnErr = fmt.Errorf("Failed to remove %s: %v", path, err)
				}
			}
		}
		return returnErr
	})
}

// InitDev init dev mode
func InitDev() {
	// logger, _ = zap.NewProduction()
	logCfg := zap.NewDevelopmentConfig()
	logCfg.Sampling = nil
	logger, zErr = logCfg.Build()
	if zErr != nil {
		log.Fatal("NewDevelopmentConfig ERR:", zErr)
	}

	errLogger = logger

	defer logger.Sync() // flushes buffer, if any
	sugar = logger.Sugar()
	errSugar = sugar
}

func confp() (string, string) {
	// var lpath, name string
	var lpath, name string = "./log", "log"

	if config.Path != "" {
		lpath = config.Path
	}

	if config.Name != "" {
		name = config.Name
	}

	return lpath, name
}

// InitLog init log
func InitLog() {
	lpath, name := confp()
	maxDays := 28
	if config.MaxDays != 0 {
		maxDays = int(config.MaxDays)
	}

	logTime := time.Now().Format("2006-01-02")
	logPath := lpath + "/" + logTime + "/" + name + ".json"
	ws := zapcore.AddSync(&lumberjack.Logger{
		Filename:   logPath,
		MaxSize:    500, // megabytes
		MaxBackups: 3,
		MaxAge:     maxDays, // days
	})
	core := zapcore.NewCore(
		zapcore.NewJSONEncoder(zap.NewProductionEncoderConfig()),
		ws,
		zap.InfoLevel,
	)
	// logger = zap.New(core).WithOptions(zap.AddCaller())
	logger = zap.New(core).WithOptions(zap.AddStacktrace(zap.InfoLevel))

	defer logger.Sync() // flushes buffer, if any
	sugar = logger.Sugar()
}

// InitErrLog init error log
func InitErrLog() {
	// lumberjack.Logger is already safe for concurrent use, so we don't need to
	// lock it.
	lpath, name := confp()
	maxDays := 28
	if config.MaxDays != 0 {
		maxDays = int(config.MaxDays)
	}

	logTime := time.Now().Format("2006-01-02")
	logPath := lpath + "/" + logTime + "/" + name + "_err.json"
	ws := zapcore.AddSync(&lumberjack.Logger{
		Filename:   logPath,
		MaxSize:    500, // megabytes
		MaxBackups: 3,
		MaxAge:     maxDays, // days
	})

	highPriority := zap.LevelEnablerFunc(func(lvl zapcore.Level) bool {
		return lvl >= zapcore.ErrorLevel
	})

	core := zapcore.NewCore(
		zapcore.NewJSONEncoder(zap.NewProductionEncoderConfig()),
		ws,
		// zap.ErrorLevel,
		highPriority,
	)

{'fraction_non_alphanumeric': 0.15743088253048412, 'fraction_numerical': 0.015694796571290595, 'mean_word_length': 3.1754032258064515, 'pattern_counts': {'":': 0, '<': 9, '<?xml version=': 0, '>': 9, 'https://': 2, 'lorem ipsum': 0, 'www.': 2, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 6, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '5057941', 'n_tokens_mistral': 3348, 'n_tokens_neox': 3101, 'n_words': 739}