Building a Dota 2 Dashboard: A Journey into Game Analytics
As a passionate Dota 2 player and developer, I’ve always been fascinated by the wealth of data available in the game. Recently, I embarked on a journey to create a custom dashboard.
Technical Implementation
The dashboard is built using modern web technologies, focusing on:
- Real-time data processing
- Interactive visualizations
- Responsive design for all devices
- Secure authentication for personal stats (soon)
- Integration with Dota 2’s OpenDota API
Key Features
- Match History Analysis
- Detailed breakdown of recent matches
- Win/loss trends
- Performance metrics per hero (soon)
Hero Statistics
- Win rates by hero
- Average KDA ratios
- Preferred roles and positions (soon)
Item

Profile

History Match

Getting Started
You can find the project on GitHub at PersonalD2 . Feel free to contribute, suggest features, or report issues.
Conclusion
Building this dashboard has been an exciting journey into both game analytics and web development.
Update
Personal Dota Dashboard
A personal Dota 2 stats dashboard in a pixel-arcade style. Sign in with Steam to see your win rate, your best heroes, a year of activity, and a breakdown of every match: how your farm, fights and skill build compared with your team and with the enemy who played your position.
What it shows
Dashboard
- Win rate across every match on record, as a health bar of wins and losses.
- Last match: hero, result, K/D/A and final items.
- Best heroes: your five most played, as floating cards coloured by each hero’s main attribute, with games and win rate.
- Activity: every day of the last year as one square, from red (lost every game) through orange (even) to green (won every game). Point at a day to see its games.
- Recent matches and a full, paged match history.
Match page
- The result, score, duration, mode and rank, the net worth lead minute by minute, how each lane went, and both drafts.
- Both teams as scoreboards. Open any player to see their game in six tabs:
- Overview: farm and impact totals, each ranked against the player’s own team, plus final items.
- Timeline: net worth by minute next to the enemy in the same position, with kills and deaths marked on the line, a slider through every purchase, and STRATZ’s impact rating minute by minute.
- Fights: when they killed and died, time spent dead, kill participation, damage by type, and stun, disable and slow time.
- Farm: where the gold came from, last hits per minute, gold spent versus unspent, and net worth at 10 and 20 minutes against the lane counterpart.
- Utility: wards placed (when, and which kind), camps stacked and runes.
- Skill build: every ability point by hero level, with talents and which ability was maxed first.
- A share card: the result as an image, ready to post.
Match summary
At the bottom of each of your matches, a summary of how you played:
- A verdict from the net worth story: a comeback, a stomp, a thrown lead or a slow slide.
- A grade (S to D) and five scores, each comparing you with the enemy in your position, where 50 means even. Cores are judged on farming, fighting, survival, pushing and impact; supports on fighting, survival, impact and utility, with farming counting for less.
- Strengths, things to work on, key moments, your share of the team’s damage, and a few plain-language takeaways.
- The formulas behind every number, one click away.
Look and feel
- Pixel Arcade theme: near-black with PICO-8 colours (green for wins, red for losses), square corners and hard shadows. Headings and numbers use the Silkscreen pixel font, body text uses IBM Plex Sans, and icons come from Pixelarticons.
- Background: a slowly drifting win/loss halftone behind every page, green squares rising from one corner and red from the other.
- “Pixel build” motion: panels assemble row by row as they come into view, bars fill block by block, the heatmap dissolves in and the grade draws itself in. With “reduce motion” turned on, everything appears still and at once.
- Phones: every page works on a phone, with a bottom tab bar instead of the side rail.
Built with
Next.js (App Router) with React and TypeScript, Tailwind CSS, Steam sign-in through NextAuth.js, and Vitest for tests. All match data comes from the STRATZ GraphQL API through a single cached, rate-limited gateway.
Credits
- Match data: STRATZ. Every stat, match, replay detail and impact (IMP) rating on this site comes from the STRATZ API. Thank you to the STRATZ team for making it available.
- Hero and item art: Valve, served from the Steam CDN. Dota 2 is a registered trademark of Valve Corporation. This is an unofficial fan project, not affiliated with or endorsed by Valve.
- Fonts: Silkscreen by Jason Kottke and IBM Plex Sans.
- Icons: Pixelarticons by Gerrit Halfmann.
- Colours: the PICO-8 palette by Lexaloffle.
Other players’ names in the match screenshots are replaced with “Player 2”, “Player 3” and so on.
License
MIT © 2025 Syauqi Ashadullah