# Temperature and humidity: for all your plant needs
###### tags: `tutorials` `pycom` `fipy` `pysense` `temperature` `humidity`
> Student name: Moa Haldorson
> Student-ID: mh226ek
This tutorial provides a step by step guide on how to build and deploy a simple Internet of Things solution that measures temperature and humidity for your plants.
Estimated time for completion: 2 hours
## Objective
The reason I decided to do this project is because I have an interest in plants and enjoy taking care of them. All plants have different preferences when it comes to watering, temperature, humidity and light. I wanted to improve my knowledge of the environment in my apartment and whether or not it is optimal for my plants and their ability to thrive.
The main purpose that this device will serve is to sense and visualize data regarding temperature and humidity in my apartment.
I believe my device will provide insights on how I can improve the care of my plants in regards to temperature and humidity. I will get a better understanding of the environment in my apartment and therefore be able to know if it is suitable for my plants. I will also be able to take action based on the provided data and improve the environmental conditions in my apartment, for example by changing the position of the plants or investing in a humidifier.
## Material
The following list contains information about all the required products for this project. For this project I purchased a component set from Electrokit, containing all the neccessary parts ([link](https://www.electrokit.com/produkt/lnu-1dt305-tillampad-iot-fipy-and-sensors-bundle/)).
You will also need a laptop or computer with USB port in order to upload code to the device.
| Product | Description | Where to buy | Price |
| ------------- | ----------------------------------------------------------------------------------------------------------------------------------------------- | -------------------------------------------------------------------------------------------------------------------------- | ------- |
| FiPy | Micropython programmable microcontroller. Provides a powerful CPU with five different network options: WiFi, BLE, cellular LTE-CAT M1/NB1, LoRa and Sigfox. | [Link](https://pycom.io/product/fipy/) | 640 SEK |
| Pysense 2.0 X | The Pysense 2.0 X is a sensor shield, a board that contains extra pins so you can connect more sensors to your microcontroller. It contains the following built in sensors:<br>- Ambient light<br>- Barometric pressure<br>- Humidity<br>- Accelerometer<br>- Temperature | [Link](https://pycom.io/product/pysense-2-0-x/) | 320 SEK |
| USB cable | For powering the device and uploading code to the microcontroller. | [Link](https://www.kjell.com/se/produkter/mobilt/ladda-koppla/kablar-adaptrar/micro-usb-kablar/micro-usb-kabel-1-m-p68687) | 100 SEK |
> <img src="https://i.imgur.com/8zdOSyV.png" alt="FiPy" style="width: 300px"><br>Fig. 1. FiPy with headers. [Pycom.io](https://pycom.io/product/fipy/)
> <img src="https://i.imgur.com/Bs0Gc4J.png" alt="Pysense" style="width: 300px"><br>Fig. 2. Pysense 2.0 X. [Pycom.io](https://pycom.io/product/pysense-2-0-x/)
## Computer setup
The following section includes all the neccessary steps for setting up your computer for the project. The tutorial is aimed for Mac users.
### IDE setup
We begin by installing the chosen IDE for this project: Atom.
* **Step 1:** Download and install Node.js [here](https://nodejs.org/en/).<br>(This is needed for the Pymkr plugin in Atom)
* **Step 2:** Download and install Atom [here](https://atom.io/).
* **Step 3:** Install the Pymkr plugin in Atom by navigating to `Atom -> Preferences -> Install` and search for the plugin.
### Pycom firmware update
* **Step 1:** Mount the FiPy on the expansion board as shown in Fig. 3.
> <img src="https://i.imgur.com/M4bBhgI.jpg" alt="fipy mounted on pysense" style="width:300px"><br>Fig. 3. FiPy mounted on top of Pysense.
* **Step 2:** Connect the expansion board to your computer with a USB cable.
* **Step 3:** Download and install the Pycom Firmware Update tool [here](https://software.pycom.io/findupgrade?product=pycom-firmware-updater&type=all&platform=macos&redirect=true).
* **Step 4:** Open the Firmware Update tool and press `Continue` until you get to the Communication section:
* On port select the **/dev/cu.usbserial0001** .
* For type select **development**.
* Make sure to check **Advanced Settings** and then press `Continue`.
* **Step 5:** The tool should automatically detect your board. In the Advanced Settings:
* Make sure to check **Erase during update**, **CONFIG partition** and **NVS partition**.
* For file system select **FatFS** and then press `Continue`.
* When the update is complete you can press `Done`.
### Pycom expansion board update
As mentioned when starting up the Pycom Firmware Update tool, you may need to update the firmware of the **Pysense** as well and to do so follow [this guide](https://docs.pycom.io/updatefirmware/expansionboard/) (make sure to choose the right DFU file).
### Uploading code
In order to upload code to the device you need to setup a project in Atom. By following these steps we will upload some simple code to test it out.
* **Step 1:** Open Atom and create a new project by pressing the `Add folders` button in the left panel.
* **Step 2:** Create a folder on any desired location and press `Open`.
* **Step 3:** Right-click on the project folder in the left panel and press `New file` and name it `main.py`*.
* **Step 4:** Copy the lines of code below and paste it into `main.py` and hit save.
```
import pycom
import time
pycom.heartbeat(False)
while True:
pycom.rgbled(0xFF0000)
time.sleep(1)
pycom.rgbled(0x00FF00)
time.sleep(1)
pycom.rgbled(0x0000FF)
time.sleep(1)
```
* **Step 5:** Press `Upload project to device` to upload the code.
* **Step 6:** Now the LED light on the FiPy should be alternating blinking in red, green and blue.
*Every project requires a `main.py` as it is the starting point for executing code.
## Putting everything together
In terms of putting everything together for this project, it is as simple as mounting the FiPy on the Pysense and connect it to your computer with a USB cable. The sensors are built in on the expansion board and will not require any external wires for connection.
It is possible to separate the FiPy and Pysense by mounting the expansion board onto a breadboard and connect it with jumper wires. Doing so will enable you to connect external sensors.
> <img src="https://i.imgur.com/jjO2ePr.png" alt="fipy on pysense" style="width: 300px"><br>
> Fig. 4. FiPy mounted on Pysense. [Pycom.io](https://pycom.github.io/pydocs/gettingstarted/connection/fipy.html#third)
## Platform
In this project Datacake was used as the chosen IoT platform. It is a cloud based platform with MQTT broker that provides simple yet effective dashboards. For this project we will focus on the single value dashboards that can show temperature and humidity in real time. Datacake is free to use with up to two devices and requires no prior programming skills. This platform is quite suitable for our simple at home project.
To start using Datacake you need to create an account which can be done [here](https://app.datacake.de/signup).
## The code
The following section presents code of the core functionality of our IoT device. Your project should contain the following files before proceeding:
* `main.py`
* `boot.py`
* `config.py`
* `mqtt.py`
Your project should also contain a folder called **lib** where we will store the library for our chosen sensor. You can download the neccessary library from [here](https://github.com/pycom/pycom-libraries/releases/). The sensor is called **SI7006A20** and you place the corresponding file inside our **lib** folder.
Inside `main.py` we begin by importing all neccessary libraries.
```python=
import time
import ujson
import machine
import config
import pycom
from SI7006A20 import SI7006A20 # The temperature and humidity sensor
from mqtt import MQTTClient
```
Then we setup the sensor and read the values of temperature and humidity in a continous loop.
```python=
# Sensor Setup
si = SI7006A20()
while True:
# Get sensor values
temperature = si.temperature()
humidity = si.humidity()
```
The remaining files will be configured in the upcoming sections.
## Transmitting the data / connectivity
For this project we are using WiFi to transmit data over the Internet. Since the device is supposed to be used at home and not over long distances, WiFi is the optimal choice. The device will be transmitting data once every hour since temperature and humidity does not change that frequently.
Our device transfers the data with MQTT to the Datacake MQTT broker with the credentials entered in `config.py`. This provides security and prevents others from publishing and subscribing to our feeds.
### WiFi setup
In order to setup the WiFi connection we put the following code into `boot.py`:
```python=
import network
import time
import config
wlan = network.WLAN(mode=network.WLAN.STA)
wlan.connect(config.WIFI_SSID, auth=(network.WLAN.WPA2, config.WIFI_PASS))
while not wlan.isconnected():
time.sleep_ms(50)
print(wlan.ifconfig())
print("Connected to Wifi")
```
The `boot.py` file runs every time we boot up our device, before `main.py` executes. The WiFi SSID and password needs to be provided in `config.py` as such:
```python=
WIFI_SSID = 'your_wifi_ssid'
WIFI_PASS = 'your_wifi_password'
```
### MQTT setup
In order to setup the MQTT broker for our device we first need to copy some code from [here](https://raw.githubusercontent.com/pycom/pycom-libraries/master/lib/mqtt/mqtt.py) and paste it into `mqtt.py`.
After that we put the following code inside `main.py`:
```python=
def sub_cb(topic, msg):
print(msg)
# MQTT Setup
client = MQTTClient(config.SERIAL_NUMBER,
config.MQTT_BROKER,
user=config.TOKEN,
password=config.TOKEN,
port=config.PORT)
client.set_callback(sub_cb)
client.connect()
print('Connected to MQTT broker')
# The MQTT topics to publish data to
my_topic_temp = config.TOPIC_TEMP
my_topic_humi = config.TOPIC_HUMI
```
Inside our while loop (also in `main.py`) we input the following code that publishes our data to the MQTT broker:
```python=
client.publish(topic=my_topic_temp, msg=str(temperature))
client.publish(topic=my_topic_humi, msg=str(humidity))
client.check_msg()
print("Send data to MQTT broker, sleeping for 1 hour...")
time.sleep(3600) # Wait 1 hour (3600 seconds)
```
### Datacake setup
In order to setup our Datacake connection we must first create an account and add our device.
* **Step 1:** Navigate to `Devices` and press `Add Device`.
* **Step 2:** Select `API` and press `Next`.
* **Step 3:** Select `New Product`, give it a name and press `Next`.
* **Step 4:** Fill in a **serial number** for your device (it can be anything but it is important that you do not leave it empty), give the device a name and press `Next`.
* **Step 5:** Select the free plan and press `Add 1 Device`.
In order to visualize our sensor data we need to create two corresponding fields for our temperature and humidity values.
* **Step 1:** Navigate to your device and press `Configuration`.
* **Step 2:** Scroll down to the **Fields** section and press `Add Field`.
* **Step 3:** Define **Type**, **Name**, **Unit** and press `Add Field`.
* **Step 4:** Repeat steps 1-3 and create one more field for humidity.
In order to update the newly created fields we must know what **Topics** to publish to. Navigate to your device, scroll down to **Integrations** and press `Configure`. In the pop up we will find the topic ending with [FIELD_NAME].
Inside `config.py` we will now input our Datacake credentials like this:
```python=
SERIAL_NUMBER = 'your_chosen_serial_number'
MQTT_BROKER = 'mqtt.datacake.co'
TOKEN = 'ACCOUNT_TOKEN'
PORT = 1883
TOPIC_TEMP = 'dtck-pub/samplename/5ef47349-2606-47a1-9719-26edfa729cf7/YOUR_FIELD_NAME'
TOPIC_HUMI = 'dtck-pub/samplename/5ef47349-2606-47a1-9719-26edfa729cf7/YOUR_FIELD_NAME'
```
The serial number is provided on your device page. Your account token can be found under `Profile -> Edit Profile -> API -> Show`. The topics can be found as mentioned above.
## Presenting the data
We will visualize our data in Datacake via a dashboard. The data will be saved once every hour. In order to create a dashboard follow these simple steps:
* **Step 1:** Press the toggle button on the far right.
* **Step 2:** Press `Add Widget` and select `Value`.
* **Step 3:** Give your widget a name and select the corresponding field.
* **Step 4:** Press `Save` and toggle the button on the far right again.
* **Step 5:** Repeat steps 1-4 and create another widget for our second value.
The result will be something like this:
<img src="https://i.imgur.com/HKlCpIe.png">
## Finalizing the design
This is the final result of the project.
<img src="https://i.imgur.com/M4bBhgI.jpg" alt="fipy mounted on pysense" style="width:300px"><br>
<img src="https://i.imgur.com/HKlCpIe.png">
I think the project went pretty well although I had many issues with connection and updating the firmware. I would have liked to have a sensor for measuring soil moisture as an expanded version of this project.