I am trying to use an integration “swiss public transport” which allows to display the next connections from our nearest tram and bus station and which - in principle - is terrific and VERY useful. BUT it has a (probably not so seldom) issue: the service which it depends on allows only for 1000 requests a day.
Thus, if I let it run continuously, the display practically always shows only an error msg essentially rendering this integration useless.
I am wondering if one could change that constant polling to a mode where the integration only requests data while the corresponding widget is actually visible on-screen. One could then place that widget on a dashboard tab that one only displays when needing that info. Of course one must then never forget to hide that tab again after “consuming” the info to stop further requests, but I’ld say that would be acceptable.
Is it possible to signal from the UI widget to the underlying integration if and when the widget is actually “active” (i.e. being displayed on-screen)?
Of course that would require in the first place that the UI widget somehow “knows” that it is currently active on-screen. Not even sure if that is a given…
the documentation of the component has some details regarding the rate limit handling. It contains a hint on how to lower the refresh rate in case you need multiple location. Please check this.
The Swiss public transport API only allows 1000 requests per 24 hours. The default polling rate is set to 90s , which is just enough for one connection polling continuously. If more entries are needed, consider defining a custom polling interval to reduce the amount of requests.
Thanks for the response and sorry for the late reaction.
I had actually seen and considered this option to reduce the polling interval. However, there are 4 lines heading to different directions from our station. If I reduce the polling interval accordingly then it would poll the service only every 5 minutes or so. This would essentially make the service useless, since it displays departures relative to “now”. A display stating “in 3 minutes” but updated only every 5 minutes is not really helpful.
An indication whether that dashboard is visible and then polling the service once per minute only during such periods thus seemed more promising to me.
But I still lack the knowledge whether that’s possible and if so, how…
here is a script that you can install in your environment. It refreshes a defined entity every 3 minutes but only when the dashboard page “swisstrain” and the browser tab is active. You need to adjust the dashboard name and the entity name of your sensor - check the config block of the script. (not tested with the mobile app)
/**
* Home Assistant Dashboard Auto-Script
* Executes a script via WebSocket every 3 minutes, but only on the configured dashboard
*
* Installation:
* 1. Copy file to /config/www/dashboard-auto-script.js
* 2. In HA: Settings → Dashboards → Resources → Add Resource
* URL: /local/dashboard-auto-script.js
* Type: JavaScript Module
* 3. Clear browser cache / Hard Refresh (Ctrl+F5)
*/
(function() {
'use strict';
const CONFIG = {
// Dashboard path where the script should be active
dashboardPath: '/lovelace/swisstrain',
// Interval in milliseconds (3 minutes = 180000ms)
interval: 3 * 60 * 1000,
// Script sequence to execute
sequence: [
{
action: "homeassistant.update_entity",
data: {
entity_id: ["sensor.XXX-REPLACE-XXX"]
}
}
]
};
// Checks if we are on the configured dashboard
function isOnDashboard() {
const path = window.location.pathname;
return path === CONFIG.dashboardPath || path.startsWith(CONFIG.dashboardPath + '/');
}
// Checks if the browser tab is active/visible
function isTabVisible() {
return document.visibilityState === 'visible';
}
// Gets the hass object
function getHass() {
return document.querySelector('home-assistant')?.hass;
}
// Executes the script via WebSocket
async function executeScript() {
if (!isOnDashboard() || !isTabVisible()) {
console.log('[Dashboard Auto-Script] Skipped - not on dashboard or tab not active');
return;
}
const hass = getHass();
if (!hass || !hass.connection) {
console.error('[Dashboard Auto-Script] No connection to Home Assistant');
return;
}
try {
const result = await hass.connection.sendMessagePromise({
type: "execute_script",
sequence: CONFIG.sequence
});
console.log('[Dashboard Auto-Script] Script executed at', new Date().toLocaleTimeString(), result);
} catch (error) {
console.error('[Dashboard Auto-Script] Error:', error);
}
}
// Initialization
function init() {
console.log('[Dashboard Auto-Script] Started');
console.log('[Dashboard Auto-Script] Dashboard path:', CONFIG.dashboardPath);
console.log('[Dashboard Auto-Script] Interval:', CONFIG.interval / 1000, 'seconds');
console.log('[Dashboard Auto-Script] Sequence:', JSON.stringify(CONFIG.sequence));
// Start interval
setInterval(executeScript, CONFIG.interval);
// Optional: Execute immediately on load
// executeScript();
}
// Wait until HA is loaded
if (document.readyState === 'complete') {
init();
} else {
window.addEventListener('load', init);
}
})();