diff --git a/src/Components/HMI/ui/ENV_SETUP.md b/src/Components/HMI/ui/ENV_SETUP.md
new file mode 100644
index 000000000..62d9bb74c
--- /dev/null
+++ b/src/Components/HMI/ui/ENV_SETUP.md
@@ -0,0 +1,46 @@
+# Environment Setup Guide
+
+This guide explains how to configure the `.env` file for the HMI service so it works correctly both locally and on the live server.
+
+## What is `.env`?
+
+The `.env` file holds environment-specific settings such as the website address (`CLIENT_URL`) and the backend API host (`API_HOST`). The same code is used everywhere — only the `.env` file changes between local and live environments.
+
+## Initial Setup
+
+1. Navigate to the HMI UI folder: `src/Components/HMI/ui/`
+2. Create a new file named `.env` (copy from `.env.example` if it exists).
+3. Add the following variables:
+
+```
+API_HOST=localhost
+CLIENT_URL=http://localhost:8080
+```
+
+## Variable Descriptions
+
+- `API_HOST` — Backend API host. Locally set to `localhost`. Automatically switches to `api-service` in Kubernetes via the ConfigMap.
+- `CLIENT_URL` — Frontend URL used for Stripe redirects and password reset emails. Locally set to `http://localhost:8080`. On the live server, this is provided by the Cloud team.
+
+## Updating `CLIENT_URL` for Live Server
+
+When the Cloud team provides the live server URL (e.g. `http://4.147.145.111:8080`), update the `.env` file on the live server only:
+
+```
+CLIENT_URL=http://4.147.145.111:8080
+```
+
+Then restart the server so the new value takes effect.
+
+## Verification
+
+After updating, the connection status badge on the admin dashboard will display:
+- `Running in Local Mode — API connected successfully.` when running locally.
+- `Running in Live Mode — API connected successfully.` when running on the live server.
+- `Live server URL not configured yet, running in local fallback mode.` if `CLIENT_URL` is empty or misconfigured.
+
+## Troubleshooting
+
+- **Badge shows "Cannot connect to backend API"** → The backend API service is not running or unreachable. Check that all Docker containers are up.
+- **Badge shows "Fallback Mode"** → `CLIENT_URL` is not set correctly in the `.env` file.
+- **Changes to `.env` not taking effect** → Restart Docker with `docker compose down && docker compose up --build`.
\ No newline at end of file
diff --git a/src/Components/HMI/ui/public/admin/dashboard.html b/src/Components/HMI/ui/public/admin/dashboard.html
index a929feb0d..facbbdb13 100644
--- a/src/Components/HMI/ui/public/admin/dashboard.html
+++ b/src/Components/HMI/ui/public/admin/dashboard.html
@@ -28,6 +28,12 @@
+
+
+Loading status...
+
+
+
diff --git a/src/Components/HMI/ui/public/js/api-status.js b/src/Components/HMI/ui/public/js/api-status.js
new file mode 100644
index 000000000..45dee00ff
--- /dev/null
+++ b/src/Components/HMI/ui/public/js/api-status.js
@@ -0,0 +1,80 @@
+// =============================================================
+// API Status & Environment Detection
+// Sprint 2 - Frontend API Environment Validation
+// =============================================================
+
+/**
+ * Test if the API connection is working.
+ * Returns true if reachable, false if not.
+ */
+async function testApiConnection() {
+ try {
+ const response = await fetch('/iot/nodes', { method: 'GET' });
+ return response.ok;
+ } catch (error) {
+ console.error('API connection test failed:', error);
+ return false;
+ }
+}
+
+/**
+ * Determine which environment the frontend is running in.
+ * Returns: "Local Mode", "Live Mode", or "Fallback Mode"
+ */
+function getEnvironmentMode() {
+ const host = window.location.hostname;
+
+ if (host === 'localhost' || host === '127.0.0.1') {
+ return 'Local Mode';
+ } else if (host.match(/^\d+\.\d+\.\d+\.\d+$/) || host.includes('project-echo')) {
+ return 'Live Mode';
+ } else {
+ return 'Fallback Mode';
+ }
+}
+
+/**
+ * Get a user-friendly status message based on environment and connection.
+ */
+function getStatusMessage(connected, mode) {
+ if (mode === 'Fallback Mode') {
+ return 'Live server URL not configured yet, running in local fallback mode.';
+ }
+ if (!connected) {
+ return 'Cannot connect to backend API. Please check your configuration.';
+ }
+ return `Running in ${mode} — API connected successfully.`;
+}
+
+/**
+ * Update the status display on the page.
+ * Looks for an element with id="api-status-badge" to update.
+ */
+async function updateApiStatus() {
+ const badge = document.getElementById('api-status-badge');
+ if (!badge) return;
+
+ const mode = getEnvironmentMode();
+ const connected = await testApiConnection();
+ const message = getStatusMessage(connected, mode);
+
+ badge.textContent = message;
+ badge.style.padding = '6px 12px';
+ badge.style.borderRadius = '6px';
+ badge.style.fontSize = '12px';
+ badge.style.fontWeight = '500';
+
+ if (connected && mode !== 'Fallback Mode') {
+ badge.style.backgroundColor = '#d4edda';
+ badge.style.color = '#155724';
+ } else {
+ badge.style.backgroundColor = '#f8d7da';
+ badge.style.color = '#721c24';
+ }
+}
+
+// Run once on page load, then refresh every 30 seconds
+document.addEventListener('DOMContentLoaded', () => {
+ updateApiStatus();
+ setInterval(updateApiStatus, 30000);
+});
\ No newline at end of file