**Author:** Kristoffer Pettersson (kp222uv)
# Overview
A tutorial on how to set up a photoresistor with raspberry pi pico w and store plus visualize its data on adafruit with a webhook on discord to get notification when its dark to turn on the lights.
**Estimated time:** 2-4hours for a beginner
# Objective
I got the idea from home automation videos which I think is a neat thing, having a home that sorts of communicates with you.
It's purpose is to make a daily activity a tad easier and funnier.
It will teach you a basic setup with a sensor (photresistor) and raspberry pi pico w, how to connect it with a broker (adafruit) to store and visualize data there and it will also teach you how to create a trigger (webhook) for certain data points.
# Material
All materials bought from electrokit.com
| Item | Description | Price |
| -------- | -------- | -------- |
| Raspberry Pi Pico WH | Microcontroller | 109.00 SEK |
| Photoresistor CdS 4-7 kohm | Light sensor | 8.00 SEK |
| 3x Jumperwires male-male | To connect the items | 49.00 SEK (40x) |
| USB-kabel A-male – mini B male 5p 1.8m | Connect pico w to computer | 39.00 SEK |
| Resistor 0.25W 10kohm (10k) | Regulate electrical current | 49 SEK (40x) |
The raspberry pi pico w is a cheap and beginner friendly microcontroller which I can recommend for an easy start into the world of IoT.
# Computer setup
I used a laptop with windows OS and the IDE im using is VSCode. Here follows a guide for the steps required.
1. Download and install [VSCode](https://code.visualstudio.com/)
2. Download and install [Node js](https://nodejs.org/en)
3. Open VS Code and then the Extensions manager from: the left panel icon OR from View >> Extensions OR by pressing Ctrl+Shift+X.
4. Look for Pymakr and Install it. (Follow the numbered steps of the following figure) 
**Firmware update**
**Step 1:** Remove the ESD sponge from the Pico before proceeding. (The black sponge attached under your pico).
**Step 2:** Download the micropython firmware from [this](https://micropython.org/download/rp2-pico-w/) website. You will get a uf2 file, be sure to download the latest one from the Releases category and not Nightly Builds.
**Step 3:** Connect the micro-usb end of your cable (the small side) into the Raspberry Pi Pico, be sure to firmly hold the back of the USB slot so that by pushing you will not bend it. The USB won’t have to be entered fully, it’s normal that a small gap will be left out from the slot.
**Step 4:** While holding the BOOTSEL key down on the board, connect the USB type A end of your cable (the big side) into your computer’s USB port. If you want to be extra safe avoid using a USB hub and prefer the ports on your desktop/laptop computer. You can release the BOOTSEL after connecting it to your computer.
**Step 5:** You will see a new drive open in your file system named RPI-RP2 which is the Raspbbery Pi Pico storage. You can copy/paste the uf2 in this storage.
**Step 6:** Wait until your board automatically disconnects from your computer and reconnects.
**Warning**
Do not remove the USB during installation as it might harm the hardware or you might have to re do the previous steps.
**Firmware guide and app/extension installtion was borrowed from the IoT roadmap in the applied IoT course**
**Uploading code**
You simply create a .py file, for example main.py and upload or write your code there.
# Putting everything together
The picture of the circuit diagram includes an Arduino instead of the pico w. The power is from the pico w's 3v3v out pin instead, the ground just goes from a ground pin of the pico w and the GP26 for data flow instead of the A0 used in the picture of the Arduino. (Check the bottom of the tutorial for a picture of the setup)

**The platform** ive chosen as [adafruit](https://io.adafruit.com/). Its free and beginner friendly to use, offers several different types of dashboards to visualize your data and you can also have several topics if youd like. Its also possible to do cool triggers with email or discord for example, this means you will get a mail or message on discord if a specific type of data occurs that you choose. (More on this later)
Going forward if I was to scale the project I would probably use docker to setup a TIG-stack.
# Code
```
# main.py -- put your code here!
import time # Allows use of time.sleep() for delays
from lib.mqtt import MQTTClient # For use of MQTT protocol to talk to Adafruit IO
import ubinascii # Conversions between binary data and various encodings
import machine # Interfaces with hardware components
import micropython # Needed to run any MicroPython code
import random # Random number generator
from machine import ADC, Pin # Define pin
# BEGIN SETTINGS
led = Pin("LED", Pin.OUT) # led pin initialization for Raspberry Pi Pico W
photoPIN = 26 #The ADC pin of Pico W
# Adafruit IO (AIO) configuration
AIO_SERVER = "io.adafruit.com"
AIO_PORT = 1883
AIO_USER = "krpe"
AIO_KEY = "your key"
AIO_CLIENT_ID = ubinascii.hexlify(machine.unique_id()) # Can be anything
AIO_LIGHTS_FEED = "krpe/feeds/picow"
AIO_BRIGHTNESS_FEED = "krpe/feeds/brightness"
# END SETTINGS
# Function to gather data from photoresistor
def readLight(photoGP):
photoRes = ADC(Pin(26))
light = photoRes.read_u16()
# Function to publish result of the photoresistor to Adafruit IO MQTT server at fixed interval
def send_brightness():
while True:
client.publish(topic=AIO_BRIGHTNESS_FEED, msg=str(readLight(photoPIN)))
time.sleep(60)
# Callback Function to respond to messages from Adafruit IO
def sub_cb(topic, msg): # sub_cb means "callback subroutine"
print((topic, msg)) # Outputs the message that was received. Debugging use.
if msg == b"ON": # If message says "ON" ...
led.on() # ... then LED on
elif msg == b"OFF": # If message says "OFF" ...
led.off() # ... then LED off
else: # If any other message is received ...
print("Unknown message") # ... do nothing but output that it happened.
# Use the MQTT protocol to connect to Adafruit IO
client = MQTTClient(AIO_CLIENT_ID, AIO_SERVER, AIO_PORT, AIO_USER, AIO_KEY)
# Subscribed messages will be delivered to this callback
client.set_callback(sub_cb)
client.connect()
client.subscribe(AIO_LIGHTS_FEED)
print("Connected to %s, subscribed to %s topic" % (AIO_SERVER, AIO_LIGHTS_FEED))
try: # Code between try: and finally: may cause an error
# so ensure the client disconnects the server if
# that happens.
while 1: # Repeat this loop forever
client.check_msg()# Action a message if one is received. Non-blocking.
send_brightness() # Send a random number to Adafruit IO if it's time.
finally: # If an exception is thrown ...
client.disconnect() # ... disconnect the client and clean up.
client = None
print("Disconnected from Adafruit IO.")
```
**This** is the main.py file and the basis of it comes from the roadmap but then ive incorporated two functions to gather data and send data to the broker from the photoresistor.
# Transmitting the data / connectivity
I choose to use wifi for connection and mqtt plus a webhook as transport protocls. Code for using mqtt is found [here](https://github.com/iot-lnu/applied-iot/blob/master/Pycom%20Micropython%20(esp32)/network-examples/mqtt_ubidots/mqtt.py).
And you also need code to connect to your wifi which you find below (data is sent once every 60 seconds which is found in the code snippet under section "Code")
```
# boot.py -- run on boot-up
def do_connect():
import network
from time import sleep
import machine
wlan = network.WLAN(network.STA_IF) # Put modem on Station mode
if not wlan.isconnected(): # Check if already connected
print('connecting to network...')
wlan.active(True) # Activate network interface
# set power mode to get WiFi power-saving off (if needed)
wlan.config(pm = 0xa11140)
wlan.connect(SSID, password) # Your WiFi Credential
print('Waiting for connection...', end='')
# Check if it is connected otherwise wait
while not wlan.isconnected() and wlan.status() >= 0:
print('.', end='')
sleep(1)
# Print the IP assigned by router
ip = wlan.ifconfig()[0]
print('\nConnected on {}'.format(ip))
return ip
# WiFi Connection
try:
ip = do_connect()
except KeyboardInterrupt:
print("Keyboard interrupt")
```
# Presenting the data
Data is presented in a flow chart as shown in the picture below. Data is saved every 60 seconds.

As mentioned previously, im also using a webhook that sends a message to my discord server everytime I gather values of 60.000 or greater (which in my opinion dark enough to turn on the lights).
To create a webhook create a discord server first.
1. Go into channel settings.
2. Integrations.
3. Create webook.
4. Copy webhook.
5. Go to [adafruit](https://io.adafruit.com/).
6. Go to "Action" page.
7. Create new action.
8. 
9. Complete!
# Finalizing the design

Overall I am happy with my project as a total beginner on working with hardware and almost a beginner on python. If I were do to the project again I would aim for a more sophisticated setup with several sensors operating and I would also try to setup a TIG-stack with docker to visualize and save my data.