我正在使用Sentry(在django项目中),我想知道如何正确地聚合错误。我将某些用户操作记录为错误,因此没有潜在的系统异常,并使用culprit
属性设置友好的错误名称。该消息是模板化的,并包含一条公共消息(“用户'x'因为'y'而无法执行操作”),但从不完全相同(不同的用户,不同的条件)。
Sentry明确地使用一些属性来确定是否将错误聚合为同一个异常,但是尽管已经查看了代码,但我无法弄清楚如何。
任何人都可以在我的代码中进一步挖掘并告诉我需要设置哪些属性以便按照我的意愿管理聚合?
[更新1:事件分组]
此行显示在sentry.models.Group:
中class Group(MessageBase):
"""
Aggregated message which summarizes a set of Events.
"""
...
class Meta:
unique_together = (('project', 'logger', 'culprit', 'checksum'),)
...
哪个有意义 - 我正在设置的项目,记录器和罪魁祸首 - 问题是checksum
。我将进一步调查,但是“校验和”表明二进制等价,它永远不会起作用 - 必须可以使用不同的属性对同一异常的实例进行分组?
[更新2:事件校验和]
事件校验和来自sentry.manager.get_checksum_from_event
方法:
def get_checksum_from_event(event):
for interface in event.interfaces.itervalues():
result = interface.get_hash()
if result:
hash = hashlib.md5()
for r in result:
hash.update(to_string(r))
return hash.hexdigest()
return hashlib.md5(to_string(event.message)).hexdigest()
下一站 - 事件interfaces
来自哪里?
[更新3:事件接口]
我已经知道interfaces是指用于描述传入哨兵事件的数据的标准机制,我使用的是标准sentry.interfaces.Message
和sentry.interfaces.User
接口。
这两个都将包含不同的数据,具体取决于异常实例 - 因此校验和永远不会匹配。有什么方法可以从校验和计算中排除这些吗? (或者至少是User
接口值,因为它必须是不同的 - 我可以标准化的Message
接口值。)
[更新4:解决方案]
以下是get_hash
和Message
接口的两个User
函数:
# sentry.interfaces.Message
def get_hash(self):
return [self.message]
# sentry.interfaces.User
def get_hash(self):
return []
查看这两个,只有Message.get_hash
接口将返回get_checksum_for_event
方法获取的值,因此这将是返回的值(散列等)网络这样做的结果是仅对消息进行校验和评估 - 理论上这意味着我可以标准化消息并保持用户定义的唯一性。
我已经在这里回答了我自己的问题,但希望我的调查能够用于遇到同样问题的其他人。 (顺便说一下,我也提交了针对Sentry文档的拉取请求作为其中的一部分; - ))
(注意任何使用/扩展Sentry和自定义接口的人 - 如果你想避免使用你的界面对异常进行分组,请返回一个空列表。)
答案 0 :(得分:17)
请参阅问题本身的最终更新。事件聚合在“项目”,“记录器”,“罪魁祸首”和“校验和”属性的组合上。前三个相对容易控制 - 第四个,'校验和'是作为事件一部分发送的数据类型的函数。
Sentry使用'interfaces'的概念来控制传入的数据结构,每个接口都带有get_hash
的实现,用于返回传入数据的哈希值.Sentry来了有许多标准接口('消息','用户','HTTP','Stacktrace','查询','例外'),这些接口都有自己的get_hash
实现。默认值(继承自Interface基类)是一个空列表,不会影响校验和。
在没有任何有效接口的情况下,事件消息本身将被哈希并作为校验和返回,这意味着消息对于要分组的事件而言必须是唯一的。
答案 1 :(得分:0)
我遇到了异常的常见问题。目前我们的系统只捕获异常,我很困惑,为什么其中一些合并为一个错误,而另一些则没有。 根据您上面的信息,我引用了“get_hash”方法并尝试找出差异“引发”我的错误。我发现的是,分组错误都来自自编写的Exception类型,它具有空的Exception.message值。
get_hash输出:
[<class 'StorageException'>, StorageException()]
并且多个错误来自具有填充消息值的异常类(jinja模板引擎)
[<class 'jinja2.exceptions.UndefinedError'>, UndefinedError('dict object has no attribute LISTza_*XYZ*',)]
不同的异常消息会触发不同的报告,在我的情况下,由于缺少Exception.message值而导致合并。
实现:
class StorageException(Exception):
def __init__(self, value):
Exception.__init__(self)
self.value = value