django的日志发往http server
配置示例:
# https://docs.djangoproject.com/zh-hans/2.1/topics/logging/
LOGGING = {
'version': ,
'disable_existing_loggers': False,
'formatters': { # 格式器
'verbose': {
# 后缀d表示数据格式是整数,s表示数据格式是字符串
'format': '[%(levelname)s] [%(asctime)s] [%(module)s] %(filename)s:%(lineno)d %(funcName)s '
'%(processName)s:[%(process)d] %(threadName)s:[%(thread)d] %(message)s'
# 'format': '{levelname} {asctime} {module} {process:d} {thread:d} {message}',
# 'style': '{',
},
'simple': {
'format': '[%(levelname)s] [%(asctime)s] %(message)s',
# 'format': '[%(asctime)s] %(message)s',
# 后缀d表示数据格式是整数,s表示数据格式是字符串
# 'format': '[%(levelname)s] [%(asctime)s] [%(module)s] %(filename)s:%(lineno)d %(funcName)s '
# '%(processName)s:[%(process)d] %(threadName)s:[%(thread)d] %(message)s',
# 'style': '{',
},
'standard': {
# 'format': '%(asctime)s [%(levelname)s] %(name)s: %(message)s',
'format': '{asctime} [{levelname:6}] {name:30}: {message}',
# 设置上面格式样式;{lineno:}是行号,至少显示3个字符,少则补空格
# 这里style选择{,是指{asctime}这种形式。
# 如果选择%,则是%(asctime)s这种形式。
# 还有一种选择,是$,是$asctime或${asctime}这种形式。
'style': '{',
# 设置时间格式
'datefmt': '%Y-%m-%d %H:%M:%S',
},
'operation': {
'format': '%(message)s'
}
},
# 'filters': {
# # 'special': {
# # '()': 'erebus.logging.SpecialFilter',
# # 'foo': 'bar',
# # },
# 'require_debug_true': {
# '()': 'django.utils.log.RequireDebugTrue',
# },
# }, # Handler是决定如何处理logger中每一条消息的引擎。它描述特定的日志行为,比如把消息输出到屏幕、文件或网络socket。
# 和 logger 一样,handler 也有日志级别的概念。如果一条日志记录的级别不匹配或者低于 handler 的日志级别,
# 对应的消息会被 handler 忽略。
'handlers': { # 处理器
'default': {
'level': 'DEBUG',
'class': 'logging.handlers.RotatingFileHandler',
'filename': 'logs/default.log',
'maxBytes': ***, # * MB
# 'maxBytes': *, # KB
# 保留7天的日志,没份5M,5份大概是一个小时的日志内容,主要是kafka日志
'backupCount': int(***/),
'formatter': 'standard',
},
'kafka': {
'level': 'DEBUG',
'class': 'logging.handlers.RotatingFileHandler',
'filename': 'logs/kafka.log',
'maxBytes': ***, # * MB
# 'maxBytes': *, # KB
# 保留7天的日志,没份5M,5份大概是一个小时的日志内容,主要是kafka日志
'backupCount': int(***/),
'formatter': 'standard',
},
'output_to_server': { # 输出到http server,参数来自类HTTPHandler初始化函数里的参数
'level': 'WARNING', # 忽略debug/info信息
'class': 'logging.handlers.HTTPHandler',
'host': '127.0.0.1:8088',
'url': '/api/v1/log',
# 使用GET方法遇到url最大长度限制
'method': 'POST',
'formatter': 'verbose',
},
'django': {
'level': 'INFO', # 忽略debug信息
'class': 'logging.FileHandler',
'filename': '{}/{}.log'.format(BASE_LOG_DIR, conf.get('log', 'name')),
'formatter': 'simple' if DEBUG else 'verbose',
'encoding': 'utf8',
},
'console': {
'level': 'DEBUG', # 所有的日志都会被输出到console
# 'filters': ['require_debug_true'],
'class': 'logging.StreamHandler',
'formatter': 'simple'
},
'operation': {
'level': 'INFO',
'class': 'logging.FileHandler',
'filename': '{}/{}.log'.format(BASE_LOG_DIR, 'operation'),
'formatter': 'operation',
'encoding': 'utf8'
},
'test': {
'level': 'INFO',
'class': 'logging.FileHandler',
'filename': '{}/{}.log'.format(BASE_LOG_DIR, 'test'),
'formatter': 'standard',
'encoding': 'utf8'
}
# 'mail_admins': {
# 'level': 'ERROR',
# 'class': 'django.utils.log.AdminEmailHandler',
# # 'filters': ['special']
# }
},
'loggers': { # 记录器 # 可以通过使用空字符串:''来设置'catch all' logger
# 在以下设置中,将所有日志事件级别为WARNING及以上的日志发送给日志服务器,但配置为'propagate': False日志事件除外,
'': {
'handlers': ['default', 'output_to_server'],
# 这样情况下的level设置是无效的,所有级别的信息都会传给handlers处理,由handlers的level界别决定
'level': 'ERROR',
'propagate': False
},
# 记录所有kakfa相关的日志
'kafka': {
'handlers': ['kafka'],
'level': 'DEBUG',
'propagate': True
},
# 这里必须使用名字django和django.request,目的是为了捕获django框架的日志内容
'django': {
'handlers': ['django', 'console'],
# 当 logger 处理一条消息时,会将自己的日志级别和这条消息的日志级别做对比。
# 如果消息的日志级别匹配或者高于 logger 的日志级别,它就会被进一步处理。
# 否则这条消息就会被忽略掉。当 logger 确定了一条消息需要处理之后,会把它传给 Handler。
# 把INFO及以上级别的日志传给handlers,然后由handlers根据handlers的level进一步处理日志输出
'level': 'INFO',
'propagate': True, # 若值为False,表示日志不会传到上个层级,自然也不会传到default.log里
},
# 使用logger = logging.getLogger('django.request'), logger.info('info'),
# 可以把日志输出到'handlers': ['django', 'console'],
'django.request': {
# 即使和django的handlers一样,level也一样,也并不会产生2次相同的日志内容,应该是个并集。
'handlers': ['django', 'console'],
'level': 'DEBUG',
# 会把日志向django.request的上层django传播
'propagate': True,
},
# sql语句
'django.db.backends': {
# 即使和django的handlers一样,level也一样,也并不会产生2次相同的日志内容,应该是个并集。
'handlers': ['django', 'console'],
'level': 'DEBUG',
# 会把日志向django.request的上层django传播
'propagate': True,
},
# 'erebus.custom': {
# 'handlers': ['console', 'mail_admins'],
# 'level': 'INFO',
# # 'filters': ['special']
# },
# 名字随意起,用时,使用logger = logging.getLogger(conf.get('log', 'name'))获取,传到相应的loggers里就可以
'operation': {
'handlers': ['operation'],
'level': 'INFO',
'propagate': True,
},
'test': {
'handlers': ['console', 'test'],
'level': 'INFO',
'propagate': False, # 不要传给上一层级
}
}
}
查看使用的class HTTPHandler,注意参数对应
class HTTPHandler(logging.Handler):
"""
A class which sends records to a Web server, using either GET or
POST semantics.
"""
def __init__(self, host, url, method="GET", secure=False, credentials=None,
context=None):
"""
Initialize the instance with the host, the request URL, and the method
("GET" or "POST")
"""
logging.Handler.__init__(self)
method = method.upper()
if method not in ["GET", "POST"]:
raise ValueError("method must be GET or POST")
if not secure and context is not None:
raise ValueError("context parameter only makes sense "
"with secure=True")
self.host = host
self.url = url
self.method = method
self.secure = secure
self.credentials = credentials
self.context = context def mapLogRecord(self, record):
"""
Default implementation of mapping the log record into a dict
that is sent as the CGI data. Overwrite in your class.
Contributed by Franz Glasner.
"""
return record.__dict__ def emit(self, record):
"""
Emit a record. Send the record to the Web server as a percent-encoded dictionary
"""
try:
import http.client, urllib.parse
host = self.host
if self.secure:
h = http.client.HTTPSConnection(host, context=self.context)
else:
h = http.client.HTTPConnection(host)
url = self.url
data = urllib.parse.urlencode(self.mapLogRecord(record))
if self.method == "GET":
if (url.find('?') >= ):
sep = '&'
else:
sep = '?'
url = url + "%c%s" % (sep, data)
h.putrequest(self.method, url)
# support multiple hosts on one IP address...
# need to strip optional :port from host, if present
i = host.find(":")
if i >= :
host = host[:i]
# See issue #: putrequest call above already adds this header
# on Python .x.
# h.putheader("Host", host)
if self.method == "POST":
h.putheader("Content-type",
"application/x-www-form-urlencoded")
h.putheader("Content-length", str(len(data)))
if self.credentials:
import base64
s = ('%s:%s' % self.credentials).encode('utf-8')
s = 'Basic ' + base64.b64encode(s).strip().decode('ascii')
h.putheader('Authorization', s)
h.endheaders()
if self.method == "POST":
h.send(data.encode('utf-8'))
h.getresponse() #can't do anything with the result
except Exception:
self.handleError(record)
参考:https://cloud.tencent.com/developer/ask/183866
django的日志发往http server的更多相关文章
- python的日志模块:logging;django的日志系统;django日志输出时间修改
Django的log,主要是复用Python标准库中的logging模块,在settings.py中进行配置 源代码 1.__init__.py包含以下类: StreamHandler Formatt ...
- Django多进程日志文件问题
Django多进程日志文件问题 最近使用Django做一个项目.在部署的时候发现日志文件不能滚动(我使用的是RotatingFileHandler),只有一个日志文件. 查看Log发现一个错误消息:P ...
- tomcat日志警告WARNING: [SetPropertiesRule]{Server/Service/Engine/Host/Context} Setting property 'debug' to '0' did not find a matching property.
日志中有警告: [SetPropertiesRule]{Server/Service/Engine/Host/Context} Setting property 'debug' to '0' did ...
- 分布式计算 要不要把写日志独立成一个Server Remote Procedure Call Protocol
w https://en.wikipedia.org/wiki/Remote_procedure_call In distributed computing a remote procedure ca ...
- django开发日志配置
做django开发离不开 日志,这用于保存我门的服务器的日志信息,便于开发人员的维护. 直接上代码: 在setting.py文件里直接配置即可 LOGGING = { 'version': 1, 'd ...
- Django中日志管理
在settings中设置日志的相关信息,然后再逻辑代码区就可以保存相应的信息了 #简单设置: LOGGING = { 'version': 1, 'disable_existing_loggers': ...
- django 自定义日志配置
如果不想使用 python 的 dictConfig 格式来配置 logger,可以制定自己的配置架构. LOGGING_CONFIG 配置定义了用来配置 django logger 的可调用函数,默 ...
- DJango错误日志生成
DJango错误日志生成 setting.py设置 LOGGING = { 'version': 1, 'disable_existing_loggers': False, 'formatters': ...
- 网络编程(client发信息给server)
client发信息给server
随机推荐
- ClouderaManager中Event Server报No such file or directory
错误日志如下: 2015-06-24 06:13:10,176 ERROR com.cloudera.cmf.eventcatcher.server.EventCatcherService: Erro ...
- Java反射1——扫描某个包下的所有类
1.从包package中获取所有的Class /** * 从包package中获取所有的Class * * @param pack * @return */ public static Set< ...
- mint-ui 关于有时候官网有时候打不开的问题
难道就我只有这种情况,不知所措的,要不好看看是什么,看到别人说,是你路由的问题,换个路由的可以了,我觉得不是,那试试HTTP协议的问题 换个https试试就可以 这是什么原因呢? http是超文本传输 ...
- Xamarin iOS教程之页面控件
Xamarin iOS教程之页面控件 Xamarin iOS 页面控件 在iPhone手机的主界面中,经常会看到一排小白点,那就是页面控件,如图2.44所示.它是由小白点和滚动视图组成,可以用来控制翻 ...
- 添加第一个控制器(Controllers)
在MVC体系架构中,输入请求是由控制器Controller来处理的(负责处理浏览器请求,并作出响应).在ASP.NET MVC中Controller本身是一个类(Class)通常继承于System.W ...
- JFreeChart 之饼图
JFreeChart 之饼图 一.JFreeChart 简介 JFreeChart是JAVA平台上的一个开放的图表绘制类库.它完全使用JAVA语言编写,是为applications, applets, ...
- BZOJ.2007.[NOI2010]海拔(最小割 对偶图最短路)
题目链接 想一下能猜出,最优解中海拔只有0和1,且海拔相同的点都在且只在1个连通块中. 这就是个平面图最小割.也可以转必须转对偶图最短路,不然只能T到90分了..边的方向看着定就行. 不能忽略回去的边 ...
- 7.30 正睿暑期集训营 A班训练赛
目录 2018.7.30 正睿暑期集训营 A班训练赛 T1 A.蔡老板分果子(Hash) T2 B.蔡老板送外卖(并查集 最小生成树) T3 C.蔡老板学数学(DP NTT) 考试代码 T2 T3 2 ...
- ElasticSearch入门 :Windows下安装ElasticSearch
这是ElasticSearch 2.4 版本系列的第一篇: ElasticSearch入门 第一篇:Windows下安装ElasticSearch ElasticSearch入门 第二篇:集群配置 E ...
- setInterval设置停止和循环
原文链接:http://caibaojian.com/setinterval-times.html 需要知道已经经过了多少次或者说过多久就会停止 var timesRun = 0; var inter ...