This is a custom integration for Home Assistant that creates sensors using data from the Jolpica-F1 API.
It also fetches live data from Formula 1’s unofficial Live Timing API during active sessions (practice, qualifying, sprint, race). These live sensors only update shortly before, during, and shortly after a session. Outside of session times, they will not update.
It is designed for users who want to build automations, scripts, notifications, TTS messages, or more advanced use cases such as generating dynamic dashboards, triggering race-day routines, syncing events to calendars, or integrating with external services based on upcoming Formula 1 events.
Tip
Visit the F1 Sensor Community at Home Assistant Community Forum to share your project and get help and inspiration. Visit to share you procejt and get help and inspiration
| Entity | Info |
|---|---|
| sensor.f1_next_race | Next race info |
| sensor.f1_season_calendar | Full race schedule |
| sensor.f1_driver_standings | Current driver championship standings |
| sensor.f1_constructor_standings | Current constructor standings |
| sensor.f1_weather | Weather forecast at next race circuit |
| sensor.f1_last_race_results | Most recent race results |
| sensor.f1_season_results | All season race results |
| binary_sensor.f1_race_week | on during race week |
| sensor.f1_constructor_points_progression | Constructors Point Progression |
| ssensor.f1_driver_points_progression | Constructors Point Progression |
| sensor.f1_session_status | LIVE - Current session phase (pre, live, suspended, finished, finalised, ended) |
| sensor.f1_track_status | LIVE - Current track status (CLEAR, YELLOW, VSC, SC, RED) |
| binary_sensor.f1_safety_car | LIVE - on when Safety Car (SC) or Virtual Safety Car (VSC) is active |
| sensor.f1_track_weather | LIVE - Current on-track weather (air temp, track temp, rainfall, wind speed, etc.) |
| sensor.f1_race_lap_count | LIVE - Current race lap number (only updates during a race, not during practice/qualy) |
| sensor.f1_current_session | LIVE - Current ongoing session, like Practice 1, Qualification, Race |
| sensor.f1_driver_list | Show list and details on all drivers, including team color, headshot URL etc from the Live API |
You can install this integration as a custom repository by following one of these guides:
To install the custom component using HACS:
or
- Install HACS if you don't have it already
- Open HACS in Home Assistant
- Search for "F1 Sensor"
- Click the download button. ⬇️
Without HACS
- Download the latest release of the F1 Sensor integration from GitHub Releases.
- Extract the downloaded files and place the
f1_sensorfolder in your Home Assistantcustom_componentsdirectory (usually located in theconfig/custom_componentsdirectory). - Restart your Home Assistant instance to load the new integration.
To add the integration to your Home Assistant instance, use the button below:
If the button above does not work, you can also perform the following steps manually:
- Browse to your Home Assistant instance.
- Go to Settings > Devices & Services.
- In the bottom right corner, select the Add Integration button.
- From the list, select F1 Sensor.
- Follow the on-screen instructions to complete the setup.
When adding or reconfiguring the integration, you can choose to enable live data via Formula 1’s unofficial Live Timing API.
-
Enable live F1 API (Race Control/Track/Session)
Creates three additional live entities:sensor.f1_session_statussensor.f1_track_statusbinary_sensor.f1_safety_carsensor.f1_track_weathersensor.f1_race_lap_countsensor.f1_current_sessionsensor.f1_driver_list
If this option is not selected, these live sensors are not created.
-
Live update delay (seconds)
Lets you delay delivery of live messages to better align with what you see on TV or streaming.Typical broadcast delays:
- Broadcast TV (satellite/cable/terrestrial): ~5–10 seconds behind
- Streaming services: ~20–45 seconds behind, sometimes more
- Sports cable/OTT providers: 45–60 seconds or more depending on provider
By setting the delay accordingly, your Home Assistant automations (for example flashing lights on a red flag) can sync more closely with the live pictures you are watching.
More info! - Live session entities
In addition to season and race data, F1 Sensor provides live session entities during race weekends.
Reflects the current phase of a session, powered by SessionStatus feed and an internal started_flag.
Possible states
-
pre – session is open but not yet started (typically ~1h before lights out).
-
live – session is running.
-
suspended – a started session is stopped (red flag or interruption).
-
finished – clock is over, chequered flag. RaceControl may still send flags on in-laps.
-
finalised – results have been confirmed.
-
ended – feed is closed for the session.
Typical transitions
pre → live → suspended ↔ live → finished → finalised → ended
After finalised or ended, logic resets and next session begins at pre.
Directly reflects the latest TrackStatus feed.
Possible states
- CLEAR
- YELLOW
- VSC
- SC
- RED
State reflects the last received track status and may persist briefly after finished while in-laps are ongoing.
Boolean entity derived from track status.
States
- on – when
sensor.f1_track_statusis SC or VSC. - off – in all other cases.
Updates approximately every minute during an active session.
Attributes include
- Air temperature
- Track temperature
- Rainfall
- Wind speed
Only updates during an active race session.
Shows the current lap number in real time.
Race Control messages are sent as events in Home Assistant under the event type f1_sensor_race_control_event.
These include flags, steward notes, incident reports, and other live race control communications.
Example payloads:
event_type: f1_sensor_race_control_event
data:
message:
Utc: "2025-09-19T12:40:18"
Category: Flag
Flag: CLEAR
Scope: Sector
Sector: 6
Message: CLEAR IN TRACK SECTOR 6
received_at: "2025-09-19T12:40:44+00:00"
origin: LOCAL
time_fired: "2025-09-19T12:40:44.106956+00:00"
event_type: f1_sensor_race_control_event
data:
message:
Utc: "2025-09-19T12:40:07"
Category: Flag
Flag: YELLOW
Scope: Sector
Sector: 6
Message: YELLOW IN TRACK SECTOR 6
received_at: "2025-09-19T12:40:44+00:00"
event_type: f1_sensor_race_control_event
data:
message:
Utc: "2025-09-19T12:40:06"
Category: Other
Message: INCIDENT INVOLVING CAR 81 (PIA) NOTED - YELLOW FLAG INFRINGEMENT
received_at: "2025-09-19T12:40:44+00:00"Note
Currently, Race Control is published as events only. In a future release, these messages will also be exposed as a > sensor.
Each timestamp attribute (e.g. race_start) is still provided in UTC. In addition, a _local variant such as race_start_local is available. These values use the circuit's timezone so you can easily create automations at the correct local time.
During installation, you can choose exactly which sensors you want to include in your setup.
This gives you control over which data points to load — for example, only the next race and weather, without standings or calendar.
You can always change this selection later by reconfiguring the integration via Settings > Devices & Services in Home Assistant.
The integration fetches fresh data from the Jolpica-F1 API every 1 hours.
I personally use this integration to display the next race and the following three races on an e-ink display. You can read more about that setup here.
Note
If your goal is to visually display upcoming race information, current standings, and more in your Home Assistant dashboard, the FormulaOne Card is the better choice for that purpose.
sensor.f1_season_results may trigger a warning in the Home Assistant logs:
Logger: homeassistant.components.recorder.db_schema
Source: components/recorder/db_schema.py:663
Integration: Recorder
State attributes for sensor.f1_season_results exceed maximum size of 16384 bytes. This can cause database performance issues; Attributes will not be storedDespite the warning, the sensor should still work fine for display in the frontend. However, to avoid any database load/performance issues, it is recommended to exclude this sensor from being recorded in your recorder: config:
recorder:
exclude:
entities:
- sensor.f1_season_resultsThese two charts visualize the season progression for both the Drivers’ Championship and the Constructors’ Championship. They rely on data from the sensors sensor.f1_driver_standings and sensor.f1_constructor_standings.
To use these examples, make sure you have the following custom cards installed in Home Assistant: • F1 Sensor integration version 2.3.0 or later • auto-entities • ApexCharts Card
Once installed, you can add the provided YAML configuration to your dashboard to display the charts.
type: custom:auto-entities
card_param: series
show_empty: false
card:
type: custom:apexcharts-card
header:
show: true
title: Season progression - drivers points
show_states: false
apex_config:
chart:
animations:
enabled: false
markers:
size: 6
strokeWidth: 2
hover:
sizeOffset: 8
states:
hover:
filter:
type: darken
value: 0.45
active:
allowMultipleDataPointsSelection: false
filter:
type: darken
value: 0.55
legend:
show: true
position: left
horizontalAlign: left
itemMargin:
vertical: 4
fontSize: 12px
xaxis:
type: category
tickPlacement: between
labels:
rotate: -35
trim: false
minHeight: 60
tooltip:
shared: false
intersect: true
x:
formatter: |
EVAL:function (val) { return val; }
"y":
formatter: |
EVAL:function (val) { return Math.round(val); }
filter:
template: >
{%- set e = 'sensor.f1_driver_points_progression' -%} {%- set drivers =
state_attr(e, 'drivers') or {} -%} {%- set palette = {
'VER':'#4781D7','PER':'#6C98FF','NOR':'#F47600','PIA':'#F47600',
'LEC':'#ED1131','SAI':'#1868DB','HAM':'#ED1131','RUS':'#00D7B6',
'ALO':'#229971','STR':'#229971','ALB':'#1868DB','SAR':'#1868DB',
'HUL':'#01C00E','MAG':'#01C00E','TSU':'#4781D7','HAD':'#6C98FF',
'OCO':'#9C9FA2','GAS':'#00A1E8','BOT':'#9C9FA2','ZHO':'#9C9FA2',
'LAW':'#6C98FF','RIC':'#6C98FF','ANT':'#00D7B6','DOO':'#00A1E8',
'BOR':'#01C00E','BEA':'#9C9FA2','COL':'#00A1E8'
} -%} {%- set ns = namespace(items=[]) -%} {%- for code, d in
drivers.items() -%}
{%- set pts = d.cumulative_points if d.cumulative_points is defined else [] -%}
{%- set last = pts[-1] if pts else 0 -%}
{%- set name = d.name if d.name is defined else (d.tla if d.tla is defined else code) -%}
{%- set js = "const a = entity.attributes || {}; const rounds = a.rounds || []; const drv = (a.drivers && a.drivers['" ~ code ~ "']) || {}; const pts = drv.cumulative_points || []; return pts.map((y, i) => { const r = rounds[i] || {}; const rn = (r.round != null) ? r.round : (i+1); const label = 'R' + rn + ' — ' + (r.race_name || ''); return { x: label, y: y }; });" -%}
{%- set obj = {
"entity": e,
"name": name,
"type": "line",
"color": palette.get(code, "#888888"),
"data_generator": js
} -%}
{%- set ns.items = ns.items + [ {"code": code, "last": last, "obj": obj} ] -%}
{%- endfor -%} [ {%- for it in ns.items | sort(attribute='last',
reverse=true) -%}
{{ it.obj | tojson }}{{ "," if not loop.last }}
{%- endfor -%} ]type: custom:auto-entities
card_param: series
show_empty: false
card:
type: custom:apexcharts-card
header:
show: true
title: Season progression - constructors points
show_states: false
apex_config:
chart:
animations:
enabled: false
markers:
size: 6
strokeWidth: 2
hover:
sizeOffset: 8
states:
hover:
filter:
type: darken
value: 0.45
active:
allowMultipleDataPointsSelection: false
filter:
type: darken
value: 0.55
legend:
show: true
position: left
horizontalAlign: left
itemMargin:
vertical: 4
fontSize: 12px
xaxis:
type: category
tickPlacement: between
labels:
rotate: -35
trim: false
minHeight: 60
tooltip:
shared: false
intersect: true
x:
formatter: |
EVAL:function (val) { return val; }
"y":
formatter: |
EVAL:function (val) { return Math.round(val); }
filter:
template: >
{%- set e = 'sensor.f1_constructor_points_progression' -%} {%- set teams =
state_attr(e, 'constructors') or {} -%} {# Färg per team (ändra fritt) #}
{%- set palette = {
'mclaren':'#F47600', 'red_bull':'#4781D7', 'mercedes':'#00D7B6',
'williams':'#1868DB', 'aston_martin':'#229971', 'sauber':'#01C00E',
'ferrari':'#ED1131', 'alpine':'#00A1E8', 'rb':'#6C98FF', 'haas':'#9C9FA2'
} -%} {%- set ns = namespace(items=[]) -%} {%- for key, t in teams.items()
-%}
{%- set pts = t.cumulative_points if t.cumulative_points is defined else [] -%}
{%- set last = pts[-1] if pts else 0 -%}
{%- set name =
(t.identity.name if t.identity is defined and t.identity.name is defined
else (t.name if t.name is defined
else (key | replace('_',' ') | title))) -%}
{%- set js = "const a = entity.attributes || {}; const rounds = a.rounds || []; const team = (a.constructors && a.constructors['" ~ key ~ "']) || {}; const pts = team.cumulative_points || []; return pts.map((y, i) => { const r = rounds[i] || {}; const rn = (r.round != null) ? r.round : (i+1); const label = 'R' + rn + ' — ' + (r.race_name || ''); return { x: label, y: y }; });" -%}
{%- set obj = {
"entity": e,
"name": name,
"type": "line",
"color": palette.get(key, "#888888"),
"data_generator": js
} -%}
{%- set ns.items = ns.items + [ {"key": key, "last": last, "obj": obj} ] -%}
{%- endfor -%} [ {%- for it in ns.items | sort(attribute='last',
reverse=true) -%}
{{ it.obj | tojson }}{{ "," if not loop.last }}
{%- endfor -%} ]Note
The Formula 1 track status blueprint for Home Assistant is now maintained by EvertJob. You can find the latest version and full instructions here: 👉 github.com/EvertJob/F1-Blueprint
This e-ink display project uses the sensors from this integration to show upcoming Formula 1 races, including race countdown and schedule.
Community user Tiidler has used the sensors from this integration to create a fully custom F1 dashboard card in Home Assistant, displaying race schedule, standings, podium results, and weather, all styled to fit their setup.
Note
This integration relies entirely on the amazing Jolpica-F1 API, which provides high-quality and up-to-date Formula 1 data for free.
If you find this integration useful, please consider supporting the creator of the API by donating to their Ko-fi page: https://ko-fi.com/jolpic
Without this API, this integration would not be possible, so any support helps keep it live and maintained. 🙏
Contributions, bug reports, and feedback are welcome. Please feel free to open issues or pull requests on GitHub.


