我不是 DBMS 方面的专家,并试图建立一个可以附加到许多表的警报系统,所以我认为提出这个问题会对我的架构有所帮助。
可能让我有点困惑的是,您可以将多个警报附加到每个模型(会话、事件、组织),这些警报在我的数据库中的表中表示。每个模型的一条记录可以有多个不同的警报响起。
解决这个问题最简单的方法是创建一个表,例如
CREATE TABLE alerts (
id uuid DEFAULT uuid_generate_v4() PRIMARY KEY,
alert_type character varying(50) NOT NULL,
metadata jsonb,
session_id uuid REFERENCES sessions(id) ON DELETE DO NOTHING ON UPDATE CASCADE,
event_id uuid REFERENCES events(id) ON DELETE DO NOTHING ON UPDATE CASCADE,
organization_id uuid REFERENCES organizations(id) ON DELETE DO NOTHING ON UPDATE CASCADE,
created_at timestamp without time zone,
updated_at timestamp without time zone
);
但如果我们将其扩展到更多附加到警报系统的表,这似乎是一个糟糕的策略。它显然不能很好地扩展。我在两种策略之间犹豫。
您有一个表alerts
和 来代表many-to-many
第二个表alerts_relations
,该表具有table_name
和table_id
来理解它所附加的每个其他模型/表。
CREATE TABLE alerts (
id uuid DEFAULT uuid_generate_v4() PRIMARY KEY,
alert_type character varying(50) NOT NULL,
metadata jsonb,
created_at timestamp without time zone,
updated_at timestamp without time zone
);
CREATE TABLE alerts_relations (
id uuid DEFAULT uuid_generate_v4() PRIMARY KEY,
alert_id uuid REFERENCES alerts(id) ON DELETE CASCADE ON UPDATE CASCADE,
table_name character varying(50) NOT NULL,
table_id character varying(50) NOT NULL,
created_at timestamp without time zone,
updated_at timestamp without time zone
);
另一种策略将其删除table_name
并table_id
替换为以下内容
CREATE TABLE session_alerts (
session_id uuid REFERENCES sessions(id) ON DELETE CASCADE ON UPDATE CASCADE
) INHERITS (alert_relations);
CREATE TABLE event_alerts (
event_id uuid REFERENCES events(id) ON DELETE CASCADE ON UPDATE CASCADE
) INHERITS (alert_relations);
CREATE TABLE organization_alerts (
organization_id uuid REFERENCES organizations(id) ON DELETE CASCADE ON UPDATE CASCADE
) INHERITS (alert_relations);
我想知道什么策略可以产生更好的性能以及什么是最容易维护的。如果这有帮助的话,我的代码库是用 Golang 编写的,所以我必须手动处理 SQL 并做很少的 ORM 工作。
最后一个策略似乎对我的业务逻辑来说是最方便的,因为每个关系都可以用不同的表和名称来表示。听起来更容易维护,但目前我还不确定什么;可能有我看不到的缺点。
当然,欢迎任何其他解决方案!谢谢阅读。