From 6ed09d5851983bbf84183bcaed0cf087224fe88c Mon Sep 17 00:00:00 2001 From: Untone Date: Fri, 23 Feb 2024 04:08:29 +0300 Subject: [PATCH] reverte --- resolvers/author.py | 4 ++-- resolvers/follower.py | 49 ++++++++++++++++++++++++++++++------------- resolvers/stat.py | 6 +++--- 3 files changed, 39 insertions(+), 20 deletions(-) diff --git a/resolvers/author.py b/resolvers/author.py index 181e5c4a..c228c9ca 100644 --- a/resolvers/author.py +++ b/resolvers/author.py @@ -10,7 +10,7 @@ from orm.reaction import Reaction, ReactionKind from orm.shout import Shout, ShoutAuthor, ShoutTopic from orm.topic import Topic from resolvers.follower import query_follows -from resolvers.stat import get_authors_with_stat, unpack_stat +from resolvers.stat import get_authors_with_stat, execute_with_ministat from services.auth import login_required from services.db import local_session from services.rediscache import redis @@ -295,4 +295,4 @@ def get_author_followers(_, _info, slug): .group_by(author_alias.id) ) - return unpack_stat(q) + return execute_with_ministat(q) diff --git a/resolvers/follower.py b/resolvers/follower.py index 810c744b..7b116d5b 100644 --- a/resolvers/follower.py +++ b/resolvers/follower.py @@ -2,7 +2,7 @@ import json import time from typing import List -from sqlalchemy import select, or_ +from sqlalchemy import select, or_, func from sqlalchemy.orm import aliased from sqlalchemy.sql import and_ @@ -10,11 +10,11 @@ from orm.author import Author, AuthorFollower # from orm.community import Community from orm.reaction import Reaction -from orm.shout import Shout, ShoutReactionsFollower +from orm.shout import Shout, ShoutReactionsFollower, ShoutAuthor, ShoutTopic from orm.topic import Topic, TopicFollower from resolvers.community import community_follow, community_unfollow from resolvers.topic import topic_follow, topic_unfollow -from resolvers.stat import get_topics_with_stat, get_authors_with_stat +from resolvers.stat import get_authors_with_stat from services.auth import login_required from services.db import local_session from services.follows import DEFAULT_FOLLOWS @@ -95,24 +95,43 @@ def query_follows(user_id: str): if isinstance(author, Author): author_id = author.id aliased_author = aliased(Author) + aliased_author_followers = aliased(AuthorFollower) + aliased_author_authors = aliased(AuthorFollower) - authors_query = ( - session.query(aliased_author, AuthorFollower) - .select_from(aliased_author) # явное указание FROM-запроса - .join(AuthorFollower, AuthorFollower.follower == author_id) + authors = ( + session.query( + aliased_author, + func.count(func.distinct(ShoutAuthor.shout)).label("shouts_stat"), + func.count(func.distinct(AuthorFollower.author)).label("authors_stat"), + func.count(func.distinct(AuthorFollower.follower)).label("followers_stat") + ) .filter(AuthorFollower.author == aliased_author.id) + .join(AuthorFollower, AuthorFollower.follower == aliased_author.id) + .outerjoin(ShoutAuthor, ShoutAuthor.author == author_id) + .outerjoin(aliased_author_authors, AuthorFollower.follower == author_id) + .outerjoin(aliased_author_followers, AuthorFollower.author == author_id) + .group_by(aliased_author.id) + .all() ) - topics_query = ( - session.query(Topic, TopicFollower) - .select_from(Topic) # явное указание FROM-запроса - .join(TopicFollower, TopicFollower.follower == author_id) - .filter(TopicFollower.topic == Topic.id) + aliased_shout_authors = aliased(ShoutAuthor) + aliased_topic_followers = aliased(TopicFollower) + aliased_topic = aliased(Topic) + topics = ( + session.query( + aliased_topic, + func.count(func.distinct(ShoutTopic.shout)).label("shouts_stat"), + func.count(func.distinct(ShoutAuthor.author)).label("authors_stat"), + func.count(func.distinct(TopicFollower.follower)).label("followers_stat") + ) + .join(TopicFollower, TopicFollower.topic == aliased_topic.id) + .outerjoin(ShoutTopic, aliased_topic.id == ShoutTopic.topic) + .outerjoin(aliased_shout_authors, ShoutTopic.shout == aliased_shout_authors.shout) + .outerjoin(aliased_topic_followers, aliased_topic_followers.topic == aliased_topic.id) + .group_by(aliased_topic.id) + .all() ) - authors = get_authors_with_stat(authors_query) - topics = get_topics_with_stat(topics_query) - return { 'topics': topics, 'authors': authors, diff --git a/resolvers/stat.py b/resolvers/stat.py index a6944490..d0e7e0bc 100644 --- a/resolvers/stat.py +++ b/resolvers/stat.py @@ -43,7 +43,7 @@ def add_author_stat_columns(q): return q -def unpack_stat(q): +def execute_with_ministat(q): records = [] with local_session() as session: for [entity, shouts_stat, authors_stat, followers_stat] in session.execute(q): @@ -59,9 +59,9 @@ def unpack_stat(q): def get_authors_with_stat(q): q = add_author_stat_columns(q) - return unpack_stat(q) + return execute_with_ministat(q) def get_topics_with_stat(q): q = add_topic_stat_columns(q) - return unpack_stat(q) + return execute_with_ministat(q)