diff --git a/src/db/functions/achievementFunctions.ts b/src/db/functions/achievementFunctions.ts index 30cbc3b..7d3ee6a 100644 --- a/src/db/functions/achievementFunctions.ts +++ b/src/db/functions/achievementFunctions.ts @@ -129,7 +129,6 @@ export async function updateAchievementProgress( ): Promise { try { await ensureDbInitialized(); - if (!db) { console.error( 'Database not initialized, cannot update achievement progress', @@ -149,21 +148,15 @@ export async function updateAchievementProgress( .then((rows) => rows[0]); if (existing) { - if (existing.earnedAt) { - return false; - } - await db .update(schema.userAchievementsTable) - .set({ - progress: Math.floor(progress) > 100 ? 100 : Math.floor(progress), - }) + .set({ progress }) .where(eq(schema.userAchievementsTable.id, existing.id)); } else { await db.insert(schema.userAchievementsTable).values({ discordId: userId, - achievementId: achievementId, - progress: Math.floor(progress) > 100 ? 100 : Math.floor(progress), + achievementId, + progress, }); } diff --git a/src/util/achievementManager.ts b/src/util/achievementManager.ts index d780545..aaf3a05 100644 --- a/src/util/achievementManager.ts +++ b/src/util/achievementManager.ts @@ -34,15 +34,13 @@ async function handleProgress( (a) => a.achievementId === achievement.id && a.earnedAt !== null, ); - if (progress >= 100) { - if (!existing && !skipAward) { - const awarded = await awardAchievement(userId, achievement.id); - if (awarded && guild) { - await announceAchievement(guild, userId, achievement); - } + await updateAchievementProgress(userId, achievement.id, progress); + + if (progress === 100 && !existing && !skipAward) { + const awarded = await awardAchievement(userId, achievement.id); + if (awarded && guild) { + await announceAchievement(guild, userId, achievement); } - } else { - await updateAchievementProgress(userId, achievement.id, progress); } } @@ -107,8 +105,23 @@ export async function processCommandAchievements( (a.requirement as any).command === commandName, ); + // fetch the user’s current achievement entries + const userAchievements = await getUserAchievements(userId); + for (const ach of commandAchievements) { - await handleProgress(userId, guild, ach, 100); + // find existing progress, default to 0 + const userAch = userAchievements.find((u) => u.achievementId === ach.id); + const oldProgress = userAch?.progress ?? 0; + + // compute how many times they've run this command so far + const timesRanSoFar = (oldProgress / 100) * ach.threshold; + const newCount = timesRanSoFar + 1; + + // convert back into a percentage + const newProgress = Math.min(100, (newCount / ach.threshold) * 100); + + // Delegate to handleProgress which will update or award + await handleProgress(userId, guild, ach, newProgress); } }