From 6e854b3cd6ce7f2da29e53606143730509d66b27 Mon Sep 17 00:00:00 2001 From: Wan Qi Chen <495709+wa0x6e@users.noreply.github.com> Date: Thu, 18 Jul 2024 13:51:06 +0900 Subject: [PATCH] fix: optimize query --- src/helpers/spaces.ts | 129 ++++++++++++++++++++++++++++++++++-------- 1 file changed, 104 insertions(+), 25 deletions(-) diff --git a/src/helpers/spaces.ts b/src/helpers/spaces.ts index aee43b4b..e256dc93 100644 --- a/src/helpers/spaces.ts +++ b/src/helpers/spaces.ts @@ -133,52 +133,131 @@ async function loadSpaces() { async function getProposals() { const ts = parseInt((Date.now() / 1e3).toFixed()); - const query = ` - SELECT space, COUNT(id) AS count, - COUNT(IF(start < ? AND end > ? AND flagged = 0, 1, NULL)) AS active, - count(IF(created > (UNIX_TIMESTAMP() - 604800), 1, NULL)) as count_7d - FROM proposals GROUP BY space + + const allActivitiesQuery = ` + SELECT + id, + proposal_count AS count + FROM spaces + `; + + const results = Object.fromEntries( + (await db.queryAsync(allActivitiesQuery)).map(({ id, count }) => [ + id, + { count, count_7d: 0, active: 0 } + ]) + ); + + const recentActivityQuery = ` + SELECT + space, + count(id) AS count + FROM proposals + WHERE created > (UNIX_TIMESTAMP() - 604800) + GROUP BY space + `; + + (await db.queryAsync(recentActivityQuery)).forEach(({ space, count }) => { + if (results[space]) results[space].count_7d = count; + }); + + const activeQuery = ` + SELECT + space, + count(id) AS count + FROM proposals + WHERE start < ? AND end > ? AND flagged = 0 + GROUP BY space `; - return await db.queryAsync(query, [ts, ts]); + + (await db.queryAsync(activeQuery, [ts, ts])).forEach(({ space, count }) => { + if (results[space]) results[space].active = count; + }); + + return results; } async function getVotes() { - const query = ` - SELECT space, COUNT(id) as count, - count(IF(created > (UNIX_TIMESTAMP() - 604800), 1, NULL)) as count_7d - FROM votes GROUP BY space + const allActivitiesQuery = ` + SELECT + id, + vote_count AS count + FROM spaces `; - return await db.queryAsync(query); + + const results = Object.fromEntries( + (await db.queryAsync(allActivitiesQuery)).map(({ id, count }) => [ + id, + { count, count_7d: 0 } + ]) + ); + + const recentActivityQuery = ` + SELECT + space, + count(id) AS count + FROM votes + WHERE created > (UNIX_TIMESTAMP() - 604800) + GROUP BY space + `; + + (await db.queryAsync(recentActivityQuery)).forEach(({ space, count }) => { + if (results[space]) results[space].count_7d = count; + }); + + return results; } async function getFollowers() { - const query = ` - SELECT space, COUNT(id) as count, - count(IF(created > (UNIX_TIMESTAMP() - 604800), 1, NULL)) as count_7d - FROM follows GROUP BY space + const allActivitiesQuery = ` + SELECT + id, + follower_count AS count + FROM spaces `; - return await db.queryAsync(query); + + const results = Object.fromEntries( + (await db.queryAsync(allActivitiesQuery)).map(({ id, count }) => [ + id, + { count, count_7d: 0 } + ]) + ); + + const recentActivityQuery = ` + SELECT + space, + count(id) AS count + FROM follows + WHERE created > (UNIX_TIMESTAMP() - 604800) + GROUP BY space + `; + + (await db.queryAsync(recentActivityQuery)).forEach(({ space, count }) => { + if (results[space]) results[space].count_7d = count; + }); + + return results; } async function loadSpacesMetrics() { const followersMetrics = await getFollowers(); - followersMetrics.forEach(followers => { - if (spaces[followers.space]) spaceFollowers[followers.space] = followers; - }); + for (const [space, metrics] of Object.entries(followersMetrics)) { + if (spaces[space]) spaceFollowers[space] = metrics; + } log.info('[spaces] Followers metrics loaded'); mapSpaces(); const proposalsMetrics = await getProposals(); - proposalsMetrics.forEach(proposals => { - if (spaces[proposals.space]) spaceProposals[proposals.space] = proposals; - }); + for (const [space, metrics] of Object.entries(proposalsMetrics)) { + if (spaces[space]) spaceProposals[space] = metrics; + } log.info('[spaces] Proposals metrics loaded'); mapSpaces(); const votesMetrics = await getVotes(); - votesMetrics.forEach(votes => { - if (spaces[votes.space]) spaceVotes[votes.space] = votes; - }); + for (const [space, metrics] of Object.entries(votesMetrics)) { + if (spaces[space]) spaceVotes[space] = metrics; + } log.info('[spaces] Votes metrics loaded'); mapSpaces(); }