Telegram – Send Messages, Photos, Animated Gifs from your Raspberry Pi and RPi Web Cam

This tutorial has been created to work with RPi Web Cam Interface (for more details see: https://elinux.org/RPi-Cam-Web-Interface)

Telegram (an IM platform similar to WhatsApp) has the ability to send messages and pictures from your RPi Web Cam to your phone or desktop whenever motion is detected for instant notification. Plus it’s FREE! 🙂
 
To find out more visit: https://telegram.org
 
We will be using a Telegram Bot which is specifically designed to work with software, meaning that a message can be sent using bash scripts: https://telegram.org/blog/bot-revolution
 
Start by installing the Telegram app on your phone or desktop (this process will create your account – https://telegram.org), and then sign up for a Telegram bot using Botfather with the instructions here: https://core.telegram.org/bots#6-botfather.
 
Make a note of your API Token and bot username (the one that must end in bot)
 
We now need to obtain your bot’s chatid. To do this, enter the bot username in the Telegram search field (either in Contacts or Chats), then select the bot to initiate a chat with it, and then send a message. This process will establish a conversation (or chat) between you and the bot, identified as a chatid.
 
To find the chatid, enter the following URL in a browser (your API token goes after and right next to /bot):

https://api.telegram.org/botReplaceThisWithTheBotFatherToken/getUpdates

 
e.g, if your API is “123456789:jekcjrnekjrhteuncheiucnf”:

https://api.telegram.org/bot123456789:jekcjrnekjrhteuncheiucnf/getUpdates

 
You need the “id” number from the output it produces:

"message":{"message_id":2872,"from":{"id":987654321,

 
In the example above, this would be “987654321”
 
If you only see {“ok”:true,”result”:[]}, it means you haven’t yet sent your bot a message from your account.
 
Ok, so now that you have your API token and chatid, we can use the Pi to send you a message. Let’s send a test message to start with by entering the following from the Pi command line (substituting with your API and chatid where relevant):

curl -s -X POST https://api.telegram.org/bot123456789:jekcjrnekjrhteuncheiucnf/sendMessage -d text="A message from your bot" -d chat_id=987654321

 
Now we need to wrap this up in a script to send you notifications when motion is detected.

Create a new config file to store variables for Telegram

sudo nano /var/www/html/macros/configfile.cfg

Enter the following text into that file, replacing where necessary

#!/bin/bash
 
#Replace text within and including the arrow brackets <> with your own details
 
#Camera details
cameraName="<Mycam>"  
 
#Telegram details
tokenurl="https://api.telegram.org/bot<your API key>"
chatid="<your chat id>"
 
#Folder paths
webfolder="/var/www/html"
nomsg="/home/pi/nomsgfile.lck"
logfile="${webfolder}/scheduleLog.txt"
curlout="${webfolder}/curlout.txt"  #Keeps a log of the curl output for troubleshooting
 
 
#Logging function
logging () {
  #logging yes true "This is my error message"
  #$1 yes/no - send telegram msg
  #$2 true/false - disable audible notification or pop-up msg on receiving device
 
  ext="$1"
  notification="$2"
  msg="$3"
 
  NOW="`date +"-%Y/%m/%d %H:%M:%S-"`"
  echo "$msg"
  echo "${NOW} ${msg}" >> $logfile
  if [ $ext == "yes" ]; then
    curl -s \
      -X POST \
      ${tokenurl}/sendMessage \
      -d text="$msg" \
      -d disable_notification=${notification} \
      -d chat_id=${chatid} >> ${curlout} &
  fi
}

Create a new macro file that will be run whenever motion is detected

sudo nano /var/www/html/macros/motion_event.sh

Copy in the following text

#!/bin/bash
. /var/www/html/macros/configfile.cfg
 
#If you wish to disable notifications, create a file using "touch /home/pi/nomsgfile.lck"
if [ -f $nomsg ]; then
  logging no true "Message alerting has been disabled, exiting..."
exit
fi
 
#Copy the low res snapshot image from memory to a file
cp /dev/shm/mjpeg/cam.jpg ${webfolder}/cam_new.jpg
 
#On motion detection start (parameter is 1 for on, 0 for off)
fileparams=$1
if [ $fileparams -eq 1 ]
then
  #Send both a single text message and a photo because sometimes the photo message times out if the Telegram servers are busy
  
  logging yes false "Motion detected from ${cameraName}"
 
  curl -s -X POST \
    ${tokenurl}/sendPhoto \
    -F chat_id=${chatid} \
    -F photo="@${webfolder}/cam_new.jpg" \
    -F caption="Motion detected on ${cameraName}" >> ${curlout} &
 
fi

We now just need to make the motion_event.sh file executable and change the ownership:

sudo chmod +x /var/www/html/macros/motion_event.sh
sudo chown www-data:www-data /var/www/html/macros/motion_event.sh
sudo chown www-data:www-data /var/www/html/macros/configfile.cfg
Advertisements

Access Raspberry Pi Filesystem from Mac OSX using Netatalk AFP

This tutorial will explain how to browse your RPi Web Cam media folder from within Finder on MacOS.

    On your Raspberry Pi:

  1. Update packages and install netatalk
  2. sudo apt-get update
    sudo apt-get install netatalk
  3. Create a password for the www-data account
    sudo passwd www-data

    On your Mac:

  4. Open terminal and type the following
  5. open afp://<your-raspberrypi-ip>
  6. When the window pops up and asks for your username and password for the Raspberry Pi, enter www-data as the username, and the password you set above.
  7. You will now be able to browse the html folder and open video files from within media on your Mac.
  8. If the video file is opened in Preview, use the J K and L keys for the following:
    J = Press to reverse video. Press more than once to increase the speed.
    K = Play the video forward at normal speed.
    L = Fast forward the video. Press more than once to increase the speed.

 

Pushover Alerts for Motion Detection with RPi Web Cam Interface

UPDATE – Pushover has its limitations such as not being able to send photos and having to pay for the service. A better, free!, alternative is Telegram. For instructions, please see my tutorial here: https://quavoce.wordpress.com/2017/09/29/telegram-send-messages-photos-animated-gifs-from-your-raspberry-pi-and-rpi-web-cam/

This post describes how to use an online push notification service called Pushover to send you notifications on your mobile devices whenever an event occurs. In this example, we are using it with the excellent RPi Web Cam Interface (http://elinux.org/RPi-Cam-Web-Interface) to send you a message whenever motion is detected.

If you would like to create a secure HTTPS remote access to your cameras, be sure to check out my other post here:

  1. Signing and Setting up Pushover
    1. Sign up for an account here: https://pushover.net/login
    2. Make a note of your “user key” (copy it into a text editor for example)
    3. Select the Apps & Plugins link
    4. Click Create a new Application
    5. Give your app a name, and choose Script within the Type drop-down menu
    6. Tick the checkbox and press Create Application
    7. Make a note of your API/Token key.
  2. Install the Smartphone App or launch the desktop client
    1. Links to the apps are on the Pushover website under the Android, iOS, & Desktop link
  3. Create a script on the Pi
    1. At the command prompt, cd to the macros folder (substitute html for the folder you specified during setup)
    2. cd /var/www/html/macros/
    3. Create a start_vid.sh file using your favourite text editor (nano or vim for example – the latter of which needs to be installed using “sudo apt-get install vim” – nano is easier if you don’t know vim)
    4. sudo vim start_vid.sh
    5. Paste the following bash script into the file:
    6. time=`date +"%d-%m-%Y %T"`
      url="https://<MyDynamicURLorIP>/mycamera" #no trailing slash after html
      cameraName="myCam"
      
      filename=${1##*/}
      thumb=`echo $filename | awk -F "_" '{ print $2 }'`
      thumbname="v${thumb}.th.jpg"
      sendurl="${url}/media/${filename}.${thumbname}"
      streamurl="${url}/media/${filename}"
      livestream="${url}/min.php"
      
      curl -s \
        -F "token=yourAPITokenKey" \
        -F "user=yourUserKey" \
        -F "device=DeviceNames" \
        -F "message=Motion detected at $time. Live video Link: ${livestream} - Recorded video link (need to wait until recording has completed): ${streamurl}" \
        -F "title=Motion Detected from $cameraName" \
        -F "url=$sendurl" \
        -F "url_title=Click to open a still image showing detected motion" \
        https://api.pushover.net/1/messages.json > /dev/null 2>&1
    7. Save the file and the change the permissions so it can be executed
    8. sudo chmod +x start_vid.sh
      sudo chown www-data:www-data start_vid.sh
    9. Test it works
    10. sudo ./start_vid.sh /var/www/html/media/vi_0003_20160818_092213.mp4
    11. This should send a push message to your phone with a link to thumbnail for the above file (which obviously won’t work for you unless you already have a video with the exact date and time as above) 🙂

Full Reverse Proxy Instructions with Dynamic IP and HTTPS Encryption

The Goal

  • Secure reverse proxy running on a Raspberry Pi at home (using the latest NGINX web-server), so that you don’t have to open multiple ports to the internet on your router.
  • Dynamic DNS URL for various web applications at home, e.g RPi Web Cam Interface – http://elinux.org/RPi-Cam-Web-Interface
  • Official HTTPS certification from letsencrypt.org for free
    • So that you don’t have to login with your password being sent in the clear!
    • Required because self-signed certs don’t work when trying to view recorded RPi Cam video on an iPhone/iPad
  • Push notifications sent to your phone when events occur such as motion detection
  • One Raspberry Pi for the proxy and separate Pis for multiple RPi Web Cam Interface cameras

To summarise how this will work once built, you will have a single external access point into your home network via the secure HTTPS port 443 using something like https://mydomain.com/mycamera/.

This method is called a Reverse Proxy and runs on a Raspberry Pi using the NGINX (Engine X) web server. This web server software is used on many official websites on the internet, and is therefore a secure barrier between the internet and your home network.

A file on the proxy Pi called /etc/nginx/services.conf is used to redirect custom URL sub-paths (such as “mycamera” in the example above) to another internal web server on whatever port you need, such as a Pi running the video surveillance dvr software RPi Web Cam Interface – http://elinux.org/RPi-Cam-Web-Interface

Pre-requisites

You will need to know how to do the following:

  • Write a Jessie image to an SD card
  • Configure a static IP (a link is included below)
  • Edit text files from the command line
  • Using an SSH client from your computer such as Putty to connect to the Pi
  • Know how to configure your router for port forwarding

Set up the Pi and Install NGINX:

  1. Create a new Jessie image on an SD card (use whichever method is required for your computer).
  2. Once booted into the GUI, goto Preferences -> Raspberry Pi Configuration
    1. Change Boot to CLI
    2. Untick Auto Login
    3. Give it a new Hostname (eg proxypi)
    4. Set your timezone
    5. Enable SSH
    6. Press OK and reboot
  3. Log into the Pi using default user/pass (pi/raspberry)
  4. Determine assigned IP by running “hostname -I”. (The proxypi really should be connected via ethernet rather than wifi, and DHCP should have assigned you an IP)
  5. SSH to the Pi using this IP address from your computer (use Putty on Windows)
  6. Change the default password
  7. passwd
  8. Set a static IP on the Pi using these instructions: https://www.modmypi.com/blog/how-to-give-your-raspberry-pi-a-static-ip-address-update
  9. Reboot and log back in using the Static IP
  10. Update the Pi
  11. sudo apt-get update
    sudo apt-get upgrade
    reboot
  12. Install the latest NGINX. Edit the sources.list and add the stretch branch of raspbian
    1. Edit the sources.list file
    2. sudo nano /etc/apt/sources.list
    3. Add the following to the last line:
    4. deb http://mirrordirector.raspbian.org/raspbian/ stretch main contrib non-free rpi
  13. Prevent all packages using stretch unless specified:
    1. Create a new file:
      sudo nano /etc/apt/preferences
    2. Add the following lines:
    3. Package: *
      Pin: release n=jessie
      Pin-Priority: 600
  14. Update:
    sudo apt-get update
  15. Install NGINX:
    sudo apt-get install -t stretch nginx

Set up a Dynamic DNS Hostname

I’m using and paying for Dyn’s Dynamic DNS server due to it’s reliability: http://dyn.com/remote-access/
There are plenty of free options out there though so follow their instructions to set up a hostname and updater client if you prefer.
The instructions below explain how to install a client on the proxypi for automatic IP updates to Dyn. This assumes you’ve already created your dynamic hostname within “My Services -> DynDNS Pro”. (ddclient):

  1. Install ddclient
    sudo apt-get install ddclient
  2. Answer the questions when prompted
    – Other DNS Provider
    – Dynamic DNS Server: members.dyndns.org
    – Protocol: dyndns2
    – Username/password
    – Network: web
    – URL name.
  3. Generate your conf file from the following link: https://account.dyn.com/tools/clientconfig.html
    1. Within the webpage, select your host and client (ddclient)
    2. Compare the generated conf file with what was configured during setup (/etc/ddclient.conf) and update accordingly
      daemon=600
      protocol=dyndns2
      use=web, web=checkip.dyndns.com, web-skip='IP Address'
      server=members.dyndns.org
      login=your_username
      password='your_password'
      your_hostname
    3. Test by running
      sudo ddclient -daemon=0 -verbose

 

Configuring HTTPS with https://letsencrypt.org/

  1. You should already have a webpage that you can browse to on your local network:
  2. http://<your-proxy-raspi-ip>/

    This should give you the welcome nginx welcome page.

  3. Configure your router to forward port 80 and 443 to your proxy raspberry Pi IP
  4. Add the Jessie backports to your sources.list by editing
  5. sudo nano /etc/apt/sources.list
  6. Then add the following line
  7. deb ftp://ftp.uk.debian.org/debian jessie-backports main
  8. Update:
    sudo apt-get update

    (ignore any GPG errors)

  9. Install Certbot
    sudo apt-get install certbot -t jessie-backports
  10. Run certbot
    sudo certbot certonly --webroot -w /var/www/html -d your_domainname

    It will ask you for your email address as part of the setup.

  11. You should see a Congratulations! message
  12. Now follow the next section “Configuring NGINX

 

Configuring NGINX Proxy:

  1. Create a new nginx configuration for reverse proxy by editing the following file:
    sudo nano /etc/nginx/sites-available/main
  2. Copy the text below into the “main”text file and edit the entries as required.
  3. access_log off;
    add_header Cache-Control public;
    server_tokens off;
    # HTTP 80
    server {
    	listen 80;
    	server_name _;
    	return 301 https://<your-domainname.com>$request_uri?;
    }
    # HTTPS 443
    server  {
    	listen 443 ssl;
    	keepalive_timeout 70;
    	server_name <your-domainname.com>;
    	include /etc/nginx/ssl.conf;
    	include /etc/nginx/services.conf;
    }
  4. Create an ssl.conf file
  5. sudo nano /etc/nginx/ssl.conf
  6. Copy the following text into it
  7. ssl on;
    ssl_certificate /etc/letsencrypt/live/<your-domainname>/fullchain.pem;
    ssl_certificate_key /etc/letsencrypt/live/<your-domainname>/privkey.pem;
    
    ssl_session_cache shared:SSL:20m;
    ssl_session_timeout 180m;
    
    ssl_protocols TLSv1 TLSv1.1 TLSv1.2;
    
    ssl_prefer_server_ciphers on;
    ssl_ciphers ECDH+AESGCM:ECDH+AES256:ECDH+AES128:DH+3DES:!ADH:!AECDH:!MD5;
    
    ssl_dhparam /etc/nginx/cert/dhparam.pem;
  8. Create the services.conf file.
  9. sudo nano /etc/nginx/services.conf
  10. Add as many entries as you need.
  11. location /picam {
    proxy_pass http://internal-rpi-cam-ip2/html;
    include /etc/nginx/proxy.conf;
    }
    location /picam2 {
    proxy_pass http://internal-rpi-cam-ip2/html;
    include /etc/nginx/proxy.conf;
    }
    location /couchpotato {
    proxy_pass http://internal-cp-ip:4001/couchpotato;
    include /etc/nginx/proxy.conf;
    }
    location /sonarr {
    proxy_pass http://internal-sonarr-ip:8989/sonarr;
    include /etc/nginx/proxy.conf;
    }
  12. Create a proxy.conf file:
  13. sudo nano /etc/nginx/proxy.conf
  14. Copy the following text into this file
  15. proxy_redirect off;
    proxy_set_header Host $host;
    proxy_set_header X-Real-IP $remote_addr;
    proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
    client_max_body_size 10m;
    client_body_buffer_size 128k;
    proxy_connect_timeout 90;
    proxy_send_timeout 90;
    proxy_read_timeout 90;
    proxy_buffers 32 4k;
  16. Create a symbolic link to the main site
  17. sudo ln -s /etc/nginx/sites-available/main /etc/nginx/sites-enabled/main
  18. (Optional) Strengthen HTTPS key exchange by running the commands below (it takes around 5 mins to generate on a RPi 3 – go make dinner if on a Pi1 – Original Instructions found here: https://bjornjohansen.no/optimizing-https-nginx)
  19. sudo mkdir /etc/nginx/cert
    sudo openssl dhparam 2048 -out /etc/nginx/cert/dhparam.pem
  20. Test the config:
  21. sudo nginx -t
    nginx: [warn] conflicting server name "_" on 0.0.0.0:80, ignored
    nginx: the configuration file /etc/nginx/nginx.conf syntax is ok
    nginx: configuration file /etc/nginx/nginx.conf test is successful
  22. Redirect Port 443 on your router to the proxypi
  23. Restart the nginx service
  24. sudo service nginx restart
  25. Test your site security from here: https://www.ssllabs.com/ssltest/index.html
    You should get an A rating! (if step 6 was also followed)
  26. Test that certificate renewal will work
  27. sudo certbot renew --dry-run
  28. Set up a cronjob to automate cert renewal. Start by opening the crontab file
  29. sudo crontab -e
  30. Enter the following line at the bottom of the file
  31. * 1 * * 1 sudo /usr/bin/certbot renew

That’s it!!

If you have installed RPi Cam on another Pi and the internal URL/IP matches what you configured in /etc/nginx/services.conf, then you should be able to browse using this URL:

https://your-domainname/picam/

PLEASE NOTE – You must end the URL with a trailing forward slash “/”, otherwise the redirect won’t work properly

I built a new proxy pi as I wrote these instructions, so it should all work… I’ll be happy to answer any questions you have though.

Optional Extras for RPi Cam

Please see my other blog posts to add extra features to your setup:

RPi Cam Web Interface: Turn on and off motion detection using IFTTT Do Buttons

Would you like the ability to turn on and off motion detection on your Rpi Cam Web Interface from your phone with just the press of an IFTTT DO button (rather than logging into the camera’s website)?

An extra bonus on the iPhone is the ability to add DO button to the home screen widget, so it’s really easy to control your camera. Plus it’s not limited to motion detection – anything the pipe commands can do (http://elinux.org/RPi-Cam-Web-Interface#Pipe), the DO button can do too!

  1. Install Dropbox-Uploader
  2. cd ~
    git clone https://github.com/andreafabrizi/Dropbox-Uploader.git
    cd Dropbox-Uploader/
    chmod +x dropbox_uploader.sh
    ./dropbox_uploader.sh
    
  3. Follow the Dropbox-Uploader instructions:
  4. - Open the following URL in your Browser, and log in using your account:&nbsp;&lt;a class="postlink" href="https://www.dropbox.com/developers/apps"&gt;https://www.dropbox.com/developers/apps&lt;/a&gt;
    
    - Click on "Create App", then select "Dropbox API app"
    - Now go on with the configuration, choosing the app permissions and access restrictions to your DropBox folder
    - Enter the "App Name" that you prefer (e.g. MyPiUploader)
    
    - Now, click on the "Create App" button.
    
    - When your new App is successfully created, please click on the Generate button
    under the 'Generated access token' section, then copy and paste the new access token here:
    
    # Access token:
    
    
  5. Install Raspi-Runner
  6. 
    cd ~
    git clone https://github.com/enkydu/Raspi_Runner
    cd Raspi_Runner/
    chmod +x raspi_runner.sh
    ./raspi_runner.sh
    What is name of Dropbox folder, for Raspi Runner commands? (i.e. Raspi_Commands): scripts
    what is the full path to your Dropbox Uploader? (i.e. /home/pi/Dropbox_Uploader): /home/pi/Dropbox-Uploader
    
    

    Note – ensure the path has Dropbox-Uploader instead of the default Dropbox_Uploader

  7. Create a text file with the following content and copy to scripts folder in your dropbox storage area:
  8. echo 'md 1' &gt; /var/www/html/FIFO
  9. Test by running the command below (it should turn on motion detection – ‘md 0’ will turn off motion)
  10. /home/pi/Raspi_Runner/raspi_runner.sh
  11. Set a schedule in cron:
  12. crontab -e
  13. Paste the following line and save
  14. */2 * * * * /home/pi/Raspi_Runner/raspi_runner.sh &gt; /dev/null 2&gt;&amp;1
  15. Create Do Button (assumes you’ve created an IFTTT account and linked DropBox to it)
    1. Press the Mortar and Pestle button bottom right or find the My Recipes page.
    2. Press the + button
    3. Select Channels
    4. Press Dropbox
    5. Press Create a New Recipe
    6. Press Create a text file
    7. Give your Recipe a
      1. Title, e.g.
      2. Outside On (Motion)
      3. Name, e.g.
      4. File-On 
      5. Content, e.g.
      6. echo 'md 1' > /var/www/html/FIFO
      7. Dropbox folder path, e.g.
      8. scripts
    8. Click Add

    What’s nice about this method is that you can turn off motion detection in the middle of a recording, whereas the website button to turn motion off is greyed out until no more motion is detected.

    Based on this guide here: https://github.com/enkydu/Raspi_Runner