This custom ESPHome component allows integration with an Attraccess API to monitor the status of resources in real-time. It uses Server-Sent Events (SSE) to establish a persistent connection to your API and receive real-time updates when the resource status changes.
- Real-time updates using Server-Sent Events (SSE)
- Persistent connection to your API (no polling)
- Automatic reconnection if connection is lost
- Works with public API endpoints (no authentication needed)
- Exposes a sensor to monitor resource status values
- Provides a binary sensor for API connectivity
- Allows ESPHome automations to be triggered based on status changes
To use this component, add it to your ESPHome configuration as an external component:
external_components:
- source:
type: git
url: https://github.com/jappyjan/Attraccess-esphome-components.git
components: [api_resource_status]
You can also use a specific reference (tag, branch, or commit):
external_components:
- source:
type: git
url: https://github.com/jappyjan/Attraccess-esphome-components.git
ref: main
components: [api_resource_status]
Make sure to place the component files in a components/api_resource_status
directory in your ESPHome configuration directory.
# Configure the component
api_resource_status:
api_url: http://your-api-url.example.com/api
resource_id: "12345" # Always use quotes for numeric resource_id values
refresh_interval: 30s # Used for reconnect attempts, not polling
# Authentication is not needed for public resources
# username: not_needed
# password: not_needed
- api_url (Required, string): The base URL of your API (must use HTTP, not HTTPS)
- resource_id (Required, string): The numeric ID of the resource to monitor. While this is configured as a string in YAML, it should be a numeric value as the API expects a number (e.g., use
"12345"
in your configuration for resource ID 12345) - refresh_interval (Optional, time): How often to attempt reconnection if the connection is lost, defaults to 60s
- username (Optional, string): Username for authentication (not needed for public resources)
- password (Optional, string): Password for authentication (not needed for public resources)
# Add a sensor to display the status
sensor:
- platform: api_resource_status
name: "Resource Status"
id: resource_status
unit_of_measurement: "%"
accuracy_decimals: 1
# Other standard sensor options are supported
# Add a binary sensor to show API availability
binary_sensor:
- platform: api_resource_status
name: "API Availability"
id: api_availability
# Other standard binary sensor options are supported
Your API needs to support Server-Sent Events (SSE) at the endpoint:
http://your-api-url.example.com/api/resources/{resource_id}/events
The API should send updates in the SSE format:
data: {"status": 0.75}
The value should be a number that represents the status of the resource. This value will be published to the sensor.
Here's a simple example of how to implement SSE for public resources on your server using Node.js and Express:
const express = require("express");
const app = express();
// Store connected clients for each resource
const clients = {};
// SSE endpoint - public access, no auth required
app.get("/api/resources/:resourceId/events", (req, res) => {
const resourceId = req.params.resourceId;
// Set SSE headers
res.setHeader("Content-Type", "text/event-stream");
res.setHeader("Cache-Control", "no-cache");
res.setHeader("Connection", "keep-alive");
// Send initial status
const currentStatus = getResourceStatus(resourceId);
res.write(`data: ${JSON.stringify({ status: currentStatus })}\n\n`);
// Add this client to the clients for this resource
if (!clients[resourceId]) {
clients[resourceId] = [];
}
clients[resourceId].push(res);
// Handle client disconnect
req.on("close", () => {
clients[resourceId] = clients[resourceId].filter(
(client) => client !== res
);
});
});
// Function to get current resource status
function getResourceStatus(resourceId) {
// Implementation to fetch resource status
return 0.75; // Example value
}
// Function to update all connected clients for a resource
function updateResourceClients(resourceId, status) {
if (clients[resourceId]) {
clients[resourceId].forEach((client) => {
client.write(`data: ${JSON.stringify({ status })}\n\n`);
});
}
}
// Example of updating a resource status
// This would be called whenever the resource status changes
function updateResource(resourceId, newStatus) {
// Update the status in your database or system
// ...
// Then notify all connected clients
updateResourceClients(resourceId, newStatus);
}
app.listen(3000, () => {
console.log("Server is running on port 3000");
});
You can use the sensor value to trigger automations:
automation:
- id: resource_status_critical
description: "Trigger when resource status is critical"
trigger:
- platform: numeric_state
entity_id: sensor.resource_status
below: 10 # Trigger when status below 10%
action:
- logger.log:
format: "Resource status is critically low: %.1f%%"
args: ["id(resource_status).state"]
See example_config.yaml
for a complete configuration example. The example already uses Git as the source, showing how to properly integrate this component using the repository URL.