summaryrefslogtreecommitdiffstatshomepage
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/hircine/api/query/__init__.py2
-rw-r--r--src/hircine/api/query/resolvers.py29
-rw-r--r--src/hircine/api/responses.py30
-rw-r--r--src/hircine/db/ops.py8
4 files changed, 68 insertions, 1 deletions
diff --git a/src/hircine/api/query/__init__.py b/src/hircine/api/query/__init__.py
index 2e07c71..7bc4b7d 100644
--- a/src/hircine/api/query/__init__.py
+++ b/src/hircine/api/query/__init__.py
@@ -24,6 +24,7 @@ from .resolvers import (
every,
scrape_comic,
single,
+ statistics,
)
@@ -52,3 +53,4 @@ class Query:
world: rp.WorldResponse = query(single(models.World))
worlds: FilterResult[World] = query(every(models.World))
scrape_comic: rp.ScrapeComicResponse = query(scrape_comic)
+ statistics: rp.Statistics = query(statistics)
diff --git a/src/hircine/api/query/resolvers.py b/src/hircine/api/query/resolvers.py
index 6609cc1..389a200 100644
--- a/src/hircine/api/query/resolvers.py
+++ b/src/hircine/api/query/resolvers.py
@@ -10,10 +10,13 @@ import hircine.plugins as plugins
from hircine.api.filters import Input as FilterInput
from hircine.api.inputs import Pagination
from hircine.api.responses import (
+ ComicTotals,
IDNotFoundError,
ScraperError,
ScraperNotAvailableError,
ScraperNotFoundError,
+ Statistics,
+ Totals,
)
from hircine.api.sort import Input as SortInput
from hircine.api.types import (
@@ -144,3 +147,29 @@ async def scrape_comic(id: int, scraper: str):
)
except ScrapeError as e:
return ScraperError(error=str(e))
+
+
+async def statistics():
+ async with db.session() as s:
+ total = Totals(
+ archives=await ops.count(s, models.Archive),
+ artists=await ops.count(s, models.Artist),
+ characters=await ops.count(s, models.Character),
+ circles=await ops.count(s, models.Circle),
+ comic=ComicTotals(
+ artists=await ops.count(s, models.ComicArtist),
+ characters=await ops.count(s, models.ComicCharacter),
+ circles=await ops.count(s, models.ComicCircle),
+ tags=await ops.count(s, models.ComicTag),
+ worlds=await ops.count(s, models.ComicWorld),
+ ),
+ comics=await ops.count(s, models.Comic),
+ images=await ops.count(s, models.Image),
+ namespaces=await ops.count(s, models.Namespace),
+ pages=await ops.count(s, models.Page),
+ scrapers=len(plugins.get_scrapers()),
+ tags=await ops.count(s, models.Tag),
+ worlds=await ops.count(s, models.World),
+ )
+
+ return Statistics(total=total)
diff --git a/src/hircine/api/responses.py b/src/hircine/api/responses.py
index 99d5113..883705b 100644
--- a/src/hircine/api/responses.py
+++ b/src/hircine/api/responses.py
@@ -147,6 +147,36 @@ class ScraperNotAvailableError(Error):
return f"Scraper {self.scraper} not available for comic ID {self.comic_id}"
+@strawberry.type
+class ComicTotals:
+ artists: int
+ characters: int
+ circles: int
+ tags: int
+ worlds: int
+
+
+@strawberry.type
+class Totals:
+ archives: int
+ artists: int
+ characters: int
+ circles: int
+ comics: int
+ comic: ComicTotals
+ images: int
+ namespaces: int
+ pages: int
+ scrapers: int
+ tags: int
+ worlds: int
+
+
+@strawberry.type
+class Statistics:
+ total: Totals
+
+
AddComicResponse = Annotated[
Union[
AddComicSuccess,
diff --git a/src/hircine/db/ops.py b/src/hircine/db/ops.py
index 91c830d..8cc5ddc 100644
--- a/src/hircine/db/ops.py
+++ b/src/hircine/db/ops.py
@@ -1,7 +1,7 @@
import random
from collections import defaultdict
-from sqlalchemy import delete, func, null, select, text, tuple_
+from sqlalchemy import delete, func, literal_column, null, select, text, tuple_
from sqlalchemy.orm import contains_eager, undefer
from sqlalchemy.orm.util import identity_key
from strawberry import UNSET
@@ -204,3 +204,9 @@ async def delete_all(session, model, ids):
result = await session.execute(delete(model).where(model.id.in_(ids)))
return result.rowcount
+
+
+async def count(session, model):
+ sql = select(func.count(literal_column("1"))).select_from(model)
+
+ return (await session.execute(sql)).scalar_one()