最近研究了一下glog,上网查如何安装日期生成日志的时候发现的问题
我的需求是每天只生成一个日期为名字的log,到下一天自动增加新的日志
上代码
LogFileObject::LogFileObject(LogSeverity severity,
const char* base_filename)
:base_filename_selected_(base_filename != NULL),
base_filename_((base_filename != NULL) ? base_filename : ""),
源代码里如果base_filename==""的话,
base_filename_selected_=true,
base_filename_="";
这样是不对的
改为以下
LogFileObject::LogFileObject(LogSeverity severity,
const char* base_filename)
:base_filename_((base_filename != NULL) ? base_filename : ""),
base_filename_selected_(!base_filename_.empty()),
这样哪怕base_filename=="",也不会改变逻辑
base_filename_selected_=false,
base_filename_="";
下边是改的代码,每天自动按天生成日志,超过大小日期后边加(NUM),
比如20180808.log如果满了,自动生成20180808(2),以此类推,如果是存在的也会继续在里边写,不会超过额定大小.
配合生成log每天生成日志的代码open的flag增加_O_APPEND
bool LogFileObject::CreateLogfile(const string& time_pid_string) {
string string_filename = base_filename_+filename_extension_+
time_pid_string;
const char* filename = string_filename.c_str();
int fd = open(filename, O_WRONLY | O_CREAT | _O_APPEND, 0664);
if (fd == -1) return false;
在utilities.cc里增加以下函数
//查看日期是否改动
static int32 g_main_day = 0;
bool DayHasChanged(time_t ×tamp) {
time_t raw_time;
time(&raw_time);
struct tm* tm_info;
tm_info = localtime(&raw_time);
if (tm_info->tm_mday == g_main_day){
return false;
}
g_main_day = tm_info->tm_mday;
timestamp = raw_time;
return true;
}
void LogFileObject::Write函数里改成这样
static int32 g_logTooBigAddName = 1;
void LogFileObject::Write(bool force_flush,
time_t timestamp,
const char* message,
int message_len) {
MutexLock l(&lock_);// We don't log if the base_name_ is "" (which means "don't write")
if (base_filename_selected_ && base_filename_.empty()) {
return;
}bool logTooBig = false;
bool logChangeDay = false;
if ( (logChangeDay = DayHasChanged(timestamp) )||
(logTooBig = (static_cast<int>(file_length_ >> 20) >= MaxLogSize() ) )/* ||
PidHasChanged()*/ ) {
if (logTooBig)
{
g_logTooBigAddName++;
}
if (logChangeDay)
{
g_logTooBigAddName = 1;
}
if (file_ != NULL) fclose(file_);
file_ = NULL;
file_length_ = bytes_since_flush_ = 0;
rollover_attempt_ = kRolloverAttemptFrequency-1;
}
// If there's no destination file, make one before outputting
if (file_ == NULL) {
// Try to rollover the log file every 32 log messages. The only time
// this could matter would be when we have trouble creating the log
// file. If that happens, we'll lose lots of log messages, of course!
if (++rollover_attempt_ != kRolloverAttemptFrequency) return;
rollover_attempt_ = 0;struct ::tm tm_time;
localtime_r(×tamp, &tm_time);// The logfile's filename will have the date/time & pid in it
ostringstream time_pid_stream;
time_pid_stream.fill('0');
/*
time_pid_stream << 1900+tm_time.tm_year
<< setw(2) << 1+tm_time.tm_mon
<< setw(2) << tm_time.tm_mday
<< '-'
<< setw(2) << tm_time.tm_hour
<< setw(2) << tm_time.tm_min
<< setw(2) << tm_time.tm_sec
<< '.'
<< GetMainThreadPid();
*/
time_pid_stream << 1900+tm_time.tm_year
<< setw(2) << 1+tm_time.tm_mon
<< setw(2) << tm_time.tm_mday
;
while (true)
{
char szAddName[16] = ".log";
if (g_logTooBigAddName != 1)
{
sprintf(szAddName,"(%d).log",g_logTooBigAddName);
}
string strfilename = base_filename_+filename_extension_+
time_pid_stream.str()+string(szAddName);
struct stat statbuf;
statbuf.st_size = 0;
stat(strfilename.c_str(),&statbuf);
if ( statbuf.st_size < MaxLogSize()*1024*1024 )
{
file_length_ += statbuf.st_size;
bytes_since_flush_ += statbuf.st_size;
break;
}
g_logTooBigAddName++;
}if (g_logTooBigAddName != 1)
{
time_pid_stream << '(' << g_logTooBigAddName << ')';
}