Skip to content

Commit

Permalink
Cache the games aggregation pipeline to optimize search
Browse files Browse the repository at this point in the history
  • Loading branch information
MattBSG committed Jun 18, 2024
1 parent 62597e1 commit 7c0fb29
Showing 1 changed file with 28 additions and 26 deletions.
54 changes: 28 additions & 26 deletions modules/games.py
Original file line number Diff line number Diff line change
Expand Up @@ -124,6 +124,32 @@ def __init__(self, bot):
self.db.create_index([("guid", pymongo.ASCENDING)], unique=True)
self.db.create_index([("game.id", pymongo.ASCENDING)])

# Generate the pipeline
self.pipeline = [
{'$match': {'_type': 'game'}}, # Select games
{
'$graphLookup': {
'from': 'games',
'startWith': '$id',
'connectFromField': 'id',
'connectToField': 'game.id',
'as': '_releases',
'restrictSearchWithMatch': {'_type': 'release'},
}
}, # Search for releases from 'id' to release 'game.id' field, and add as '_releases'
{
'$project': {
'guid': 1,
'name': 1,
'aliases': 1,
'original_release_date': 1,
'_releases.name': 1,
'_releases.release_date': 1,
}
}, # Filter to only stuff we want
]
self.aggregatePipeline = list(self.db.aggregate(self.pipeline))

if AUTO_SYNC:
self.sync_db.start() # pylint: disable=no-member

Expand Down Expand Up @@ -171,6 +197,7 @@ async def sync_db(self, force_full: bool = False) -> Tuple[int, str]:
'count': count,
'running': False,
}
self.aggregatePipeline = list(self.db.aggregate(self.pipeline))

return count, detail_str

Expand Down Expand Up @@ -199,32 +226,7 @@ def update_item_in_db(self, type: Literal['game', 'release'], game: dict):

def search(self, query: str) -> Optional[dict]:
match = {'guid': None, 'score': None, 'name': None}

pipeline = [
{'$match': {'_type': 'game'}}, # Select games
{
'$graphLookup': {
'from': 'games',
'startWith': '$id',
'connectFromField': 'id',
'connectToField': 'game.id',
'as': '_releases',
'restrictSearchWithMatch': {'_type': 'release'},
}
}, # Search for releases from 'id' to release 'game.id' field, and add as '_releases'
{
'$project': {
'guid': 1,
'name': 1,
'aliases': 1,
'original_release_date': 1,
'_releases.name': 1,
'_releases.release_date': 1,
}
}, # Filter to only stuff we want
]

for game in self.db.aggregate(pipeline):
for game in self.aggregatePipeline:
names = collections.Counter([game['name']])
if game['aliases']:
names.update(game['aliases'])
Expand Down

0 comments on commit 7c0fb29

Please sign in to comment.