How to Build an Achievements Feature

Your team wants achievements. Track user progress. Award badges for milestones. Display completion status. Seems straightforward. Three weeks later, you're debugging why some users didn't get achievements they qualified for, handling backdating for new achievements, and optimizing queries that check completion criteria for every user action.
Achievement systems appear simple until you implement them at scale. The core concept (recognize milestone completion) hides complexity. When do you check if achievements are complete? How do you handle users who qualified before the achievement existed? What about achievements that require checking historical data across multiple metrics?
Trophy handles achievement systems including completion logic, progress tracking, and backdating. The complete implementation guide walks through the full process. Integration takes 1 day to 1 week. But understanding what building from scratch involves helps you make informed build versus buy decisions.
Key Points
- Technical challenges in achievement system implementation
- Completion checking patterns that scale
- Backdating strategies for fairness
- Integration examples with Trophy's API
- Build versus buy considerations for achievement features
The Technical Reality
Before building achievement systems, understand the problems beyond simple milestone tracking.
Completion checking logic needs efficiency at scale. Checking every achievement on every user action kills performance. You need smart triggering that only checks relevant achievements. Building this trigger system takes time.
Progress tracking for multi-step achievements adds complexity. "Complete 100 tasks" needs counting. Showing users "45/100" requires storing partial progress. Updating this efficiently as users act requires careful database design.
Backdating ensures fairness when you add new achievements. Users who qualified before the achievement existed should complete it automatically. Scanning historical data for every user takes time. Getting this right without overloading your database is tricky.
Badge hosting and delivery seems minor but adds infrastructure. Where do badge images live? How do you serve them efficiently? What formats work across platforms? These details accumulate.
Rarity calculations show how many users completed each achievement. This requires counting completions across your entire user base and keeping these counts updated as more users complete achievements.
Building production-ready achievement systems typically takes 3-5 weeks including completion logic, progress tracking, and backdating. Trophy's infrastructure handles these problems, reducing implementation to integration work.
Architecture Patterns
If building in-house, these patterns avoid common mistakes.
Event-based checking triggers achievement evaluation only when relevant events occur. Store achievement triggers. When events arrive, check only achievements that could complete based on that event type. This scales better than checking all achievements on every action.
Incremental progress updates maintain partial completion state. Store "tasks completed: 45" instead of recalculating from history on every check. Update incrementally as users act. Trophy uses this pattern for efficient progress tracking.
Async backdating processes achievement qualification in background jobs. When you create an achievement, queue a job that scans historical data and awards to qualified users. Don't block achievement creation on backdating completion.
Denormalized completion state stores which users completed which achievements in fast-access storage. Recompute from history only when needed. Trophy maintains completion state with millisecond query latency.
Trigger mapping links achievement requirements to specific events. Achievement requires metric X reaching value Y, so only check it when metric X events arrive. Trophy's configuration system includes this trigger mapping automatically.
Trophy implements these patterns. You configure achievement criteria. Trophy handles the infrastructure complexity.
Implementation Estimate
Here's realistic timeline for building achievements in-house:
Week 1: Basic implementation. Create achievements. Track completions. Display badges. Works in development with simple achievements.
Week 2: Progress tracking. Store partial progress for multi-step achievements. Update progress efficiently. Show users their advancement toward incomplete achievements.
Week 3: Completion logic. Build trigger system that checks relevant achievements on user actions. Optimize to avoid checking irrelevant achievements. Handle achievement criteria complexity.
Week 4: Backdating and edge cases. Implement fair backdating for new achievements. Handle concurrent completion attempts. Test with realistic data volumes.
Ongoing: Maintenance and expansion. New achievements need adding regularly. Badge management continues. Performance tuning as usage scales.
That's 4+ weeks of engineering time plus ongoing maintenance. Trophy's infrastructure eliminates this timeline, reducing implementation to 1 day to 1 week of integration work.
Building with Trophy
Trophy's integration is faster because achievement infrastructure already exists. Here's what implementation looks like.
Step 1: Create Achievements
In Trophy's dashboard, create achievements with:
- Name and description
- Badge image (Trophy hosts this for you)
- Trigger type (metric-based, API-based, or streak-based)
- Completion criteria
For metric achievements, specify which metric and what threshold completes the achievement. Trophy automatically tracks progress and awards completion when users reach the threshold.
Managing achievements online means future additions or changes happen in the dashboard and not in your codebase, preventing back and forth changes.
Step 2: Track User Actions
Send events to Trophy when users perform achievement-relevant actions:
import { TrophyApiClient } from '@trophyso/node';
const trophy = new TrophyApiClient(process.env.TROPHY_API_KEY);
// When user completes a task
const response = await trophy.metrics.event('tasks_completed', {
user: {
id: 'user-123'
},
value: 1
});
// Check if user completed any achievements
if (response.achievements && response.achievements.length > 0) {
response.achievements.forEach(achievement => {
console.log(`Unlocked: ${achievement.name}`);
console.log(`Badge: ${achievement.badgeUrl}`);
showAchievementNotification(achievement);
});
}
Trophy processes events and automatically checks if any achievements should complete. The response includes newly completed achievements for immediate user feedback.
Step 3: Display User Achievements
Fetch achievements a user has completed:
// Get user's completed achievements
const achievements = await trophy.users.achievements('user-123', {
includeIncomplete: 'false' // Only show completed
});
achievements.forEach(achievement => {
console.log({
name: achievement.name,
description: achievement.description,
badgeUrl: achievement.badgeUrl,
completedAt: achievement.achievedAt,
rarity: achievement.rarity // Percentage of users who completed it
});
});
Trophy returns achievement data including badges, completion timestamps, and rarity statistics. The achievements API documentation covers all available fields.
Step 4: Show Achievement Progress
For incomplete achievements, show progress toward completion:
// Get all achievements including incomplete ones with progress
const allAchievements = await trophy.users.achievements('user-123', {
includeIncomplete: 'true'
});
allAchievements.forEach(achievement => {
if (achievement.achievedAt) {
// Completed
console.log(`✓ ${achievement.name}`);
} else {
// Incomplete - show progress if available
if (achievement.progress) {
const percent = (achievement.progress.current / achievement.progress.target) * 100;
console.log(`${achievement.name}: ${percent}% complete`);
}
}
});
Trophy tracks progress for metric-based achievements automatically. Users see how close they are to completion.
Step 5: Complete API Achievements
For achievements that can't be automatically tracked via metrics (completing onboarding, linking accounts, etc.), use the complete achievement API:
// When user completes onboarding
await trophy.achievements.complete('user-123', 'onboarding_complete');
// Trophy marks it as complete and returns achievement data
const result = await trophy.achievements.complete('user-123', 'onboarding_complete');
if (result.achievement) {
console.log(`Completed: ${result.achievement.name}`);
showAchievementNotification(result.achievement);
}
This gives you control over when achievements complete for events Trophy can't track automatically.
Achievement Types and Strategies
Different achievement structures serve different product goals. Understanding when your app needs achievements helps you design effective systems.
Metric achievements track cumulative actions. "Complete 100 tasks" or "View 50 lessons." These recognize consistent usage and progress toward mastery. Trophy's metric system tracks these automatically.
Streak achievements recognize consistency. "Maintain a 30-day streak" celebrates sustained engagement. Trophy's streak tracking makes these simple to implement.
API achievements recognize specific one-time events. "Complete onboarding" or "Link social account." You trigger these manually when appropriate events occur.
Tiered achievements create progression. Bronze (10 tasks), silver (50 tasks), gold (100 tasks). Users see clear advancement path. Trophy's metric thresholds support tiered structures naturally.
Hidden achievements surprise users through discovery. Don't show them until completed.
Mix achievement types to serve different user motivations and engagement patterns.
Designing Achievement Structures
Effective achievement design requires understanding user psychology and product goals. Designing achievements for optimal engagement explores strategic frameworks for achievement creation.
Accessibility balance matters. Some achievements should be easy (first task completed) for quick wins. Others should be challenging (1,000 tasks completed) for long-term goals. Trophy's analytics show completion rates helping you tune difficulty.
Progressive revelation prevents overwhelming new users. Show basic achievements upfront. Reveal advanced achievements as users progress. Trophy's achievement system supports controlling visibility.
Meaningful milestones align with user goals. Achievements should recognize progress users care about, not arbitrary metrics. Trophy's flexible metric system lets you track what matters for your product.
Rarity indicators show prestige. "Only 5% of users have completed this" motivates completion. Trophy automatically calculates and displays rarity statistics.
Backdating Logic
When you create new achievements, users who already qualified should complete them automatically. Trophy handles this through backdating.
When you activate an achievement in Trophy:
- Trophy scans historical data for users who meet completion criteria
- Awards the achievement to qualified users with original completion timestamp
- Updates completion counts and rarity statistics
- Processes in background without blocking achievement activation
This ensures fairness without requiring manual intervention. Users who completed 100 tasks before that achievement existed get credit when you launch it.
Your code doesn't change. Trophy handles backdating automatically based on achievement configuration.
Notification Strategy
Achievement completions need communication without overwhelming users. Trophy's email system handles notification timing.
Configure achievement emails in Trophy's dashboard:
- When to send (immediately, batched, specific times)
- Email content and design
- Which achievements trigger emails
Trophy sends notifications automatically when users complete achievements. No manual email logic needed in your code.
// Trophy handles notifications automatically
// Your code just tracks events
await trophy.metrics.event('tasks_completed', {
user: { id: 'user-123' },
value: 1
});
// If user completes achievement, Trophy sends configured emails
Performance Considerations
Trophy's infrastructure is built for scale, but your integration patterns affect performance.
Check achievements server-side only. Don't query achievement status on every page load. Cache achievement data and refresh periodically or after user actions.
Cache completion state for display-heavy scenarios. Achievement lists don't need real-time accuracy. Cache for 5-10 minutes:
const cache = new Map();
async function getCachedAchievements(userId: string) {
const cached = cache.get(userId);
if (cached && Date.now() - cached.timestamp < 300000) {
return cached.data;
}
const fresh = await trophy.users.achievements(userId);
cache.set(userId, { data: fresh, timestamp: Date.now() });
return fresh;
}
Trophy handles backend scaling. These client-side patterns optimize your application's performance.
Analytics and Tuning
Trophy provides analytics for achievement system health.
Completion rates show whether achievements are appropriately difficult. Trophy's dashboard shows what percentage of users complete each achievement. Aim for variety: some easy (60%+), some moderate (30-60%), some difficult (5-30%).
Completion velocity reveals how long achievements take. If most users complete an achievement within days of starting, it might be too easy. If it takes months on average, consider whether it's appropriately challenging or frustratingly difficult.
Rarity distribution shows whether you have enough aspirational achievements. If all achievements have 40-60% completion, you might need harder goals for engaged users.
Abandonment patterns indicate where users give up. If users progress halfway toward an achievement then stop, the difficulty curve might be wrong or the achievement might not be compelling.
Use these insights to refine achievement thresholds and create new achievements that fill gaps. Trophy's dashboard configuration makes adjustments quick without code changes.
Common Implementation Mistakes
Teams integrating Trophy make predictable errors.
Too many achievements at launch. Start with 10-15 achievements covering basic to advanced milestones. Add more based on completion data. Trophy makes adding achievements easy, so start focused.
Ignoring completion data. If achievements never get completed, they're too hard or unclear. Trophy shows completion rates. Use this data to retire ineffective achievements.
Generic achievement design. Copy-pasting achievement structures from other products without adapting creates disconnected systems. Trophy provides flexible tools, but you need product-specific strategy.
No progression structure. Random achievements at similar difficulty don't create growth paths. Trophy's tiered metric achievements support clear progression from beginner to expert.
Blocking user flows on Trophy responses. Trophy is fast, but don't block critical user actions waiting for achievement checks. Process events asynchronously when possible.
Build vs. Buy Decision
Here's how to think about build versus buy for achievements:
Build in-house when:
- Your achievement mechanics are so unusual platforms don't support them
- You have backend engineers with capacity for 2-3 months plus maintenance
- Engineering control over infrastructure is critical
- Scale is small enough that simple implementations work (under 1,000 users)
Use Trophy when:
- You want achievements in days, not months
- Backdating and progress tracking need to work correctly
- Engineering time is better spent on core features
- Badge hosting and rarity calculations aren't core to your business
Trophy's implementation guide covers the complete integration process. Most teams implement basic achievements in 1-2 days, advanced multi-tiered structures in 3-5 days. Compare this to 2-3 months building from scratch.
FAQ
How long does Trophy integration take for achievements?
Basic achievement tracking: 1-2 days including dashboard configuration and event integration. Advanced features like complex progress tracking and tiered structures: 3-5 days. Compare this to 2-3 months building in-house.
How does backdating work?
Trophy automatically awards new achievements to users who already qualified based on historical data. This happens in background when you activate achievements. Users receive credit without manual intervention.
Can we adjust achievement criteria after launch?
Carefully. Changing requirements after users have started working toward achievements can frustrate them. Trophy supports adjusting thresholds through configuration, but communicate changes clearly to users.
What if we want achievements to expire?
Trophy's achievements are permanent once completed. For time-limited challenges, consider using time-bounded leaderboards or seasonal competitions instead.
How do we prevent users from gaming achievements?
Design achievements around meaningful actions that are hard to fake. Trophy's event tracking includes your authentication, so users must be properly authenticated. Avoid achievements based purely on time or button clicks.
Can we have secret/hidden achievements?
Yes. Trophy supports marking achievements as hidden until completion. Users discover them through gameplay without seeing them in their achievement list beforehand.
What happens if Trophy's API goes down?
Design your integration to degrade gracefully. Queue events for retry. Show cached achievement data. Most teams find Trophy's uptime exceeds what they'd achieve with in-house infrastructure.
Trophy is gamification infrastructure that retains users.
Gamification infrastructure that retains users.
Gamification APIs for web and mobile
Free up to 100 users. No CC required.
Get updates
Stay in the loop with all things gamification.