Класс логирования - C#
Формулировка задачи:
Добрый день. Не судите строго С# изучаю всего 2 недели. Решил написать (в учебных целях) систему логирования приложения. Программа должна создавать файл с логами logs.log и при достижении файла 100 Кб создавался новый файл с расширением *.old. при этом сохранять на диске только последние 20 файлов с расширением *.old. Долго бился создал такой клас который всё это проделывает. И он даже работает.
Обращаюсь к знающим язык программирования С# правильно ли реализован класс. Возможно, кому-то будет полезен этот пример
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.IO;
using System.Xml.Serialization;
namespace test_log
{
class Logs
{
static private string path;
static private string directory;
static public DirectoryInfo di;
static public FileInfo fileInfo;
public Logs() //Конструктор
{
directory = AppDomain.CurrentDomain.BaseDirectory + @"\Log";
path = directory + @"\logs.log";
di = new DirectoryInfo(directory);
if (!di.Exists) // директория не существует
{
di.Create(); // создаём директорию
}
if (!File.Exists(path)) //файла нет создаем
{
using (StreamWriter sw = File.AppendText(path))
{
sw.WriteLine("---------Start----------");
}
}
}
static public void FileEx()
{
DateTime now = DateTime.Now;
//Console.WriteLine(directory + @"\" + now.ToString("yyMMddhhmmss") + ".old");
String newfile = directory + @"\" + now.ToString("yyMMddhhmmss") + ".old";
fileInfo = new FileInfo(path);
if (fileInfo.Length > 100000) // если размер файло больше 100000
{
if (!File.Exists(directory + @"\" + now.ToString("yyMMddhhmmss") + ".old"))
{
File.Move(path, newfile); // перемещяем лог файл
FileInfo fileOld = new FileInfo(newfile);
fileOld.CreationTime = now; // устанавливаем дату создания
}
else
{
fileInfo = new FileInfo(directory + @"\" + now.ToString("yyMMddhhmmss") + ".old");
fileInfo.Delete();
}
}
// Получение списка файлов в папке
var files = Directory.GetFiles(directory, "*.old", SearchOption.AllDirectories);
if (files.Length > 20) // если в папке больше 20 файлов
{
var iter = files.OrderByDescending(f => File.GetCreationTime(f)); // сортируем по дате создания
foreach (string item in iter.Skip(20)) // пропускаем первые 20
{
fileInfo = new FileInfo(item);
fileInfo.Delete(); //удаляем старые файлы
Console.WriteLine(item);
}
}
}
static public void Info(string msg) // запись информации
{
FileEx();
using (StreamWriter sw = File.AppendText(path))
{
sw.WriteLine("{0} [INFO] {1}", DateTime.Now, msg);
}
}
static public void Error(string msg) //запись Ошибки
{
FileEx();
using (StreamWriter sw = File.AppendText(path))
{
sw.WriteLine("{0} [ERR] {1}", DateTime.Now, msg);
}
}
}
}Решение задачи: «Класс логирования»
textual
Листинг программы
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.IO;
using System.Xml.Serialization;
namespace test_log
{
class Logs
{
static private string path;
static private string directory;
static public DirectoryInfo di;
static public FileInfo fileInfo;
public Logs()
{
// Используйте Path.Combine(AppDomain.CurrentDomain.BaseDirectory, "Log")
directory = AppDomain.CurrentDomain.BaseDirectory + @"\Log";
// То же самое: path = Path.Combine(directory, "logs.log");
path = directory + @"\logs.log";
di = new DirectoryInfo(directory);
// Эта проверка делается в теле метода Create, потому дублировать ее не обязательно
if (!di.Exists)
{
di.Create();
}
if (!File.Exists(path))
{
// Для добавления одной строчки можно воспользоваться File.AppendAllText("---------Start----------" + Environment.NewLine
using (StreamWriter sw = File.AppendText(path))
{
sw.WriteLine("---------Start----------");
}
}
}
static public void FileEx()
{
DateTime now = DateTime.Now;
// Снова Path.Combine. В данном случае форматирования даты лучше использовать HH для указания часов - они будут в 24-часовом формате, а не в 12-часовом, как у вас
String newfile = directory + @"\" + now.ToString("yyMMddhhmmss") + ".old";
fileInfo = new FileInfo(path);
if (fileInfo.Length > 100000) // Ататат, а как же 1кб = 1024б? :)
{
// Опять вызов DateTime.Now? А если между созданием newfile и этой строчкой прошла секунда? И почему бы не воспользоваться ранее созданной newfile?
// Личное предпочтение: не люблю сравнение от обратного при наличии else. Так, мне кажется, более понятно: if (File.Exists(...)) { } else { }
if (!File.Exists(directory + @"\" + now.ToString("yyMMddhhmmss") + ".old"))
{
File.Move(path, newfile);
// Для изменения одного свойства не обязательно создавать новый объект. Можно воспользоваться File.SetCreationTime(newfile, now)
FileInfo fileOld = new FileInfo(newfile);
fileOld.CreationTime = now;
}
else
{
// Почему не вызвать просто File.Delete(newfile)?
fileInfo = new FileInfo(directory + @"\" + now.ToString("yyMMddhhmmss") + ".old");
fileInfo.Delete();
}
}
var files = Directory.GetFiles(directory, "*.old", SearchOption.AllDirectories);
if (files.Length > 20)
{
var iter = files.OrderByDescending(f => File.GetCreationTime(f));
foreach (string item in iter.Skip(20))
{
// Снова File.Delete(item)
fileInfo = new FileInfo(item);
fileInfo.Delete();
Console.WriteLine(item);
}
}
}
static public void Info(string msg)
{
FileEx();
using (StreamWriter sw = File.AppendText(path))
{
sw.WriteLine("{0} [INFO] {1}", DateTime.Now, msg);
}
}
static public void Error(string msg)
{
FileEx();
using (StreamWriter sw = File.AppendText(path))
{
sw.WriteLine("{0} [ERR] {1}", DateTime.Now, msg);
}
}
}
}