]> git.ipfire.org Git - dbl.git/commitdiff
lists: Store a stats history
authorMichael Tremer <michael.tremer@ipfire.org>
Mon, 5 Jan 2026 10:08:54 +0000 (10:08 +0000)
committerMichael Tremer <michael.tremer@ipfire.org>
Mon, 5 Jan 2026 10:08:54 +0000 (10:08 +0000)
Signed-off-by: Michael Tremer <michael.tremer@ipfire.org>
src/database.sql
src/dnsbl/lists.py

index 94146f1060ac702b6aa869c9403dbe9b0c0f1281..f1d32946d6babd31e3d33fbd3142062fab9c1157 100644 (file)
@@ -2,7 +2,7 @@
 -- PostgreSQL database dump
 --
 
-\restrict pXUPUyLkgUWquVqcqOb0Ffu3EcVPJGROwmyXhgPEICcDG5af5bsnhpnMAO9PMhG
+\restrict rL7JZX9lefDYCij1ck1YZ9zBYKQONa1UgbdrSppmH7VGwDI2usPtcuRDMxQJwsl
 
 -- Dumped from database version 17.6 (Debian 17.6-0+deb13u1)
 -- Dumped by pg_dump version 17.6 (Debian 17.6-0+deb13u1)
@@ -109,6 +109,38 @@ CREATE SEQUENCE public.domains_id_seq
 ALTER SEQUENCE public.domains_id_seq OWNED BY public.domains.id;
 
 
+--
+-- Name: list_stats; Type: TABLE; Schema: public; Owner: -
+--
+
+CREATE TABLE public.list_stats (
+    id integer NOT NULL,
+    list_id integer NOT NULL,
+    ts timestamp with time zone DEFAULT CURRENT_TIMESTAMP NOT NULL,
+    total_domains integer NOT NULL
+);
+
+
+--
+-- Name: list_stats_id_seq; Type: SEQUENCE; Schema: public; Owner: -
+--
+
+CREATE SEQUENCE public.list_stats_id_seq
+    AS integer
+    START WITH 1
+    INCREMENT BY 1
+    NO MINVALUE
+    NO MAXVALUE
+    CACHE 1;
+
+
+--
+-- Name: list_stats_id_seq; Type: SEQUENCE OWNED BY; Schema: public; Owner: -
+--
+
+ALTER SEQUENCE public.list_stats_id_seq OWNED BY public.list_stats.id;
+
+
 --
 -- Name: lists; Type: TABLE; Schema: public; Owner: -
 --
@@ -287,6 +319,13 @@ ALTER TABLE ONLY public.api_keys ALTER COLUMN id SET DEFAULT nextval('public.api
 ALTER TABLE ONLY public.domains ALTER COLUMN id SET DEFAULT nextval('public.domains_id_seq'::regclass);
 
 
+--
+-- Name: list_stats id; Type: DEFAULT; Schema: public; Owner: -
+--
+
+ALTER TABLE ONLY public.list_stats ALTER COLUMN id SET DEFAULT nextval('public.list_stats_id_seq'::regclass);
+
+
 --
 -- Name: lists id; Type: DEFAULT; Schema: public; Owner: -
 --
@@ -339,6 +378,14 @@ ALTER TABLE ONLY public.domains
     ADD CONSTRAINT domains_pkey PRIMARY KEY (id);
 
 
+--
+-- Name: list_stats list_stats_pkey; Type: CONSTRAINT; Schema: public; Owner: -
+--
+
+ALTER TABLE ONLY public.list_stats
+    ADD CONSTRAINT list_stats_pkey PRIMARY KEY (id);
+
+
 --
 -- Name: lists lists_pkey; Type: CONSTRAINT; Schema: public; Owner: -
 --
@@ -435,6 +482,13 @@ CREATE UNIQUE INDEX domains_unique ON public.domains USING btree (list_id, name)
 CREATE INDEX domains_updated_at ON public.domains USING btree (source_id, updated_at) WHERE (removed_at IS NULL);
 
 
+--
+-- Name: list_stats_unique; Type: INDEX; Schema: public; Owner: -
+--
+
+CREATE UNIQUE INDEX list_stats_unique ON public.list_stats USING btree (list_id, ts DESC);
+
+
 --
 -- Name: lists_unique; Type: INDEX; Schema: public; Owner: -
 --
@@ -495,6 +549,14 @@ ALTER TABLE ONLY public.domains
     ADD CONSTRAINT domains_source_id FOREIGN KEY (source_id) REFERENCES public.sources(id);
 
 
+--
+-- Name: list_stats list_stats_list_id; Type: FK CONSTRAINT; Schema: public; Owner: -
+--
+
+ALTER TABLE ONLY public.list_stats
+    ADD CONSTRAINT list_stats_list_id FOREIGN KEY (list_id) REFERENCES public.lists(id);
+
+
 --
 -- Name: reports reports_list_id; Type: FK CONSTRAINT; Schema: public; Owner: -
 --
@@ -523,5 +585,5 @@ ALTER TABLE ONLY public.sources
 -- PostgreSQL database dump complete
 --
 
-\unrestrict pXUPUyLkgUWquVqcqOb0Ffu3EcVPJGROwmyXhgPEICcDG5af5bsnhpnMAO9PMhG
+\unrestrict rL7JZX9lefDYCij1ck1YZ9zBYKQONa1UgbdrSppmH7VGwDI2usPtcuRDMxQJwsl
 
index 324ab9f05bbf96127e6bdc65c5fbeff93ed54ee4..2fcfb345a50038ca7131ee4007cbcc5ae7a8cb96 100644 (file)
@@ -403,6 +403,13 @@ class List(sqlmodel.SQLModel, database.BackendMixin, table=True):
                # Store the number of total domains
                self.total_domains = self.backend.db.fetch_one(stmt)
 
+               # Store the stats history
+               self.backend.db.insert(
+                       ListStats,
+                       list          = self,
+                       total_domains = self.total_domains,
+               )
+
        # Export!
 
        def export(self, f, format, **kwargs):
@@ -641,3 +648,24 @@ class List(sqlmodel.SQLModel, database.BackendMixin, table=True):
                )
 
                return self.backend.db.select(stmt)
+
+
+class ListStats(sqlmodel.SQLModel, table=True):
+       __tablename__ = "list_stats"
+
+       # ID
+       id: int = sqlmodel.Field(primary_key=True, exclude=True)
+
+       # List ID
+       list_id: int = sqlmodel.Field(foreign_key="lists.id", exclude=True)
+
+       # List
+       list: "List" = sqlmodel.Relationship()
+
+       # Timestamp
+       ts: datetime.datetime = sqlmodel.Field(
+               sa_column_kwargs = { "server_default" : sqlmodel.text("CURRENT_TIMESTAMP") },
+       )
+
+       # Total Domains
+       total_domains: int