Use C ++ to implement a simple logging system

I. Overview

    This article describes the use of C ++ to implement a simple logging system in windows platform approach. Features of the system log as follows:

1. Support output similar to the c language printf-style, to support variable parameters.

2. Supports output to the screen and the log file.

3. support printing system time.

4. The security thread, each thread can simultaneously write the log.

 

Second, implementation

 

Codes are as follows:

AfMutex.h

#ifndef _OSAPI_MUTEX_H
#define _OSAPI_MUTEX_H

struct AfMutex_Priv;

//互斥锁相关的类
class AfMutex
{
public:
	AfMutex();
	~AfMutex();

	int Lock();
	int TryLock();
	void Unlock();

private:
	int Init(); 

private:
	AfMutex_Priv *m_Priv;

};

 

AfMutex_Win32.cpp

#include "AfMutex.h"

#ifdef _WIN32
#include <windows.h>

struct AfMutex_Priv
{
	HANDLE hMutex;
};

AfMutex::AfMutex()
:m_Priv(NULL)
{
	Init();
}

AfMutex::~AfMutex()
{
	if(m_Priv) 
	{
		CloseHandle(m_Priv->hMutex);
		delete m_Priv;
	}
}

int AfMutex::Init()
{
	m_Priv = new AfMutex_Priv;
	m_Priv->hMutex = CreateMutex(NULL, true, NULL);
	if(m_Priv->hMutex == NULL)
	{
		delete m_Priv;
		m_Priv = NULL;
		return -1;
	}

	ReleaseMutex(m_Priv->hMutex);
	return 0;
}

int AfMutex::Lock()
{
	if(!m_Priv) return -1;

	WaitForSingleObject(m_Priv->hMutex, INFINITE);
	return 0;
}

int AfMutex::TryLock()
{
	if(!m_Priv) return -1;

	DWORD  ret = WaitForSingleObject(m_Priv->hMutex, 1);	
	if( ret == WAIT_OBJECT_0)
	{
		return 0; // success
	}
	if( ret == WAIT_TIMEOUT)
	{
		return -1; // timeout
	}
	return -1;
}

void AfMutex::Unlock()
{
	if(!m_Priv) return;
	ReleaseMutex(m_Priv->hMutex);
}

#endif

 

Clog.h

#ifndef CLOG_H
#define CLOG_H

#include <stdio.h>
#include <ctime>
#include <stdarg.h>
#include "AfMutex.h"

//日志相关的类
class CLog
{
public:
	CLog(void)
	{
		;
	}
public:
	static CLog *i()                    //单例模式
	{
		static CLog c_log;
		return &c_log;
	}
	void InitLog(const char *log_dir)   //打开log_dir目录下的日志文件,如果该文件不存在,则创建它
	{
		char filePath[100] = { 0 };
		time_t now = time(0);
		tm *ltm = localtime(&now);
		sprintf(filePath, "%s/%04d-%02d-%02d_%02d%02d%02d.log", log_dir, 1900 + (ltm->tm_year), 1 + (ltm->tm_mon), ltm->tm_mday, ltm->tm_hour, ltm->tm_min, ltm->tm_sec);

		m_fp = fopen(filePath, "a");     //以附加的方式打开只写文件filePath。使用fopen打开的文件是共享的,即使不关闭文件指针,其它文件也可以访问该文件
		if (NULL == m_fp)
		{
			printf("can not open log file: %s/n", filePath);
		}
	}
	void WriteLog(const char *msg ...)   //将信息msg写入到文件指针为m_fp的日志文件中,并打印到控制台上(支持ANSI,格式化输出)
	{
		m_mutex.Lock();

		char buf[1024] = { 0 };
		char t_buf[50] = { 0 };
		time_t now = time(0);
		tm *ltm = localtime(&now);

		sprintf(t_buf, "<%d年%d月%d日%d时%d分%d秒>:", 1900 + (ltm->tm_year), 1 + (ltm->tm_mon), ltm->tm_mday, ltm->tm_hour, ltm->tm_min, ltm->tm_sec, msg);
		printf("%s", t_buf);
		fprintf(m_fp, "%s", t_buf);

		va_list vp;
		va_start(vp, msg);
		vfprintf(stdout, msg, vp);
		vfprintf(m_fp, msg, vp);
		va_end(vp);
		fflush(m_fp);
		
		m_mutex.Unlock();
	}
private:
	FILE *m_fp;               //日志文件的文件指针
	AfMutex m_mutex;          //互斥锁
};

#endif

 

main.cpp

#include "Clog.h"
#include <stdio.h>

using namespace std;


int main()
{
	CLog::i()->InitLog("log");
	char *buf = "xiaoming";
	CLog::i()->WriteLog("name:%s\n", buf);
	return 0;
}

 

Third, the operating results

 

We have created in vs (such as vs2015) a console project, add the above code, create a log directory under the project directory, as shown below:

 

Then compile and run, we can see that already can print out the log information in the console.

 

Generate log files corresponding to the time to start the program in accordance with at log directory.

 

IV Summary

    This article demonstrates logs only the most basic function of a log has. Actual use in a production environment log should consider many issues, such as performance logs, in time to save the log support program fault exception exit, whether to support accurate source traceability, log output level; if it is on the server, but also consider log support alternation (no server failure is not restarted, half a year into a log file will cause the file is too large), and so on. So in the project, we give priority to the use of existing open source libraries (such as log4cpp, boost.log, spdlog, glog, zlog, etc.), especially in the company's projects, rather than trying to achieve a log, made their own wheels might not only imperfect , not easy to use.

 

Fifth, reference links

Code portion mutex used herein reference made teacher Shao code linked below:

https://download.csdn.net/download/iamshaofa/4303875

 

 

Published 54 original articles · won praise 55 · views 120 000 +

Guess you like

Origin blog.csdn.net/u014552102/article/details/103517018
Recommended