This is a powerful, unified custom integration for Home Assistant that tracks and consolidates gaming presence across Steam, Xbox Live, PlayStation Network, Discord, Playnite, and custom PC clients into a single, clean dashboard sensor for each person in your household / friend group. It's super useful if you want to be able to track who is online, what they're playing, and for how long.
I started developing this as a way to have persistent sensors since I was annoyed that the Xbox and Steam sensors would regularly flutter between online/offline status, making notifications and my gaming dashboard unreliable. This evolved into making master sensors instead of simply tracking each platform independently. Over time, this has grown into a much more complex integration that now tracks game time, records the last game played, provides cover art, allows for rich notifications through Discord and much, much more.
Some of the key features are listed below.
- Unified Master Sensor: Combines Xbox, PlayStation, Steam, Discord, Playnite, and Custom PC clients into one clean "Master Status" sensor per person.
- Online/Offline Notifications: Receive Discord, SMS, and/or Mobile notifications when users start or finish playing a game.
- Parental Controls: Track daily playtime and recieve notifications when a limit, curfew, or age-rating threshold is reached.
- Discord Rich Presence: Track hundreds of standalone games, emulators, and Epic/EA/Ubisoft launchers automatically by hooking into Discord's Rich Presence status. Automatically ignores custom text statuses to prevent false positives.
- Custom PC Game Support: Track non-platform games (like Epic Games, Minecraft, or Genshin Impact) using template funnels or binary sensors.
- PC Sub-Master Sensor: Automatically aggregates Custom, Steam, and Discord tracking into a single, unified "PC" status. It features smart platform yielding (e.g., Discord quietly steps aside if Steam is tracking the same game) to completely eliminate double-counting in your playtime analytics.
- Smart Ghosting Protection: Prevents echo sessions on a shared PC — e.g., when the Windows Xbox app incorrectly broadcasts another player's Steam/Playnite game as its own. Configured on the authoritative player (pick which other players' Xbox sensors to suppress).
- Drop-Out Protection: Built-in grace periods prevent a gamer from appearing "Offline" if their game crashes, they switch titles, or their internet briefly blips, keeping play sessions perfectly intact.
- Playtime Analytics: Automatically calculates session time, daily hours, and a rolling 7-day total for easy dashboard charting.
- Clean Dashboards: Automatically sanitizes messy game titles (e.g., changes "Minecraft Launcher" to "Minecraft") and pulls high-quality cover art from SteamGridDB.
- Advanced Exclusion Filtering: Prevent media apps (Netflix, YouTube, Spotify) or background processes from triggering gaming statuses using a global exclusions list.
- Customizable Cover Art: Automatically fetches gorgeous images from SteamGridDB and passes them to your dashboard via URL and/or caches them locally for fast updates.
- "Last Seen" Memory: When gamers go offline, the sensor retains their last played game and calculates exactly how long ago they were active (e.g., Last seen 3h ago: Genshin Impact (1h 37m)).
- Custom Avatars: Automatically pulls live gamer pictures from platform APIs, with the option to easily override missing or incorrect images with your own local images.
This integration acts as a "wrapper" that intelligently processes data from your existing integrations. Before installing, ensure you have any necessary base integrations installed and working in Home Assistant. Not all are required, but I recommend having at least ONE official integration installed. Discord and Playnite can also be used for game tracking with or without the other integrations, but they are more complicated to set up:
While not required for functionality, I recommend installing the following HACS for the most robust dashboard cards:
- SteamGridDB API Key - Provides artwork for games. This is not REQUIRED, but it is HIGHLY recommended!
- Gaming Status Cards - Easy to use companion dashboard cards, so you don't have to make your own.
- Official Discord Integration - Requires setting up a Discord Bot. REQUIRED if you want to use Discord for notifications.
- Mosquitto Broker - REQUIRED if you plan to use Playnite for tracking games. You will also need an MQTT add-on installed in Playnite (such as Playnite MQTT Client) to broadcast your status to Home Assistant.
- HASS.Agent - Allows you to create custom sensors for otherwise untrackable games. Install both the PC app and the integration for Custom PC sensors. Try using Discord or Playnite tracking first, if possible, since HASS Agent sensors have to be individually created for each tracked game.
To display beautiful, high-resolution game covers on your dashboard, this integration requires a free API key from SteamGridDB.
- Go to SteamGridDB.com.
- Click Login in the top right corner and authenticate using your Steam account.
- Click your profile picture in the top right and select Preferences.
- Navigate to the API tab on the left menu.
- Click Generate API Key.
- Copy the string of letters and numbers generated.
If you plan to use the Content Rating Limit parental control, this integration looks up each game's ESRB rating via a free API key from RAWG.io.
- Go to RAWG.io API Docs.
- Click GET API KEY and sign up or log in.
- Copy the generated key and paste it into the RAWG.io API Key field during Initial Setup or under the Advanced menu.
Note: RAWG's rating coverage isn't complete for every title. If a game comes back unrated, you can manually assign it a rating using the Content Rating Overrides field under Advanced (see below).
Method 1: HACS (Recommended) Installation is easiest via the Home Assistant Community Store (HACS). Gaming Status is a default repository in HACS, so you do not need to add any custom links!
Simply click the button below (requires My Home Assistant configured) to open the download page directly, or search for "Gaming Status" in HACS.
Method 2: Manual
Copy the gaming_status folder into your custom_components folder and restart Home Assistant.
Go to Settings / Devices & Services and press the Add Integration button, or click the shortcut button below (requires My Homeassistant configured):
Gaming Status is configured entirely through the Home Assistant UI. There is no YAML or JSON configuration required. (Note: If you are upgrading from an older version, your gaming_profiles.json file will be automatically migrated to the new database and can be safely deleted).
- In Home Assistant, navigate to Settings > Devices & Services.
- Click + Add Integration and search for Gaming Status.
- You will be prompted to enter a SteamGridDB API Key (Optional). This is highly recommended to automatically fetch beautiful hero art for your games. You can get a free key here.
- You'll also see a RAWG.io API Key (Optional) field, used to automatically look up content/age ratings for the Parental Controls Content Rating Limit rule. You can get a free key here, or add it later under Advanced.
- Click Submit.
To configure your players, notifications, and rules, click the Configure button (gear icon) on the Gaming Status integration card. This opens the main configuration hub, which is divided into six menus based on your enabled features:
Add, edit, or delete the gamers in your household.
- Platform Sensors: When adding a player, you simply select their respective integration sensors from the dropdowns. The integration will automatically filter your entities to show the correct Steam (
sensor.steam_*), Xbox (sensor.*_status), PlayStation (sensor.*_now_playing), and Playnite (MQTTbinary_sensor.*_playnite_playing_game) entities. (Note: To remove a previously assigned sensor, simply click the 'X' to clear the entity dropdown and click Submit. The integration will safely save the empty state and stop tracking that platform). - Player Details: After adding a player, you can configure:
- Session Notifications: Select notification methods for when this specific player starts or stops gaming. Note: These must be configured under Notifications.
- Suppress other players' Xbox sensors: Configured on the player whose own sensor(s) are accurate — pick which other players' Xbox sensors should be suppressed whenever this player is confirmed playing. Fixes a shared-PC Xbox app misattributing this player's Steam/Playnite session to someone else's Xbox account. Only for cross-player mixups; the same player's own overlapping sensors are already handled automatically.
- Exclude Games: Comma-separated list of games to ignore for this specific player.
Manage where your gaming alerts and weekly reports are sent.
- Notify Artwork Style: Choose which fetched artwork type (Cover, Hero, Logo, Icon) attaches to your notifications.
- Add Notification: Map a friendly name (e.g., "Dad's Phone") to an existing Home Assistant
notify.service. It fully supports standard mobile app notifications, Discord, and SMS. - Discord Notification Colors: Customize the embed colors for Discord alerts (Default, Platform Colors, Game Color, or Custom Hex).
- Weekly Report: Send a beautifully formatted summary of everyone's weekly playtime and top games to your selected notification methods on a specific day and time.
Set automated rules based on accumulated playtime, time of day, or game content rating.
- Screen Time: Set distinct weekday and weekend daily minute limits.
- Curfew: Set distinct weekday and weekend cutoff times (e.g., 22:00).
- Content Rating Limit: Set a maximum allowed age rating (e.g., "Ages 13+"). Ratings are looked up automatically via a free RAWG.io API key (configured under Advanced) and cached indefinitely once found for a game. If the player's active game exceeds the configured age, a notification is sent the moment that game starts — switching to a different over-the-limit game always sends a fresh notification, but the same game won't spam you again while it keeps running.
- Reminder Frequency: (Screen Time and Curfew only) Set how often to repeat the notification(s).
- Notifications: When a limit is reached, you can automatically send a notification using any of your configured methods.
Manually assign artwork or colors to specific games using simple Game = Value lists.
- Custom Asset Maps (Grid, Hero, Logo, Icon): Assign artwork for custom games or unrecognized titles. Fully supports web URLs and Home Assistant
/local/paths. (Example:Marvel Rivals = /local/covers/marvel.png) - Custom Colors: Override the automatic dominant color extractor by assigning specific hex codes to games. (Example:
Cyberpunk 2077 = #fcee0a)
Update your API keys and fine-tune text processing rules.
- API Keys & Tokens: Update your SteamGridDB API key, RAWG.io API key (for content ratings), or your Discord Bot Token and Server ID.
- Game Title Overrides: Clean up messy or lengthy names. Format as
raw name = display name. (Example:Minecraft Launcher = Minecraft) - Title Cleanups: A list of strings to automatically strip from game names. (Example:
Tom Clancy's, Sid Meier's) - Global Exclusions: Games or apps that should be universally ignored by the tracker. (Example:
Home, YouTube, Netflix, Xbox App) - Content Rating Overrides: (Only shown when Parental Controls is enabled) Manually assign a rating to games your rating provider has no data for. Format as
Game = Code, using the codesE,E10,T,M, orAO. (Example:Skull and Bones = M)
These variables control how the integration handles platforms, caching, and network drops across all players.
- Enabled Platforms: Select which gaming platforms to track (Steam, Xbox, PlayStation, Discord, Playnite, and Custom).
- Master Toggles: Enable or disable the Notifications and Parental Controls configuration hubs.
- Cache Settings: Toggle local image caching, automatic vibrant color extraction, and configure background cleanup limits (Max Files & Max Days).
- Grace Periods (Network / Away / Transition): Configure exactly how long the integration waits during network drops, idle statuses, or game switches before ending a session.
- Minimum Session Duration: Prevents quickly opening and closing a game (like launching a launcher) from cluttering your play history.
- Master Handoff Grace Period: If a player is genuinely, continuously active on two platforms at once (e.g. playing a Steam game while also idling into a console game), whichever platform is currently shown on the Master sensor keeps that spot indefinitely as long as it stays healthy — this setting only comes into play once that platform's own connection drops into its own offline-grace or ghosted state and stays stuck there continuously; only after it's been stuck for this long does a more-recently-started game on another platform get to take over the display. Prevents notification spam from a platform's brief connectivity blips repeatedly flipping which one is shown. Default: 300 seconds (5 min). Set to 0 to restore instant hand-off.
- Reset History: A toggle to clear all accumulated daily/weekly session history upon the next Home Assistant restart. Use with caution!
- Remove Disabled Sensors: Automatically deletes orphaned sensors from the registry if their platform is un-checked from the Enabled Platforms list.
To provide the most accurate PC tracking possible, this integration can monitor Steam, Discord, Playnite, and Custom clients simultaneously and output the result as one "PC" sensor.
Setting up Discord Tracking: Because Home Assistant does not natively track Rich Presence, this integration features a built-in Discord tracker. To use it, you must create a bot in the Developer Portal to read your server's statuses.
- Go to the Discord Developer Portal and log in.
- Click New Application in the top right corner and give your bot a name (e.g., "Home Assistant Tracker").
- On the left menu, click Bot. Scroll down to the Privileged Gateway Intents section.
- CRITICAL: You must turn on Presence Intent and Server Members Intent. Without these, the integration cannot see what games you are playing. Save your changes.
- Scroll up and click Reset Token. Copy this newly generated Bot Token to a safe place.
- On the left menu, click OAuth2, then URL Generator. Under Scopes, check the bot box.
- Copy the generated URL at the bottom, paste it into your browser, and authorize the bot to join your personal Discord server.
- Open your Discord app, right-click your server icon, and click Copy Server ID (Note: This requires Developer Mode to be enabled in Discord's advanced settings).
- Finally, in Home Assistant, add the Gaming Status integration (or go to the Advanced menu if already installed) and make sure Discord is checked in the platforms list. Paste your Bot Token and Server ID. The integration will automatically fetch a list of your server members so you can easily assign them to your players from a dropdown menu!
- Smart Application ID Filtering: Once set up, the integration automatically ignores custom text statuses (like 'Eating dinner' or listening to Spotify). It strictly requires a verified Discord
application_idto trigger, guaranteeing only legitimate gaming sessions are captured.
Setting up Playnite Tracking: Playnite is an incredible open-source library manager that can track games across almost any PC launcher or emulator. To link it to Gaming Status, it utilizes MQTT.
- Ensure you have an MQTT Broker (like Mosquitto) installed and configured in Home Assistant.
- Open Playnite on your PC, navigate to the Add-ons menu, and install an MQTT broadcasting add-on (e.g., MQTT Client).
- Configure the add-on in Playnite with your Home Assistant MQTT broker IP address, username, and password.
- In Home Assistant, ensure the MQTT integration detects and creates this binary sensor.
- Go to the Gaming Status configuration, select Playnite as an Enabled Platform, and assign that new
binary_sensorto your player! By default, it may be namedbinary_sensor.desktop_playnite_playnite_playing_game.
The PC Sub-Master Priority Logic:
If a player launches a game, it is very common for multiple trackers (like Discord, Playnite, and Steam) to detect it simultaneously. To prevent double-counting your playtime hours and sending duplicate push notifications, the sensor.gaming_status_XXXXX_pc sensor uses strict Smart Platform Yielding.
Platforms are prioritized in this exact order: Playnite > Custom > Steam > Discord.
- Example: If a player launches a Steam game, Discord will likely detect it first and claim the dashboard. Seconds later, when Steam wakes up and detects the same game, Discord will instantly pause its timer and yield control to Steam.
- Result: You get the lightning-fast notifications of Discord, but the pristine, deduplicated analytics of Steam!
Upon restart, the integration will instantly read your settings and generate the master tracking sensors for your dashboard. All entities generated by the integration are strictly standardized under the gaming_status_ namespace.
| Entity | Type | Description |
|---|---|---|
| sensor.gaming_status_XXXXX_steam | Sensor | Steam sensor for each added profile |
| sensor.gaming_status_XXXXX_xbox | Sensor | Xbox sensor for each added profile |
| sensor.gaming_status_XXXXX_playstation | Sensor | PlayStation sensor for each added profile |
| sensor.gaming_status_XXXXX_discord | Sensor | Discord sensor for each added profile |
| sensor.gaming_status_XXXXX_playnite | Sensor | Playnite sensor for each added profile |
| sensor.gaming_status_XXXXX_custom | Sensor | Custom sensor for each added profile |
| sensor.gaming_status_XXXXX_pc | Sensor | Sub-master sensor that automatically aggregates Steam, Discord, Playnite, and Custom PC clients into a single unified PC state |
| sensor.gaming_status_XXXXX_master | Sensor | Master sensor for each added profile that combines all added platforms into one "Online/Offline" status |
| sensor.gaming_status_players_online | Sensor | Global sensor that tracks the total number of players currently online |
| binary_sensor.gaming_status_anyone_gaming | Binary Sensor | Useful for showing or hiding cards |
Each sensor has a set of attributes that can be utilized in dashboards charts, etc. The *_master sensors provide the following attibutes:
Aggregate Analytics
| Attribute | Description |
|---|---|
| friendly_name | Display name for this player's entity |
| total_daily_hours | Sum of daily hours across all platforms (float) |
| total_weekly_hours | Sum of weekly hours across all platforms (float) |
| rolling_weekly_hours | Sum of rolling hours across all platforms |
| total_weekly_hours_last_week | Sum of last week's hours |
| weekly_breakdown | A copy of rolling_weekly_breakdown, retained for backward-compatibility |
| calendar_weekly_breakdown | Consolidated dictionary of all games played across all platforms for the current calendar week (Monday–Sunday), formatted as human-readable strings (e.g., "5h 30m") |
| rolling_weekly_breakdown | Consolidated dictionary of all games played across all platforms, formatted as human-readable strings (e.g., "5h 30m") as a rolling 7-day total |
| raw_rolling_breakdown | Dictionary of game names to total hours (float) over the rolling 7-day window, used by the Gaming Status Cards for chart rendering |
| raw_calendar_breakdown | Dictionary of game names to total hours (float) for the current calendar week, used by the Gaming Status Cards for chart rendering |
| platform_split | A dictionary showing the percentage of total weekly hours spent on each platform (e.g., {"Steam": "55%"}) |
| longest_session | A copy of rolling_longest_session, retained for backward-compatibility |
| calendar_longest_session | A formatted string showing the game title and duration of the longest single session across all platforms for the current calendar week (e.g., "DELTARUNE (1h 24m)") |
| rolling_longest_session | A formatted string showing the game title and duration of the longest single session across all platforms over the rolling 7-day window |
| play_history | Per-day, per-game playtime aggregated across all platforms: {"YYYY-MM-DD": {"Game Title": seconds, ...}}. Used by the Gaming Status Cards for chart rendering |
| recent_sessions | List of the most recently completed play sessions across all of this player's platforms (newest first, capped at 20): {game, platform, duration_seconds, date, start_time, end_time, hero_art_url, game_dominant_color} |
Parental/Limit Controls
| Attribute | Description |
|---|---|
| daily_play_limit_minutes | The configured daily limit |
| remaining_play_time_minutes | Calculated remaining time based on current usage |
| current_game_rating | The rating label (e.g., "Mature") of the currently active game, only populated when the Content Rating Limit rule is enabled |
| rating_exceeded | true if the Content Rating Limit rule is enabled and the player's currently active game exceeds the configured age threshold |
Active Status
| Attribute | Description |
|---|---|
| secondary | Current state or the time elapsed and session duration of the last played game |
| active_platform | The name of the platform currently driving the status (e.g., "Steam") |
| entity_picture | URL of the player's avatar fetched from the active platform |
| icon | Dynamic icon to match the active platform |
| game_cover_art | URL of cover art, either local or SteamGridDB |
| game_hero_art | URL of hero art, either local or SteamGridDB |
| game_logo_art | URL of logo art, either local or SteamGridDB |
| game_icon_art | URL of icon art, either local or SteamGridDB |
| game_dominant_color | The automatically extracted vibrant hex color from the game's artwork, or a manually assigned color |
| game_content_rating | Rating metadata for the currently active game: {esrb, pegi, age_floor, descriptors, unrated, source} (source is "rawg", "override", or null if never looked up) |
| current_game | Inherited from the most active underlying platform tracker |
| play_start_time | Inherited from the most active underlying platform tracker |
| last_played_game | Title of the most recent game detected across all tracked platforms |
| last_online_valid_timestamp | Timestamp of the last time detected online |
Each sensor has a set of attributes that can be utilized in dashboards charts, etc. The individual *_steam, *_xbox, *_discord, and *_playstation sensors provide the following attibutes:
Core State Attributes
| Attribute | Description |
|---|---|
| friendly_name | Display name for this player's entity |
| secondary | Current state or the time elapsed and session duration of the last played game |
| current_game | Title of the game actively being played right now, or null if the user is offline |
| entity_picture | The local path to the cached avatar image |
| last_online_valid_timestamp | Timestamp of the last time detected online |
| play_start_time | Timestamp when the current, active gaming session began |
| timer_status | Current state of the internal playtime stopwatch (Running, Paused, or Stopped) |
| xbox_suppressed | Xbox sensors only. true when a detected game was suppressed because another player's suppresses_xbox_sensors setting names this sensor and one of that player's own sensors is confirmed playing the same game (see Smart Ghosting Protection). Always false for non-Xbox platforms |
| cached_game_cover | Backup URL for the last known game cover art, used during grace periods or offline states |
| game_cover_art | URL of cover art, either local or SteamGridDB |
| game_hero_art | URL of hero art, either local or SteamGridDB |
| game_logo_art | URL of logo art, either local or SteamGridDB |
| game_icon_art | URL of icon art, either local or SteamGridDB |
| game_dominant_color | The automatically extracted vibrant hex color from the game's artwork, or a manually assigned color |
| game_content_rating | Rating metadata for the currently active/cached game: {esrb, pegi, age_floor, descriptors, unrated, source} (source is "rawg", "override", or null if never looked up) |
Rich Tracking & Analytics
| Attribute | Description |
|---|---|
| icon | Icon to match the current platform |
| daily_play_time | Total seconds played today |
| weekly_play_time | Total seconds played this calendar week |
| weekly_play_time_last_week | Total seconds played in the previous week |
| last_played_game | Title of the most recently closed game detected on this specific platform |
| weekly_game_breakdown | Dictionary mapping game names to total seconds over the rolling 7-day window (alias of rolling_weekly_breakdown) |
| rolling_weekly_breakdown | Dictionary mapping game names to total seconds over the rolling 7-day window |
| calendar_weekly_breakdown | Dictionary mapping game names to total seconds for the current calendar week (Monday–Sunday) |
| play_history | Per-day, per-game playtime for this platform: {"YYYY-MM-DD": {"Game Title": seconds, ...}} |
| recent_sessions | List of the most recently completed play sessions on this platform (newest first, capped at 20): {game, platform, duration_seconds, date, start_time, end_time, hero_art_url, game_dominant_color}. A session only appears here once it has ended |
| longest_session_details | Dict of {game, duration} (seconds) for the longest single session today; resets at midnight |
| rolling_longest_session_details | Dict of {game, duration} (seconds) for the longest single session over the rolling 7-day window |
| calendar_longest_session_details | Dict of {game, duration} (seconds) for the longest single session in the current calendar week |
| Attribute | Description |
|---|---|
| active_games | A comma-separated string of the games currently being played by online players |
Several of these attributes (e.g., artwork URLs, breakdown dictionaries, session detail dicts, play_history, and recent_sessions) are explicitly added to _unrecorded_attributes in the sensor classes. This is a deliberate performance optimization to prevent Home Assistant from saving these frequently-changing or large values into the long-term database (recorder), which keeps your database file from growing excessively large.
Beyond the dashboard, Gaming Status exposes two Home Assistant services (Developer Tools → Actions, or callable from automations/scripts) for cleaning up a player's stored game history after the fact — useful when a data source ever misreports a game's name (e.g. DOOM Eternal In the menu instead of DOOM Eternal) or when you simply want to remove a game's history entirely.
gaming_status.rename_game
Renames a game across a player's stored history (recent sessions, daily/weekly breakdowns, and archived per-day totals), merging its playtime into an existing name if one already matches. Does not rename a currently in-progress session — the fix applies once that session ends naturally.
| Field | Required | Description |
|---|---|---|
player |
Yes | The player's configured name, e.g. Adam |
platform |
No | Limit the rename to one platform (steam, xbox, playstation, playnite, custom, discord). Omit to apply across all of the player's platforms |
old_name |
Yes | The exact game name currently stored, e.g. DOOM Eternal In the menu |
new_name |
Yes | The name to rename it to, e.g. DOOM Eternal |
gaming_status.delete_game
Permanently purges every trace of a named game from a player's stored history — every recorded session, today's live totals, and every archived day's contribution to daily/weekly breakdowns. This cannot be undone.
| Field | Required | Description |
|---|---|---|
player |
Yes | The player's configured name, e.g. Adam |
platform |
No | Limit the deletion to one platform. Omit to purge across all of the player's platforms |
game |
Yes | The exact game name to delete |
Both services can also be triggered from a dashboard using the Game Management card, which provides player/platform/game dropdowns populated from real data instead of requiring you to type exact names.
Once everything is up and running (with sensors showing up from the integration), try playing a game for at least 5 minutes to make sure the online status is reflected in the _master sensors. Note that, by default, sessions shorter than 300 seconds (5 minutes) are discarded and do not count toward the total playtime hours. If the sensors are working correctly, try some of the following! If not, see the troubleshooting documentation.
- Add some sweet displays to your dashboard, showing who's online and what they're playing
- Set up Discord, SMS, and/or Mobile notifications for when users start, stop, and switch games
- Add a slideshow to your dashboard or wallpanel display to see what's being played
- Add a weekly hours chart or a per-game breakdown chart to visualize playtime trends across your household
- Add custom sensors to track PC games not logged by Steam or Xbox sensors
- Use a sensor to track whether or not anyone is gaming (useful for automations or contextual card display)
- Check out other advanced setup options for features like preventing tracking of games by the wrong players and per-user game exclusions
