load topic parents

This commit is contained in:
knst-kotov 2021-12-12 16:00:38 +03:00
parent 5b6545536f
commit 04f2ceb629
5 changed files with 58 additions and 24 deletions

View File

@ -2,7 +2,7 @@ from orm.rbac import Operation, Resource, Permission, Role, RoleStorage
from orm.community import Community
from orm.user import User, UserRating, UserRole, UserStorage
from orm.message import Message
from orm.topic import Topic, TopicSubscription
from orm.topic import Topic, TopicSubscription, TopicStorage
from orm.notification import Notification
from orm.shout import Shout, ShoutAuthor, ShoutTopic, ShoutRating, ShoutViewByDay,\
ShoutRatingStorage, ShoutViewStorage
@ -23,3 +23,4 @@ with local_session() as session:
ShoutViewStorage.init(session)
RoleStorage.init(session)
UserStorage.init(session)
TopicStorage.init(session)

View File

@ -3,6 +3,8 @@ from sqlalchemy import Table, Column, Integer, String, ForeignKey, DateTime, JSO
from sqlalchemy.orm import relationship
from orm.base import Base
import asyncio
class TopicSubscription(Base):
__tablename__ = "topic_subscription"
@ -22,3 +24,48 @@ class Topic(Base):
pic: str = Column(String, nullable=True, comment="Picture")
children = Column(JSONType, nullable=True, comment="list of children topics")
community = Column(ForeignKey("community.slug"), nullable=False, comment="Community")
class TopicStorage:
topics = {}
lock = asyncio.Lock()
@staticmethod
def init(session):
self = TopicStorage
topics = session.query(Topic)
self.topics = dict([(topic.slug, topic) for topic in topics])
for topic in self.topics.values():
self.load_parents(topic)
@staticmethod
def load_parents(topic):
self = TopicStorage
parents = []
for parent in self.topics.values():
if topic.slug in parent.children:
parents.append(parent.slug)
topic.parents = parents
return topic
@staticmethod
async def get_topics(slugs):
self = TopicStorage
async with self.lock:
if not slugs:
return self.topics.values()
topics = filter(lambda topic: topic.slug in slugs, self.topics.values())
return list(topics)
@staticmethod
async def get_topics_by_community(community):
self = TopicStorage
async with self.lock:
topics = filter(lambda topic: topic.community == community, self.topics.values())
return list(topics)
@staticmethod
async def add_topic(topic):
self = TopicStorage
async with self.lock:
self.topics[topic.slug] = topic
self.load_parents(topic)

View File

@ -4,7 +4,7 @@ from resolvers.zine import create_shout, get_shout_by_slug, top_month, top_overa
recent_shouts, top_authors, top_viewed
from resolvers.profile import get_users_by_slugs, get_current_user
from resolvers.topics import topic_subscribe, topic_unsubscribe, topics_by_author, \
topics_by_community, topics_by_slugs, topics_all
topics_by_community, topics_by_slugs
from resolvers.comments import create_comment
from resolvers.community import create_community, delete_community, get_community, get_communities
@ -27,7 +27,6 @@ __all__ = [
"top_month",
"top_overall",
"top_viewed",
"topics_all",
"topics_by_slugs",
"topics_by_community",
"topics_by_author",

View File

@ -1,41 +1,29 @@
from orm import Topic, TopicSubscription, Shout, User
from orm import Topic, TopicSubscription, TopicStorage, Shout, User
from orm.base import local_session
from resolvers.base import mutation, query, subscription
from resolvers.zine import ShoutSubscriptions
from auth.authenticate import login_required
import asyncio
@query.field("topicsAll")
async def topics_all(_, info):
topics = []
with local_session() as session:
topics = session.query(Topic)
return topics
@query.field("topicsBySlugs")
async def topics_by_slugs(_, info, slugs):
topics = []
async def topics_by_slugs(_, info, slugs = None):
with local_session() as session:
topics = session.query(Topic).filter(Topic.slug.in_(slugs))
return topics
return await TopicStorage.get_topics(slugs)
@query.field("topicsByCommunity")
async def topics_by_community(_, info, community):
topics = []
with local_session() as session:
topics = session.query(Topic).filter(Topic.community == community)
return topics
return await TopicStorage.get_topics_by_community(community)
@query.field("topicsByAuthor")
async def topics_by_author(_, info, author):
topics = {}
slugs = set()
with local_session() as session:
shouts = session.query(Shout).\
filter(Shout.authors.any(User.slug == author))
for shout in shouts:
topics.update(dict([(topic.slug, topic) for topic in shout.topics]))
return topics.values()
slugs.update([topic.slug for topic in shout.topics])
return await TopicStorage.get_topics(slugs)
@mutation.field("topicSubscribe")
@login_required

View File

@ -151,8 +151,7 @@ type Query {
topAuthors(limit: Int): [User]!
# topics
topicsAll: [Topic]!
topicsBySlugs(slugs: [String]!): [Topic]!
topicsBySlugs(slugs: [String]): [Topic]!
topicsByCommunity(community: String!): [Topic]!
topicsByAuthor(author: String!): [Topic]!