Я знаю, що це вже вирішена відповідь, але відповідно до django> = 1.3 є новий параметр журналу.
Перехід від старого до нового не є автоматичним, тому я подумав, що запишу його тут.
І звичайно оформити док-джанго на ще декілька.
Це основний конф, створений за замовчуванням за допомогою django-admin createproject v1.3 - пробіг може змінитися в останніх версіях django:
LOGGING = {
'version': 1,
'disable_existing_loggers': False,
'handlers': {
'mail_admins': {
'level': 'ERROR',
'class': 'django.utils.log.AdminEmailHandler',
}
},
'loggers': {
'django.request': {
'handlers': ['mail_admins'],
'level': 'ERROR',
'propagate': True,
}
}
}
Ця структура заснована на стандартному протоколі протоколу Python dictConfig , який диктує такі блоки:
formatters
- відповідне значення буде диктатом, у якому кожен ключ є ідентифікатором форматера, а кожне значення - це дікт, що описує, як налаштувати відповідний екземпляр Форматтера.
filters
- відповідне значення буде диктатом, у якому кожен ключ є ідентифікатором фільтра, і кожне значення є діктом, що описує, як налаштувати відповідний екземпляр фільтра.
handlers
- відповідне значення буде диктатом, у якому кожен ключ є ідентифікатором обробника, і кожне значення є діктом, що описує, як налаштувати відповідний екземпляр обробника. Кожен обробник має такі ключі:
class
(обов’язково). Це повністю кваліфікована назва класу обробників.
level
(на вибір). Рівень обробника.
formatter
(на вибір). Ідентифікатор форматера для цього обробника.
filters
(на вибір). Список ідентифікаторів фільтрів для цього обробника.
Я зазвичай роблю принаймні так:
- додати файл .log
- налаштувати мої програми для запису в цей журнал
Що перекладається на:
LOGGING = {
'version': 1,
'disable_existing_loggers': False,
'formatters': {
'verbose': {
'format': '%(levelname)s %(asctime)s %(module)s %(process)d %(thread)d %(message)s'
},
'simple': {
'format': '%(levelname)s %(message)s'
},
},
'filters': {
'require_debug_false': {
'()': 'django.utils.log.RequireDebugFalse'
}
},
'handlers': {
'null': {
'level':'DEBUG',
'class':'django.utils.log.NullHandler',
},
'console':{
'level': 'DEBUG',
'class': 'logging.StreamHandler',
'formatter': 'simple'
},
# I always add this handler to facilitate separating loggings
'log_file':{
'level': 'DEBUG',
'class': 'logging.handlers.RotatingFileHandler',
'filename': os.path.join(VAR_ROOT, 'logs/django.log'),
'maxBytes': '16777216', # 16megabytes
'formatter': 'verbose'
},
'mail_admins': {
'level': 'ERROR',
'filters': ['require_debug_false'],
'class': 'django.utils.log.AdminEmailHandler',
'include_html': True,
}
},
'loggers': {
'django.request': {
'handlers': ['mail_admins'],
'level': 'ERROR',
'propagate': True,
},
'apps': { # I keep all my of apps under 'apps' folder, but you can also add them one by one, and this depends on how your virtualenv/paths are set
'handlers': ['log_file'],
'level': 'INFO',
'propagate': True,
},
},
# you can also shortcut 'loggers' and just configure logging for EVERYTHING at once
'root': {
'handlers': ['console', 'mail_admins'],
'level': 'INFO'
},
}
редагувати
Перегляньте винятки щодо запиту, які завжди реєструються, і Ticket № 16288 :
Я оновив вищевказаний зразок conf, щоб явно включити правильний фільтр для mail_admins, так що за замовчуванням електронні листи не надсилаються, коли налагодження відповідає True.
Вам слід додати фільтр:
'filters': {
'require_debug_false': {
'()': 'django.utils.log.RequireDebugFalse'
}
},
і застосуйте його до обробника mail_admins:
'mail_admins': {
'level': 'ERROR',
'filters': ['require_debug_false'],
'class': 'django.utils.log.AdminEmailHandler',
'include_html': True,
}
В іншому випадку django.core.handers.base.handle_uncaught_exception
не передає помилок у реєстратор 'django.request', якщо налаштування.DEBUG є True.
Якщо цього не зробити в Django 1.5, ви отримаєте
DeprecationWarning: у обробника журналу 'mail_admins' не визначено фільтрів: додавання неявного фільтра, що відповідає лише налагодженням
але все одно працюватимуть правильно БАТЬ у django 1.4 та django 1.5.
** завершити редагування **
Ця конфіденція сильно надихається зразком conf в документі django, але додаючи частину файлу журналу.
Я часто також роблю такі дії:
LOG_LEVEL = 'DEBUG' if DEBUG else 'INFO'
...
'level': LOG_LEVEL
...
Тоді в свій код python я завжди додаю NullHandler на випадок, якщо конфліктування журналів не визначено. Це дозволить уникнути попереджень для жодного обробника. Особливо корисно для ліб, які не обов'язково називати лише в Джанго ( ref )
import logging
# Get an instance of a logger
logger = logging.getLogger(__name__)
class NullHandler(logging.Handler): #exists in python 3.1
def emit(self, record):
pass
nullhandler = logger.addHandler(NullHandler())
# here you can also add some local logger should you want: to stdout with streamhandler, or to a local file...
[...]
logger.warning('etc.etc.')
Сподіваюся, це допомагає!