Tag: bash

Using the REST api to read sensors on Home assistant

During one of my little project of making timelapses videos with some IP cameras, I had the following problem : How do you stop capturing new images at night when the camera see nothing,
After all , the sun rise and sun set time are changing everyday ! and i didn’t see a simple way to calculate this.
then i remembered the sun.sun integration in Home assistant.

If i had a simple way to query this integration in my script , i could very simply stop my script when the sun was no longer present in the sky !

The Home assistant REST API

In any home assistant installation there is access to a REST API that lets you do a lot a things , but in my case, I don’t want much , I just want to know if the sun is above or below the horizon.

  1. Get a Authorization: Bearer token
    you first have to generate a token to authenticate your request . You have to go to your user section , this is the circle a the bottom of the toolbar, then at the bottom of the page , you can create a long term token ,
    Please take note of this token because Home assitant can only display it one time , if you loose it , you must recreate an other one.
  2. Then in my script i can use this
  3. it will return either above_horizon or below_horizon, I can then use this in my script to stop the capture when it’s below_horizon

I used jq filter the json result , but , if you can’t or don’t want to install it , you can replace it with this simple awk

Using bash and gatttool to get readings from Xiaomi Mijia LYWSD03MMC Temperature Humidity sensor

There is a new inexpensive Temperature and humidity sensor by xiaomi.
This time is no longer round ,

Xiaomi Mijia LYWSD03MMC Bluetooth 4.2 Temperature Humidity sensor

if you like me would like to get the temperature and humidity data from time to time to import in a graphing tool like grafana, there is a simple solution using classic bash tools and gatttool.
First you have to indentify the mac-address of your little sensor, for this , just make sure the sensor is in range of your linux device ans launch a
hcitool lescann

this command will spit out all the bluetooth devices in range
just find the line with the name of the device and copy the mac address A4:C1:38:8C:77:CA LYWSD03MMC

then you must start a little bash script like this :

#!/bin/bash
bt=$(timeout 15 gatttool -b A4:C1:38:8C:77:CA --char-write-req --handle='0x0038' --value="0100" --listen)
if [ -z "$bt" ]
then
echo "The reading failed"
else
echo "Got data"
echo $bt temphexa=$(echo $bt | awk -F ' ' '{print $12$11}'| tr [:lower:] [:upper:] )

humhexa=$(echo $bt | awk -F ' ' '{print $13}'| tr [:lower:] [:upper:])
temperature100=$(echo "ibase=16; $temphexa" | bc)
humidity=$(echo "ibase=16; $humhexa" | bc)
echo "scale=2;$temperature100/100"|bc
echo $humidity
fi

this is a skeleton that you can improve , but for now it pretty much work like that ,

first it use gatttol to connect to the sensor and listen for 15 sec
During these fifteen seconds , you can be pretty much sure to receive at least some data like this :

Characteristic value was written successfully Notification handle = 0x0036 value: 58 03 47 a0 0b Notification handle = 0x0036 value: 55 03 47 a0 0b

this tell me that during the 15 sec of connection i received the information that i need two times.
what i’m after are the value 58 03 for the temperature , and 47 for the humidity.

the temperature is little endian format its mean that the two group must be inverted before decoding the data. i invert the values with awk and decode them using bc.
bc doesn’t like when the hex values are not capitalised so tr is used to do that.

bc then give you the temperature multiplied by 100. relaunch bc to divice per 100,

For the humidity its simpler , you get the value in one step without inverting anyting

Then you can do what you need with theses two vars , insert then in some database etc ..

there is room from improvement: for example this script is not capable of decoding negative temperature.
i will post an improved version when i figure out how to do it

Bash keyboard shortcuts

When you are spending your day in the terminal , you will find that navigating using only the arrows keys although fine at the the start will frustrate you because it’s quite slow.
Bash come with a lot of keyboard shortcuts design to gain precious time.

CTRL+A # will move the cursour to the beginning of the line
CTRL+E # moves to end of line
CTRL+C # halts the current command and back to prompt
CTRL+D # deletes one character backward or logs out of current session, similar to exit
CTRL+K # deletes all the text forward to the end of the line
CTRL+L # clears screen and redisplay the line
CTRL+R # searches history entering keyword ,
CTRL+T # transposes two characters
CTRL+U # kills backward from point to the beginning of line
CTRL+W # kills the word behind the cursor

i’ve put in bold the shortcuts that i use every day , i don’t use CTRL+A and CTRL+E because the keyboard has keys that are foing the same thing.

Bash brace expansion. (to delete files)

In bash , it is common to have to do some action on a numéric serie of files , like deleting or renaming ,

Using brace expansion you will be able to générate a single line that will act on multiple targets ,

For our example , let’s think about a list of ten files

in the simple case where i want to delete the complete list of files, i just have to run de command,

The 10 files will be deleted, but , this is not practical if you want to keep the last file , and delete the other nine,

In that case we can use a usefull tool called brace expansion,

To delete the files 1 to 9 , i just have to run in my bash terminal!

This last one is extremely practical , I use it very often in a lot of different uses cases.

But in other cases , you may want to delete even on odd files , or one every three files,

This is also doable with braces expansions

Redirect stdout and stderr to a file

il you need to run a script unattended and wish to log the output of that script you must already know that you can simply do

the problem with that is you will not log the error messages , only the output messages ,
the error are going to be displayed on the terminal but , not logged
and the error message are often as important as the output message , we do not want to dismiss them from the log ,

the solution to that issue is to run the script using this

With this , both the output will be logged in to the log file.

Bash script to clean movies name


The issue when you download movies online, is that most of the time the file name is going to be complete trash , filled with useless info like the team that made the rip or the website from where the movie was downloaded.
This is very annoying when you sort by name and the website made the idiotic decision to put their name in front of the actual film name.

for example here a typical movie name
[ Torrent9.info ] Dont.Think.Twice.2016.FRENCH.WEBRip.XviD-NEWCiNE.avi
the actual useful data that i wish to keep is Dont.Think.Twice.2016.avi

for this purpose i’ve developped a small bash script that will list all the files in a chosen directory then , if necessary , will rename the file.

this is not a very efficient script
but it’s fulfill it’s purpose and very rarely encounter a filename that he is unable to clean.

BASH:check if a number is even or odd


In a bash script you might need to check if a var is even or odd , 

in my case im going to use a if to make that check

You can use this simple code to make that check and display the result.

the result will be :