Skip to content
This repository has been archived by the owner on Dec 15, 2024. It is now read-only.

Commit

Permalink
feat: implement filters
Browse files Browse the repository at this point in the history
  • Loading branch information
ArtemSBulgakov committed Nov 22, 2024
1 parent 2d17897 commit 0fb1209
Show file tree
Hide file tree
Showing 3 changed files with 71 additions and 3 deletions.
53 changes: 53 additions & 0 deletions backend/src/modules/events/repository.py
Original file line number Diff line number Diff line change
@@ -1,5 +1,9 @@
__all__ = ["events_repository"]

from beanie import SortDirection
from beanie.odm.operators.find.comparison import In

from src.modules.events.schemas import Filters, Pagination, Sort
from src.storages.mongo.events import Event


Expand All @@ -17,5 +21,54 @@ async def create_many(self, events: list[Event]) -> bool:
return False
return True

async def read_with_filters(self, filters: Filters, sort: Sort, pagination: Pagination) -> list[Event]:
query = Event.all()

# Apply filters
if filters.age and filters.age.min is not None:
query = query.find(Event.age_max >= filters.age.min)
if filters.age and filters.age.max is not None:
query = query.find(Event.age_min <= filters.age.max)
if filters.participant_count and filters.participant_count.min is not None:
query = query.find(Event.participant_count >= filters.participant_count.min)
if filters.participant_count and filters.participant_count.max is not None:
query = query.find(Event.participant_count <= filters.participant_count.max)
if filters.gender is not None:
query = query.find(Event.gender == filters.gender)
if filters.date and filters.date.start_date is not None:
query = query.find(Event.start_date >= filters.date.start_date)
if filters.date and filters.date.end_date is not None:
query = query.find(Event.end_date <= filters.date.end_date)
if filters.discipline:
# FIXME: Может работать неверно, если у указанных спортов есть одинаковые названия дисциплин
query = query.find(In(Event.sport, [discipline.sport for discipline in filters.discipline]))
query = query.find(In(Event.discipline, [discipline.discipline for discipline in filters.discipline]))
if filters.location:
# TODO: Проверить
query = query.find(In(Event.location, filters.location))
if filters.query:
query = query.find({"$text": {"$search": filters.query}})

# Apply sorting
if sort.date:
query = query.sort(
("start_date", SortDirection.ASCENDING if sort.date == "asc" else SortDirection.DESCENDING)
)
if sort.participant_count:
query = query.sort(
(
"participant_count",
SortDirection.ASCENDING if sort.participant_count == "asc" else SortDirection.DESCENDING,
)
)
if sort.age:
query = query.sort(("age_min", SortDirection.ASCENDING if sort.age == "asc" else SortDirection.DESCENDING))

# Apply pagination
query = query.skip(pagination.page_size * (pagination.page_no - 1)).limit(pagination.page_size)

# Return results
return await query.to_list()


events_repository: EventsRepository = EventsRepository()
4 changes: 2 additions & 2 deletions backend/src/modules/events/routes.py
Original file line number Diff line number Diff line change
Expand Up @@ -62,12 +62,12 @@ async def search_events(filters: Filters, sort: Sort, pagination: Pagination) ->
"""
Search events.
"""
events = await events_repository.read_all()
events = await events_repository.read_with_filters(filters, sort, pagination)
return SearchEventsResponse(
filters=filters,
sort=sort,
pagination=pagination,
page=1,
page=pagination.page_no,
pages_total=1,
events=events,
)
Expand Down
17 changes: 16 additions & 1 deletion backend/src/storages/mongo/events.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,9 @@

import datetime

import pymongo
from pymongo import IndexModel

from src.modules.events.schemas import Gender
from src.pydantic_base import BaseSchema
from src.storages.mongo.__base__ import CustomDocument
Expand Down Expand Up @@ -50,4 +53,16 @@ class EventSchema(BaseSchema):

class Event(EventSchema, CustomDocument):
class Settings:
pass
indexes = [
IndexModel(
[
("title", pymongo.TEXT),
("sport", pymongo.TEXT),
("location.country", pymongo.TEXT),
("location.region", pymongo.TEXT),
("location.city", pymongo.TEXT),
],
default_language="russian",
name="text_index",
),
]

0 comments on commit 0fb1209

Please sign in to comment.