Конфигурация Log4Net во внешнем файле не работает
-
22-07-2019 - |
Вопрос
Мы используем log4net и хотим указать его конфигурацию во внешнем конфигурационном файле (как мы это делали с другими разделами). Для этого мы изменили раздел log4net в файле App.config:
...
<section name="log4net"
type="log4net.Config.Log4NetConfigurationSectionHandler, log4net"/>
...
<log4net configSource="Log.config" />
...
И в файле Log.Config (тот же каталог, что и у App.config) мы имеем:
<log4net>
<appender name="General" type="log4net.Appender.FileAppender">
<file value="myapp.log" />
<layout type="log4net.Layout.SimpleLayout" />
</appender>
<root>
<appender-ref ref="General" />
</root>
</log4net>
Однако, когда мы запускаем приложение, файл журнала не создается (и регистрация не производится). На консоль не выводятся сообщения об ошибках.
Если мы переместим содержимое файла Log.config обратно в App.config (заменив первую строчку кода выше), он будет работать как положено. Есть идеи, почему он не работает во внешнем файле?
Решение
У вас есть следующий атрибут в файле AssemblyInfo.cs
:
[assembly: log4net.Config.XmlConfigurator(ConfigFile = "Log4Net.config", Watch = true)]
и код, подобный этому, в начале каждого класса, для которого требуется функциональность ведения журнала:
private static readonly ILog log =
LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType);
У меня есть запись в блоге, содержащая эту и другую информацию здесь .
Другие советы
По этому вопросу имеется открытый дефект . Log4Net не поддерживает атрибут configSource элементов конфигурации. Чтобы использовать чисто конфигурационное файловое решение, используйте ключ log4net.Config в appSettings.
Шаг 1. Включите определение раздела нормальной конфигурации:
<configSections>
<section name="log4net" type="log4net.Config.Log4NetConfigurationSectionHandler, log4net"/>
</configSections>
Шаг 2. Используйте волшебный ключ log4net.Config в appSettings. Р>
<appSettings>
<add key="log4net.Config" value="log4net.simple.config" />
</appSettings>
Шаг 3. Добавьте исправление для исправления обработки configSource. Р>
Пропущенный шаг:
log4net.Config.XmlConfigurator.Configure();
это приведет к использованию configSource. Убедитесь, что вы вызываете его один раз перед вызовом GetLogger ();
Убедитесь, что для вашего файла log4net.config заданы следующие свойства:
Действие создания: содержимое
Копировать в выходной каталог: всегда копировать
Либо используйте,
<configuration>
<configSections>
<section name="log4net" type="log4net.Config.Log4NetConfigurationSectionHandler, log4net"/>
</configSections>
<appSettings>
<add key="log4net.Config" value="Log4Net.config" />
</appSettings>
или просто
log4net.Config.XmlConfigurator.ConfigureAndWatch(new System.IO.FileInfo("Log4Net.config"));
В обоих случаях файл Log4Net.config должен находиться в выходном каталоге. Вы можете сделать это, установив свойства файла Log4Net.config в обозревателе решений. Действие построения - содержимое и копирование в выходной каталог - всегда копировать
Остерегайтесь этой проблемы ...
В моем случае все было настроено правильно. Проблема в том, что я использовал веб-развертывание в Visual Studio 2013 для загрузки сайта на WinHost.com и сбросил ACL на сервере. Это, в свою очередь, отозвало все разрешения для папок и файлов - log4net не смог записать файл.
Подробнее об этом можно прочитать здесь:
Как остановить веб-развертывание / MSBuild не испортить права доступа к серверу
Я попросил группу поддержки там сбросить ACL, а затем log4net начал выплевывать логи. :) Р>
Предполагая, что у вас есть внешний файл конфигурации с именем log4net.config, который копируется в ваш каталог развертывания, вы можете настроить его следующим образом:
using System;
using System.Collections.Generic;
using System.Windows.Forms;
using System.Reflection;
using log4net;
namespace MyAppNamespace {
static class Program {
//declare it as static and public so all classes in the project can access it
//like so: Program.log.Error("got an error");
public static readonly log4net.ILog log = log4net.LogManager.GetLogger(typeof(Program));
/// <summary>
/// The main entry point for the application.
/// </summary>
[STAThread]
static void Main() {
//configure it to use external file
log4net.Config.XmlConfigurator.Configure(new Uri(Application.StartupPath + "\\log4net.config"));
//use it
log.Debug("############# STARING APPLICATION #################");
Application.EnableVisualStyles();
Application.SetCompatibleTextRenderingDefault(false);
Application.Run(new FormMain());
}
}
}
У меня была та же проблема, кроме того, что
[assembly: log4net.Config.XmlConfigurator(ConfigFile = "log4net")]
в работающем проекте у меня также была следующая строка в ссылочном проекте:
[assembly: log4net.Config.XmlConfigurator]
Когда я удалил эту строку в ссылочных проектах, журналы начали появляться.
Также можно включить режим отладки для log4net
. Вставьте это в файл App.config:
<appSettings>
<add key="log4net.Internal.Debug" value="true"/>
</appSettings>
<system.diagnostics>
<trace autoflush="true">
<listeners>
<add
name="textWriterTraceListener"
type="System.Diagnostics.TextWriterTraceListener"
initializeData="link\to\your\file.log" />
</listeners>
</trace>
</system.diagnostics>
и вы будете по крайней мере получать сообщения об ошибках, из которых вы сможете узнать, что именно пошло не так. В моем случае я просто забыл установить Копировать в выходной каталог
в Копировать всегда
.
@Mitch, оказывается, есть файл с объявлением [assembly: ...], но у него не было свойства ConfigFile. Р>
Как только я добавил его и указал на Log.config, он начал работать. Я бы подумал, что он будет работать как все остальные разделы конфигурации (то есть AppSettings) и будет принимать внешние файлы конфигурации без изменений.
У нас нет второго упомянутого вами утверждения, поскольку мы заключаем его в глобальный поставщик статического журнала.
В моем случае я получил это сообщение об ошибке:
log4net: config file [C:\........\bin\Debug\log4net.config] not found.
И log4net.config
файл был в проекте Visual Studio 2017, но когда я проверил файл в bin \ Debug
папку я не смог найти.
Моя первоначальная установка сборки была такой:
[assembly: log4net.Config.XmlConfigurator(ConfigFile = "log4net.config", Watch = true)]
После некоторого времени исследования я изменяю его на следующее, и оно работает:
[assembly: log4net.Config.XmlConfigurator(ConfigFile = @"..\..\log4net.config", Watch = true)]
[сборка: log4net.Config.XmlConfigurator (ConfigFile = " Log4Net.config ")]
- Убедитесь, что log4net.config включен в проект
- В свойствах log4net.config Ол>
- Дважды проверьте уровень журнала значение уровня = " ALL " Ол>
измените Копировать в выходной каталог на Копировать, если новее