{"slug": "antimould-shower-sentinel", "title": "AntiMould Shower Sentinel", "summary": "A new smart device called AntiMould Shower Sentinel uses machine learning on an Arduino Q to detect shower sounds and check if an extractor fan is running, sending real-time alerts via Home Assistant on a Raspberry Pi 5 to prevent mould growth in UK bathrooms. The system addresses high humidity and poor ventilation in well-insulated homes by prompting users to turn on the fan, and also notifies them if the fan is left on unnecessarily.", "body_md": "**AntiMould Shower**** Sentinel** is a smart, ML‑powered device that listens for the sound of a running shower and instantly detects when the extractor fan hasn’t been switched on. By sending real‑time alerts to Home Assistant, it prompts the user to activate ventilation before humidity builds up. The result is simple but powerful: a low‑cost, automated way to prevent mould growth, protect bathroom surfaces, and keep your home healthier — all without installing new sensors or modifying existing wiring.\n\nIn the UK, **mould risk is significantly elevated** because showers generate high moisture loads in small, enclosed bathrooms. When the extractor fan is off, **relative humidity quickly exceeds 70–80%**, pushing surfaces toward the **dew‑point**, where condensation forms. UK homes are typically **well‑insulated with limited passive airflow**, so this moisture cannot dissipate naturally. The combination of **high humidity**, **cold external walls**, and **poor ventilation** creates ideal conditions for rapid mould growth, especially on grout, plasterboard, and silicone seals.\n\nWhen a user begins showering, the **Edge Impulse machine‑learning model running on the Arduino Q** identifies the acoustic signature of the shower. Once shower activity is confirmed, the system checks whether the **extractor fan is running** and continues monitoring for the next **20 minutes** to ensure proper post‑shower ventilation.\n\nIf the fan is **not detected** during or after the shower, the Arduino Q sends a signal to **Home Assistant**, running locally on a **Raspberry Pi 5**, which then triggers a mobile notification reminding the user to switch the fan on to prevent humidity build‑up and mould growth.\n\nThe system also handles the reverse scenario: if the user **forgets to turn the fan off**, Home Assistant sends a notification prompting them to switch it off, helping reduce unnecessary electricity.\n\nTo build this project from scratch, follow these steps:\n\n**1.****Set up your Home Assistant server on the Raspberry Pi 5**\n\nInstall Home Assistant OS or supervised setup so it can act as the central automation hub.\n\n**2.Connect your Home Assistant mobile app to your local server**\n\nThis enables secure local notifications and lets your phone receive alerts from the system.\n\n**3.Train Edge Impulse machine‑learning model**\n\nCollect shower‑sound samples, label them, and train a classifier capable of detecting shower activity reliably.\n\n**4.Deploy the trained model to the Arduino Q**\n\nExport the Edge Impulse model and flash it onto the Arduino Q so it can run inference locally at the edge.\n\n**5.Integrate the Edge Impulse model with Home Assistant**\n\nSend shower‑detection and fan‑status events from the Arduino Q to Home Assistant, enabling automated alerts and energy‑saving reminders.\n\nStep 1: Set up your Home Assistant server on the Raspberry Pi 5Please keep in mind that in this setup, the **Raspberry Pi 5 acts as the Home Assistant server**, while the **Arduino Q functions as the client running the ML model**. The Arduino Q detects both shower and extractor‑fan sounds, and based on this detection, it sends events to Home Assistant. Home Assistant then triggers mobile notifications to alert the user when ventilation is needed or when the fan has been left running unnecessarily.\n\n**128 GB SD Card**— Class 10 or better recommended** Raspberry Pi 5**— Board and case (optional but recommended)** Keyboard and Monitor**— HDMI-compatible display** Official Raspberry Pi 5 Power Supply**— 27W USB‑C PD supply\n\nFirst, you’ll need to flash **Home Assistant OS** onto the SD card and boot up the Raspberry Pi. The full instructions for this initial setup are provided in the link below, so please follow them carefully:\n\n[https://www.home-assistant.io/installation/raspberrypi/](https://www.home-assistant.io/installation/raspberrypi/)\n\nIf you don’t have an Ethernet connection available on your Raspberry Pi 5, follow the steps below **after installing Home Assistant OS** to connect to Wi‑Fi.\n\n1. Open the HA OS Terminal\n\nif you have a keyboard/monitor connected to the Pi, use the local console.\n\n2. Scan for available Wi‑Fi networks\n\nCode\n\n```\nnmcli device wifi list\n```\n\nThis shows SSIDs around you.\n\n3. Connect to your Wi‑Fi network\n\nReplace YOUR_SSID and YOUR_PASSWORD with your actual Wi‑Fi details:\n\nCode\n\n```\nnmcli device wifi connect \"YOUR_SSID\" password \"YOUR_PASSWORD\"\n```\n\nIf successful, you’ll see a confirmation message and the Pi will join your Wi‑Fi.\n\nStep2: Connect your Home Assistant mobile app to your local serverNow that Home Assistant is fully configured on your Raspberry Pi 5 and successfully connected to your Wi‑Fi network, the next step is to **enable communication between Home Assistant and the Home Assistant mobile app** so your system can deliver real‑time notifications to the user.\n\nYou need the official app to enable secure local notifications and device tracking.\n\n1.Download the **Home Assistant** app from the App Store (iOS) or Play Store (Android)\n\n2.Ensure your phone is connected to the **same Wi‑Fi network** as your Raspberry Pi 5\n\n3. Launch the app\n\n4.Wait for it to detect ** http://homeassistant.local:8123** or your Pi’s IP address\n\n5. Log In With Your Home Assistant Account\n\nThis links your phone to your Home Assistant user profile.\n\nAfter login, the app will automatically register your device. You will see your phone listed under **Settings → Devices & Services → Devices**\n\n**Enable Notifications**\n\nNotifications must be allowed both in the app and on your phone. In the app: go to **App Configuration → Notifications** and enable them\n\nOn your phone: allow notifications for the Home Assistant app in system settings\n\n**Test a Notification**\n\n* Please* follow the below steps to test a notification :\n\n- Verifies that your phone can receive alerts from Home Assistant.\n- In Home Assistant, go to\n**Developer Tools → Services** - Select\n`notify.mobile_app_<your_phone_name>`\n\n- Send a test message like:\n`{\"message\": \"Test notification\"}`\n\n- Confirm the notification appears on your phone\n\nWhen testing the full notification flow—from the **Arduino Q** to the **Home Assistant server** and finally to **mobile notifications**—I used a simple Python script on the Arduino Q to verify connectivity. To enable this communication, you must generate a **Long‑Lived Access Token** in your Home Assistant profile; this token securely links the Arduino Q with Home Assistant and your mobile device. Also ensure that the **Raspberry Pi (server)**, **Arduino Q**, and **mobile phone** are all connected to the **same Wi‑Fi network** for reliable local communication.\n\nYou must enable **Long‑Lived Access Tokens** in Home Assistant:\n\n**Profile → Long‑Lived Access Tokens → Create Token**\n\nTo run Python code on the Arduino Q, you’ll first need to complete a few essential setup steps. The following workflow outlines everything required to prepare the board, configure the environment, and ensure it can execute your Python scripts reliably.\n\n[https://docs.edgeimpulse.com/hardware/boards/arduino-uno-q](https://docs.edgeimpulse.com/hardware/boards/arduino-uno-q)\n\nA brief demo of the workflow is available in the Edge Impulse video link provided below.\n\n``` python\nimport requests# Home Assistant URL (use your local IP or homeassistant.local)HA_URL = \"http://homeassistant.local:8123/api/services/notify/mobile_app_your_phone\"# Replace mobile_app_your_phone with your mobile device name in Home Assistant# Replace with your long-lived access tokenTOKEN = \"YOUR_LONG_LIVED_ACCESS_TOKEN\"headers = {    \"Authorization\": f\"Bearer {TOKEN}\",    \"Content-Type\": \"application/json\",}data = {    \"message\": \"This was sent via the Home Assistant REST API\",    \"title\": \"Hello from Python\"}response = requests.post(HA_URL, headers=headers, json=data)print(\"Status:\", response.status_code)print(\"Response:\", response.text)\n```\n\nAfter running the Python script, I received a notification on my iPhone sent directly from the Arduino Q. This confirms that the end‑to‑end communication path is working correctly. Now we can move on to building the Edge Impulse ML model in the next step.\n\nIn Edge Impulse, we will follow a structured workflow to build the model. First, we create a dataset and label the audio samples using the four target classes: “Shower‑ON‑Extractor‑Fan‑Off”, “Shower‑ON‑Extractor‑Fan‑On”, “Shower‑Off‑Extractor‑Fan‑Off”, and “Shower‑Off‑Extractor‑Fan‑On”. After preparing and labeling the dataset, we begin training the machine‑learning model in Edge Impulse.\n\nBased on the validation results, we may need to refine the training parameters or collect additional samples to improve classification accuracy. Once the model achieves a satisfactory performance level, we proceed to deploy it to the **Arduino Q** using the generated **Arduino library**, enabling real‑time inference directly on the device.\n\nTo connect the Arduino Q board to the EI account, please follow the steps outlined in the link below.\n\nThe Arduino Q does not include a built‑in microphone, so I connected a USB Type‑C microphone through a USB hub to provide audio input.\n\nAfter installing the firmware, open the command window and type the following daemon command:\n\n`edge-impulse-linux`\n\nOnce the device is connected, navigate to the Data Acquisition section.\n\nBegin collecting audio data by recording the audio through Arduino Q. Here I recorded shower sound, Extractor fan sound and combination of both in edge impulse tool and labelled it as “Shower‑ON‑Extractor‑Fan‑Off”, “Shower‑ON‑Extractor‑Fan‑On”, “Shower‑Off‑Extractor‑Fan‑Off”, and “Shower‑Off‑Extractor‑Fan‑On”.\n\nModel training in Edge ImpulseIn the Create Impulse section, please set the Preprocessing block as MFE and select \"Classification\" as the learning block.\n\nThen generate the features and visualise to get high level overview of each labels.\n\nIn the NN settings, configure the training cycles as 100 and learning rate as 0.005. In the Neural Network section, configure the layers as indicated.\n\nI have used reshape layer to convert the audio data to 1D array and applied 1D convolution layer for model training. For improving the accuracy, I have used the drop out layer as well.\n\nThe model achieved an accuracy of 100% during the training phase, which is sufficient to proceed to the next step.\n\nDuring the testing phase, the model is evaluated using new datasets that were not incorporated in the training process. The Model achieved 100 % which is sufficient for hardware deployment.\n\nAfter validating the model, run the following command in the terminal to proceed.\n\nFirst we need to download the trained EIM file in the local machine.\n\n```\nedge-impulse-linux-runner --download modelfile.eim\n```\n\nNext, follow the steps below to install the Linux SDK on your Arduino Q. These steps are also available in the linked documentation, where I’ve highlighted the key actions for convenience.\n\nInstall a recent version of [Python 3 ](https://www.python.org/downloads/)(>=3.7).\n\nInstall the SDK\n\n```\npip3 install edge_impulse_linux\n```\n\nClone this repository to get the examples:\n\n```\ngit clone https://github.com/edgeimpulse/linux-sdk-python\n```\n\n(Optional) If you want to use the camera or microphone examples, install the dependencies:\n\n```\ncd linux-sdk-pythonpip install -r requirements.txt\n```\n\nThe `classify.py`\n\nexample located in `linux-sdk-python/examples/audio`\n\nis not directly compatible with the Arduino Q, as it cannot read audio data at the required frequency. I have modified the script and uploaded the updated version to my Git repository. The revised code loads audio buffers based on time‑based sampling and resamples them to match the model’s expected rate.\n\nDownload and keep the classify_EI.py and model [file.EIM](http://file.EIM) in `inux-sdk-python/examples/audio`\n\nand run the below command to execute the model classification in local.\n\n```\npython3 classify_EI.py modelfile.eim\n```\n\nStep 5: Integrate the Edge Impulse model with Home AssistantThe system receives continuous **audio data**, which is buffered and passed into the customised **EI_classify.py** script for processing..The script uses the embedded **EIM model** to generate a **classification result** for each audio window.\n\nA **classification label counter** inside `EI_classify.py`\n\ntracks how many consecutive times each label has appeared. When the label is either **“Shower‑ON‑Extractor‑Fan‑Off”** or **“Shower‑ON‑Extractor‑Fan‑On”**, and the count exceeds **DETECTION_COUNT_SHOWER_ON** (15 seconds), the system concludes that the shower is active.\n\nWhen this condition becomes true, the system **enables a timer** that will later verify whether the Extractor Fan is still switched ON after **5 minutes** (a configurable duration.\n\nIf the extractor‑fan‑ON condition is not satisfied, the system sends a notification prompting the user to switch on the extractor fan.\n\nWhen the label is either **“Shower‑Off‑Extractor‑Fan‑ON”** or **“Shower‑ON‑Extractor‑Fan‑On”**, and the count exceeds **DETECTION_COUNT_FAN_ON** (1 minute), the system determines that the extractor fan should be considered active.\n\nWhen this condition becomes true, the system **enables a second timer** that will later check whether the Extractor fan is still active after **20 minutes** (also configurable).\n\n- When the\n**shower‑active timer** expires, the system checks whether the label count for**“Shower‑Off‑Extractor‑Fan‑On”** is equal to zero. - If the count is zero, the system concludes that the extractor fan is not running while the shower is active.\n- When this condition is true, the system\n**sends a notification to Home Assistant**, prompting it to switch on the extractor fan for** 15–20 minutes**. - Home Assistant then forwards this notification to the user’s smartwatch or preferred device\n\n- When the\n**fan‑active timer** expires, the system checks whether the label count for**“Shower‑Off‑Extractor‑Fan‑ON”** is greater than**7**(a configurable threshold). - If this condition is true, the system determines that the extractor fan has been running long enough to reduce humidity.\n- The system then\n**sends a notification to Home Assistant** instructing it to switch off the extractor fan. - Home Assistant relays this message to the user’s smartwatch, confirming that humidity has reduced and the fan can be turned off.\n\nIn this prototype, I used a weather‑resistant enclosure, and the Arduino Q is powered by a portable power bank. For long‑term deployment, however, the 5‑volt supply should be provided through a dedicated wired power connection instead of a portable source.\n\nThis project can be further improved to achieve full autonomy by adding **Home Assistant automations** that automatically switch the extractor fan **on** or **off** based on shower detection events.\n\n[Read more](javascript:void(0))", "url": "https://wpnews.pro/news/antimould-shower-sentinel", "canonical_source": "https://www.hackster.io/manivannan/antimould-shower-sentinel-9b0d87", "published_at": "2026-06-13 05:09:52+00:00", "updated_at": "2026-06-25 21:46:37.404060+00:00", "lang": "en", "topics": ["machine-learning", "ai-products", "ai-tools", "ai-infrastructure"], "entities": ["AntiMould Shower Sentinel", "Edge Impulse", "Arduino Q", "Home Assistant", "Raspberry Pi 5"], "alternates": {"html": "https://wpnews.pro/news/antimould-shower-sentinel", "markdown": "https://wpnews.pro/news/antimould-shower-sentinel.md", "text": "https://wpnews.pro/news/antimould-shower-sentinel.txt", "jsonld": "https://wpnews.pro/news/antimould-shower-sentinel.jsonld"}}