{"id":1436,"date":"2024-11-10T21:06:53","date_gmt":"2024-11-11T03:06:53","guid":{"rendered":"https:\/\/www.nathanhunstad.com\/blog\/?p=1436"},"modified":"2024-11-10T21:06:53","modified_gmt":"2024-11-11T03:06:53","slug":"simple-home-observability-with-the-esp32-platform","status":"publish","type":"post","link":"https:\/\/www.nathanhunstad.com\/blog\/2024\/11\/simple-home-observability-with-the-esp32-platform\/","title":{"rendered":"Simple home observability with the ESP32 platform"},"content":{"rendered":"\n<p>It has long been a goal of mine to distribute temperature and humidity sensors around the house and track that data over time. Part of the reason is practical, to identify outliers and adjust things to be more consistent; part of it is because I just like having all the data.  Several years ago, I tried using some Bluetooth Low Energy (BLE) sensors I bought online, but the &#8220;short range&#8221; inherent in BLE was quite short range. Although I create a <a href=\"https:\/\/github.com\/huns0004\/SensorScanner\/blob\/master\/readsensor.py\" target=\"_blank\" rel=\"noopener\" title=\"\">Python project<\/a> to collect the data, I gave up pretty quickly due to the range issue.<\/p>\n\n\n\n<p>Fast-forward to today: we&#8217;ve moved to a new house, with more space and more need to track things. While 5 years ago the wifi-enabled sensors I looked at were far too expensive to be practical, I figured with the passage of time and Moore&#8217;s Law there would be some new options to play around with. A quick Reddit search pointed me to the <a href=\"https:\/\/en.wikipedia.org\/wiki\/ESP32\" target=\"_blank\" rel=\"noopener\" title=\"\">ESP32<\/a> platform and the <a href=\"https:\/\/www.bosch-sensortec.com\/products\/environmental-sensors\/humidity-sensors-bme280\/\" target=\"_blank\" rel=\"noopener\" title=\"\">BME280<\/a> temperature\/humidity\/pressure sensor, which immediately seemed promising: wifi, easy to configure, and inexpensive. I decided to give it a go, and much to my surprise it took just over an hour to get a functioning sensor on my network! In this blog post I&#8217;ll share how I got up and running.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\">Buying the components<\/h2>\n\n\n\n<p>The ESP32 board I got was <a href=\"https:\/\/www.amazon.com\/dp\/B0CP5FR172?ref=ppx_yo2ov_dt_b_fed_asin_title&amp;th=1\" target=\"_blank\" rel=\"noopener\" title=\"\">this one<\/a> from Amazon. The cost is only $20 for 3, a pretty amazing price when you think about it. For the BME280 sensor, I got this <a href=\"https:\/\/www.amazon.com\/gp\/product\/B0CTHN8461\/ref=ppx_yo_dt_b_asin_title_o01_s01?ie=UTF8&amp;psc=1\" target=\"_blank\" rel=\"noopener\" title=\"\">Waveshare<\/a> device for about $12. That means all in, it&#8217;s less than $20 for a single sensor, which is quite cheap compared to the other ones I was looking at.<\/p>\n\n\n\n<p>Physically assembling it was simple: following <a href=\"https:\/\/randomnerdtutorials.com\/esp32-bme280-arduino-ide-pressure-temperature-humidity\/\" target=\"_blank\" rel=\"noopener\" title=\"this tutorial\">this tutorial<\/a>, I connected the power and ground pins, as well as the clock and data pins to the two GPIO pins on the board. When that was done, I moved onto the next step: configuration.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\">Setup<\/h2>\n\n\n\n<p>To get things up and running as quickly as possible, I used the <a href=\"https:\/\/esphome.io\/\" target=\"_blank\" rel=\"noopener\" title=\"\">ESPHome<\/a> project. I installed it using PIP and soon enough I allegedly had the right EXE file&#8230;somewhere. Tracking it down due to how Windows saves Python apps was an adventure, but I eventually found it in &#8220;C:\\Users\\username\\AppData\\Local\\Packages\\PythonSoftwareFoundation.Python.3.12_qbz5n2kfra8p0\\LocalCache\\local-packages\\Python312\\Scripts&#8221;. Such an obvious place.<\/p>\n\n\n\n<p>From there, I followed <a href=\"https:\/\/esphome.io\/guides\/getting_started_command_line\" target=\"_blank\" rel=\"noopener\" title=\"\">yet another tutorial<\/a> to get a basic YAML config file set up for the sensor. I configured the wifi, and then added the <a href=\"https:\/\/esphome.io\/components\/i2c#i2c\" target=\"_blank\" rel=\"noopener\" title=\"\">I2C<\/a> and <a href=\"https:\/\/esphome.io\/cookbook\/bme280_environment.html#bme280-environment\" target=\"_blank\" rel=\"noopener\" title=\"\">sensor<\/a> configurations as appropriate:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>i2c:\n  sda: GPIO21\n  scl: GPIO22\n  scan: true\n  id: bus_a\n\nsensor:\n  - platform: bme280_i2c\n    temperature:\n      name: \"Main Bedroom Temperature\"\n    pressure:\n      name: \"Main Bedroom Pressure\"\n    humidity:\n      name: \"Main Bedroom Humidity\"<\/code><\/pre>\n\n\n\n<p>Next was to run the &#8220;esphome run&#8221; command, and here I ran into my first problem: figuring out what <a href=\"https:\/\/docs.platformio.org\/en\/latest\/platforms\/espressif32.html#boards\" target=\"_blank\" rel=\"noopener\" title=\"\">board<\/a> I had. Of course, the one I bought wasn&#8217;t listed, but it was shown as WROOM32 and so I went with &#8220;denky32&#8221; as the closest match, which seemed to work just fine.<\/p>\n\n\n\n<p>That took me to my next problem: after plugging it in and selected the USB-SERIAL connection, I kept on getting connection failed errors due to &#8220;Wrong boot mode detected (0x13)!&#8221; This one took a bit longer to track down, but I eventually learned that I had to put the chip into download mode by pressing the only two buttons on the chip (BOOT and EN) at the same time when doing the flash. Finally, after several tries, it flashed successfully!<\/p>\n\n\n\n<h2 class=\"wp-block-heading\">You&#8217;ve got data!<\/h2>\n\n\n\n<p>Board flashed, I eagerly awaited some word that it was working as intended. It didn&#8217;t take long at all to see that the sensor was detected and sending information:<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>&#91;16:53:40]&#91;D]&#91;sensor:094]: 'Main Bedroom Temperature': Sending state 22.68312 \u00b0C with 1 decimals of accuracy\n&#91;16:53:40]&#91;D]&#91;sensor:094]: 'Main Bedroom Pressure': Sending state 985.91486 hPa with 1 decimals of accuracy\n&#91;16:53:40]&#91;D]&#91;sensor:094]: 'Main Bedroom Humidity': Sending state 40.07617 % with 1 decimals of accuracy<\/code><\/pre>\n\n\n\n<p>The logs also showed that the device was connected to wifi, which I confirmed in my own DHCP logs. After little more than an hour, I had a working sensor! It didn&#8217;t look pretty, but it did the job.<\/p>\n\n\n\n<figure class=\"wp-block-image size-large\"><a href=\"https:\/\/www.nathanhunstad.com\/blog\/wp-content\/uploads\/2024\/11\/Sensor-2-scaled.jpg\"><img loading=\"lazy\" decoding=\"async\" width=\"1024\" height=\"873\" src=\"https:\/\/www.nathanhunstad.com\/blog\/wp-content\/uploads\/2024\/11\/Sensor-2-1024x873.jpg\" alt=\"\" class=\"wp-image-1440\" srcset=\"https:\/\/www.nathanhunstad.com\/blog\/wp-content\/uploads\/2024\/11\/Sensor-2-1024x873.jpg 1024w, https:\/\/www.nathanhunstad.com\/blog\/wp-content\/uploads\/2024\/11\/Sensor-2-300x256.jpg 300w, https:\/\/www.nathanhunstad.com\/blog\/wp-content\/uploads\/2024\/11\/Sensor-2-768x655.jpg 768w\" sizes=\"auto, (max-width: 1024px) 100vw, 1024px\" \/><\/a><figcaption class=\"wp-element-caption\">It&#8217;s not pretty but it works<\/figcaption><\/figure>\n\n\n\n<h2 class=\"wp-block-heading\">Next steps<\/h2>\n\n\n\n<p>OK, so I had a sensor, but where was that data going to go? Ultimately, as with every other log I use, I wanted to get the data into Elastic so I could query it and show dashboards. So far, I had the data, but I was missing a step. Enter <a href=\"https:\/\/www.home-assistant.io\/\" target=\"_blank\" rel=\"noopener\" title=\"\">Home Assistant<\/a>, and in the next blog I&#8217;ll show how I got that data into Home Assistant and then into Elastic using their API. Until next time!<\/p>\n","protected":false},"excerpt":{"rendered":"<p>In this blog post I talk about setting up a cheap temperature\/humidity sensor based on an EPS32 board and BME280 sensor combined with the ESPHome project.<\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"om_disable_all_campaigns":false,"_monsterinsights_skip_tracking":false,"_monsterinsights_sitenote_active":false,"_monsterinsights_sitenote_note":"","_monsterinsights_sitenote_category":0,"footnotes":""},"categories":[19],"tags":[],"class_list":["post-1436","post","type-post","status-publish","format-standard","hentry","category-tech-2","entry"],"aioseo_notices":[],"_links":{"self":[{"href":"https:\/\/www.nathanhunstad.com\/blog\/wp-json\/wp\/v2\/posts\/1436","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/www.nathanhunstad.com\/blog\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/www.nathanhunstad.com\/blog\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/www.nathanhunstad.com\/blog\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/www.nathanhunstad.com\/blog\/wp-json\/wp\/v2\/comments?post=1436"}],"version-history":[{"count":2,"href":"https:\/\/www.nathanhunstad.com\/blog\/wp-json\/wp\/v2\/posts\/1436\/revisions"}],"predecessor-version":[{"id":1441,"href":"https:\/\/www.nathanhunstad.com\/blog\/wp-json\/wp\/v2\/posts\/1436\/revisions\/1441"}],"wp:attachment":[{"href":"https:\/\/www.nathanhunstad.com\/blog\/wp-json\/wp\/v2\/media?parent=1436"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/www.nathanhunstad.com\/blog\/wp-json\/wp\/v2\/categories?post=1436"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/www.nathanhunstad.com\/blog\/wp-json\/wp\/v2\/tags?post=1436"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}