I have a problem with my project, I have a little python script to read my gas meter.
Every revolution of digits a small magnet inside the gas meter close to the reed switch makes an input for my raspberry. The problem is when the magnet stops close to the sensor circuit leaving on a high level, which cause false inputs, here my script.
Any suggestion? thanks to all
#!/usr/bin/env python
import time
import datetime
import os.path
import pycurl
import RPi.GPIO as GPIO
GPIO.setmode(GPIO.BCM)
GPIO.setup(10, GPIO.IN, pull_up_down=GPIO.PUD_DOWN)
GPIO.add_event_detect(10, GPIO.RISING, bouncetime = 5000)
def GetGas(arg):
time.sleep(0.01) # need to filter out the false positive of some power fluctuation
if GPIO.input(10) != GPIO.HIGH:
return
gastotale=0
if os.path.isfile('/var/www/myscripts/gas/gastotale.txt'):
file = open("/var/www/myscripts/gas/gastotale.txt","r")
gastotale = float(file.read())
file.close()
gastotale = gastotale+0.01
file = open("/var/www/myscripts/gas/gastotale.txt","w")
file.write(str(gastotale))
file.close()
now = datetime.datetime.now()
fileday = '/var/www/myscripts/gas/'+now.strftime("%Y-%m-%d")+'.txt'
gasday = 0
if os.path.isfile(fileday):
file = open(fileday,"r")
gasday = float(file.read())
file.close()
gasday = gasday+0.01
file = open(fileday,"w")
file.write(str(gasday))
file.close()
oem = pycurl.Curl()
oem.setopt(oem.URL, 'http://emoncms.org/input/post.json?node=0
csv=0,'+str(gasday)+',0,0,'+str(gastotale)+'&apikey=dfb6ccf')
oem.perform()
laststate = 0
while True:
if (GPIO.input(10) == 1 ):
if (laststate == 0):
gastotale = gastotale+0.01
laststate=1
else:
laststate=0
time.sleep(30)
Related
I have made a raspi0 PIR cam and am trying to get it to write to my network storage device. The .py writes to the drive but just keeps re-saving over the same file unless I ctrl C and manually restart.
from picamera import PiCamera
import time
from time import sleep
import os
import sys
from datetime import datetime
import RPi.GPIO as GPIO
GPIO.setmode(GPIO.BCM)
GPIO.setwarnings(False)
pir_sensor = 17 #GPIO physical pin 11
GPIO.setup(pir_sensor, GPIO.IN, GPIO.PUD_DOWN)
current_state = 0
filename_part1="surv"
file_ext=".mp4"
now = datetime.now()
current_datetime = now.strftime("%d-%m-%Y_%H:%M:%S")
filename=filename_part1+"_"+current_datetime+file_ext
filepath="/mnt/local_share/Surveillance_Captures/"
def capture_video():
camera.start_preview()
camera.start_recording('/home/pi/python_code/capture/newvideo.h264')
camera.wait_recording(10)
camera.stop_recording()
camera.stop_preview()
def remove_file():
if os.path.exists("/home/pi/python_code/capture/newvideo.h264"):
os.remove("/home/pi/python_code/capture/newvideo.h264")
else:
print("file does not exist")
camera=PiCamera()
while True:
i = GPIO.input(17)
if i==1:
print("Motion Detected")
capture_video()
sleep(2)
res=os.system("MP4Box -add /home/pi/python_code/capture/newvideo.h264 /home/pi/python_code/capture/newvideo.mp4")
os.system("mv /home/pi/python_code/capture/newvideo.mp4 "+filepath+filename)
print("File Moved")
print("Scanning Sector")
sleep(2)
remove_file()
Because you put filename=filename_part1+"_"+current_datetime+file_ext out of while loop, so the filename never change.
while True:
now = datetime.now()
current_datetime = now.strftime("%d-%m-%Y_%H:%M:%S")
filename=filename_part1+"_"+current_datetime+file_ext
I need to connect a serial device to gpio pin of a raspberry pi. My UART port is already used. For that, I need a simple code which can convert any gpio like Tx and Rx pin. I wrote a code but it could not receive data properly at higher baudrate.
My simple code of myuart is:
import RPi.GPIO as GPIO
import time,threading
GPIO.setwarnings(False)
GPIO.setmode(GPIO.BCM)
baudrate = OneBitDelay = timeout = Tx = Rx = timeout_exit = False
def begin(tx=2,rx=3,Baudrate=9600,Timeout=float('inf')):
global Tx,Rx,baudrate,OneBitDelay,timeout
Tx = tx
Rx = rx
baudtate = Baudrate
timeout = Timeout
GPIO.setup(Tx, GPIO.OUT, pull_up_down=GPIO.PUD_UP)
GPIO.setup(Rx, GPIO.IN, pull_up_down=GPIO.PUD_UP)
OneBitDelay = 1/baudrate
def setBaudrate(BaudRate):
global Baudrate,OneBitDelay
Baudrate = BaudRate
OneBitDelay = 1/Baudrate
def mytimer():
global timeout_exit
timeout_exit = True
def read(byte = 0):
global Tx,Rx,OneBitDelay,timeout,timeout_exit
data_array = ""
if timeout != float('inf'):
timer = threading.Timer(timeout, mytimer)
timer.start()
while GPIO.input(Rx):
if timeout_exit:
timeout_exit = False
return None
data = readValue = ""
if byte == 0:
while True:
time.sleep(OneBitDelay/baudrate) ## I think synchronization problem arries due to this delay
for count in range(0,8):
readValue = readValue + str(GPIO.input(Rx))
time.sleep(OneBitDelay)
if readValue != "11111111":
print("Received binary ",readValue)
data = data + chr(int(readValue, 2))
readValue = ""
else:
return data
else:
for r in range(0,int(byte/8)):
for count in range(0,8):
readValue = readValue + str(GPIO.input(Rx))
time.sleep(OneBitDelay)
data = data + chr(int(readValue, 2))
readValue = ""
return(data)
def write(data):
global OneBitDelay
if type(data) == int:
data = str(data)
data = getbinarystring(data)
dataTemp =""
for r in range(0,data.count(" ")+1):
dataTemp = dataTemp + data.split()[r].zfill(8)
for sendBit in range(0,len(dataTemp)):
GPIO.output(Tx, int(dataTemp[sendBit]))
time.sleep(OneBitDelay)
GPIO.output(Tx, True)
time.sleep(.005) ## I think synchronization problem aeries due to this delay
def getbinarystring(data):
return ' '.join(format(ord(x), 'b') for x in data)
Then I wrote a simple read.py and write.py code to transmit and receive data. but I am not getting whatever I send. also I am getting different data at different time. at lower baudrate this code works but at higher baudrate it's not working.
what are the mistakes I am making?? please help to improve synchronization.
for any kind of help thanks in advance.
write.py
import myuart,time
myuart.begin(tx=4,rx =17,Baudrate = 9600)
while True:
myuart.write("hello")
time.sleep(1)
read.py
import myuart,time
myuart.begin(tx=4,rx =17,Baudrate = 9600)
while True:
print myuart.read()
I started learning Python two months ago and I have written a code for a Raspberry pi project. My problem is that the program stucks after some hours of operation. I think that in all cases, it stopped after some wifi connection drops. But I don't understand why the whole program stops if there something wrong with the wifi connection. It stops uploading values and renew the lcd screen messages it prints (I removed this and other stuff from the code in order to be more easy to read.)
The code starts at the startup (sudo python /home/pi/test.py &) and contains two Threads:
The "Control" thread reads temperature and humidity by using an i2c bus and a sensor am2315 and according to a temperature threshold, controls a relay through GPIO.
The "Thingspeak" thread reads the temperature threshold from a 'Thingspeak' channel and then uploads the measurements from the previous thread to 'Thingspeak'.
I really don't know what to do and how to search for any solutions.
Any help will be much appreciated.
#! /usr/bin/env python
from time import sleep
import datetime
import urllib2
import RPi.GPIO as GPIO
import threading
import smbus
from tentacle_pi.AM2315 import AM2315
import smtplib
import contextlib
sleep(120)
# Lock
tLock = threading.Lock()
# Global variables
tem_global = 0; hum_global = 0
tem_hi = 35; relay = 21
# GPIO setup
GPIO.setmode(GPIO.BCM)
GPIO.setup(relay, GPIO.OUT)
GPIO.output(relay, False)
sleep(1)
def Control():
global temg, humg, tem_hi, relay
# AM2315 setup
am = AM2315(0x5c,"/dev/i2c-1")
I2C_address = 0x70; I2C_bus_number = 1; i2c_channel_setup = 1
bus = smbus.SMBus(I2C_bus_number)
bus.write_byte(I2C_address, i2c_channel_setup)
sleep(1)
while True:
try:
tem_local, hum_local = am2315meas()
except:
tem_local = -1; hum_local = -1
tLock.acquire()
tem_global = tem_local; hum_global = hum_local
if tem_local < tem_hi:
GPIO.output(relay, True)
else:
GPIO.output(relay, False)
tLock.release()
sleep(150)
def Thingspeak():
global tem_global, hum_global, tem_hi
myAPI = "..."
channelID = "..."
baseURL = 'https://api.thingspeak.com/update?api_key=%s' % myAPI
while True:
sleep(30)
try:
# Reading value from thingspeak
tLock.acquire()
with contextlib.closing(urllib2.urlopen("https://api.thingspeak.com/channels/%s/fields/1/last?" % channelID)) as f_read:
tem_hi = float(fread.read())
t.Lock.release()
sleep(30)
# Uploading values to thingspeak
tLock.acquire()
with contextlib.closing(urllib2.urlopen(baseURL + "&field1=%s" % tem_global + "&field2=%s" % hum_global)) as f_upload:
pass
tLock.release()
except:
with open('/home/pi/errors.txt', mode='a') as file:
file.write('Network error recorded at %s.\n' % datetime.datetime.now())
file.close()
sleep(60)
continue
def Main():
t1 = threading.Thread(target=Thingspeak)
t2 = threading.Thread(target=Control)
t1.start()
t2.start()
t1.join()
t2.join()
GPIO.cleanup()
if __name__ == '__main__':
Main()
Problem solved. As James K Polk indicated, there was an error after the tLock.acquire(), every time the internet connection went off, causing deadlock of the program. Below is a corrected part of the code for anyone would be interested.
def Control():
global tem_global, hum_global, tem_hi, relay
# AM2315 setup
am = AM2315(0x5c,"/dev/i2c-1")
I2C_address = 0x70; I2C_bus_number = 1; i2c_channel_setup = 1
bus = smbus.SMBus(I2C_bus_number)
bus.write_byte(I2C_address, i2c_channel_setup)
sleep(1)
while True:
try:
tem_local, hum_local = am2315meas()
except:
tem_local = -1; hum_local = -1
with tLock:
tem_global = tem_local; hum_global = hum_local
if tem_local < tem_hi:
GPIO.output(relay, True)
else:
GPIO.output(relay, False)
sleep(150)
def Thingspeak():
global tem_global, hum_global, tem_hi
myAPI = "..."
channelID = "..."
baseURL = 'https://api.thingspeak.com/update?api_key=%s' % myAPI
while True:
sleep(30)
try:
# Reading value from thingspeak
with tLock:
with contextlib.closing(urllib2.urlopen("https://api.thingspeak.com/channels/%s/fields/1/last?" % channelID)) as f_read:
tem_hi = float(fread.read())
sleep(30)
# Uploading values to thingspeak
with tLock:
with contextlib.closing(urllib2.urlopen(baseURL + "&field1=%s" % tem_global + "&field2=%s" % hum_global)) as f_upload:
pass
except:
with open('/home/pi/errors.txt', mode='a') as file:
file.write('Network error recorded at %s.\n' % datetime.datetime.now())
sleep(60)
continue
I am running a Python Program on a Raspberry Pi 3 which I want to log the temperature from a DS18B20 sensor once every 0.25 seconds.
Earlier, when the program was simple and displaying the temperature on shell, it was quite fast and not having issues. Unfortunately due to the program itself now which includes logging to a file, I am getting a log every 2 seconds or 3 seconds only.
How do I ensure the 0.25 second logging interval.
I have shared the code below:
#This program logs temperature from DS18B20 and records it
#Plots the temperature-time plot.
import os
import sys
#import matplotlib.pyplot as plt
from re import findall
from time import sleep, strftime, time
from datetime import *
#plt.ion()
#x = []
#y = []
ds18b20 = ''
def setup():
global ds18b20
for i in os.listdir('/sys/bus/w1/devices'):
if i != 'w1_bus_master1':
ds18b20 = i
# Reads temperature data from the Temp sensor
# This needs to be modified for use with max31855 and K-type thermocouples
def read():
# global ds18b20
location = '/sys/bus/w1/devices/' + ds18b20 + '/w1_slave'
tfile = open(location)
text = tfile.read()
tfile.close()
secondline = text.split("\n")[1]
temperaturedata = secondline.split(" ")[9]
temperature = float(temperaturedata[2:])
temperature = temperature / 1000
return temperature
#Loop for logging - sleep, and interrupt to be configured.
def loop():
while True:
if read() != None:
print "Current temperature : %0.3f C" % read()
#sleep(0.25)
func()
def write_temp(temperature,file_name):
with open(file_name, 'a') as log:
log.write("{0},{1}\n".format(datetime.now().strftime("%d-%m-%Y %H:%M:%S"),str(temperature)))
arg = sys.argv[1]
filename1 = str(arg) + "-" + datetime.now().strftime("%d-%m-%Y-%H-%M-%S")+".csv"
def func():
temperature = read()
#sleep(0.25)
write_temp(temperature,filename1)
#graph(temperature)
#For plotting graph using MatPlotLib
#Comment out this function during foundry trials to avoid system slowdown
#Check system resource usage and slowdown using TOP or HTOP
#def graph(temperature):
# y.append(temperature)
# x.append(time())
# plt.clf()
# plt.scatter(x,y)
# plt.plot(x,y)
# plt.draw()
#Interrupt from command-line
def destroy():
pass
if __name__ == '__main__':
try:
setup()
func()
loop()
except KeyboardInterrupt:
destroy()
I have commented out sections that I thought to be resource heavy, but still I can't manage anything less than 2 seconds. I am getting results as below:
Output:
27-09-2016 12:18:41,23.0
27-09-2016 12:18:43,23.062
27-09-2016 12:18:46,23.125
27-09-2016 12:18:48,23.187
27-09-2016 12:18:50,23.187
27-09-2016 12:18:53,23.562
27-09-2016 12:18:55,25.875
27-09-2016 12:18:58,27.187
27-09-2016 12:19:00,27.5
Only open the logfile once (and close it on program exit)
Don't always re-read the temperature from the sensor. You call read() way too often.
Reduce general overhead and simplify your calls.
I am not able to completely test this, but something like this sould work:
import os
import sys
import time
from datetime import datetime
def read_temp(dev):
'''Reads temperature from sensor and returns it as float.'''
loc = '/sys/bus/w1/devices/' + dev + '/w1_slave'
with open(loc) as tf:
return float(tf.read().split('\n')[1].split(' ')[9][2:]) / 1000.0
def write_temp(t, logfile):
'''Writes temperature as .3 float to open file handle.'''
logfile.write('{0},{1:.3f}\n'.format(datetime.now().strftime('%d-%m-%Y %H:%M:%S'), t))
def loop(dev, logfile):
'''Starts temperature logging until user interrupts.'''
while True:
t = read_temp(dev)
if t:
write_temp(t, logfile)
print('Current temperature: {0:.3f} °C'.format(t))
sys.stdout.flush() # Flush. Btw, print is time-consuming!
time.sleep(.25)
if __name__ == '__main__':
# Take the first match for a device that is not 'w1_bus_master1'
dev = [d for d in os.listdir('/sys/bus/w1/devices') if d != 'w1_bus_master1'][0]
# Prepare the log filename
fname = str(sys.argv[1]) + "-" + datetime.now().strftime("%d-%m-%Y-%H-%M-%S")+".csv"
# Immediately open the log in append mode and do not close it!
logfile = open(fname, 'a')
try:
# Only pass device and file handle, not the file name.
loop(dev, logfile)
except KeyboardInterrupt:
# Close log file on exit
logfile.close()
I just finished all of the prototyping of this project:, and I encountered 2 problems: https://www.pubnub.com/blog/2015-03-17-building-a-model-smart-home-with-raspberry-pi/
I cant run all of the programs at once(Humidity and Temperature, LEDs, Micro Servo motors, etc...)
I can't have more than three LED's (technically two)
What can I do to run everything at once, so it is all displayed in the WEB UI? How can I have more LED's, since the limit is 50mah which is about 2 LED's? (they can be three per 'room', so three per GPIO pin or just per GPIO). I dont see hoe it could work with such a power limit. Also, they need to be controlled with PWM. There simply isn't enough power on the Raspberry Pi!
the code for the DHT22 sensor is:
import time
import sys
from pubnub import Pubnub
import Adafruit_DHT as dht
pubnub = Pubnub(publish_key='demo', subscribe_key='demo')
channel = 'pi-house'
def callback(message):
print(message)
#published in this fashion to comply with Eon
while True:
h,t = dht.read_retry(dht.DHT22, 4)
temp='{0:0.1f}'.format(t)
hum='{0:0.1f}'.format(h)
message = {'temperature': temp, 'humidity': hum}
print 'Temp={0:0.1f}*C Humidity={1:0.1f}%'.format(t, h)
pubnub.publish(channel=channel, message=message, callback=callback, error=callback)
the code for the led's is:
import RPi.GPIO as GPIO
import time
import sys
from pubnub import Pubnub
GPIO.setmode(GPIO.BCM)
PIN_LIVING = 22
PIN_PORCH = 17
PIN_FIREPLACE = 27
GPIO.setup(PIN_LIVING,GPIO.OUT)
GPIO.setup(PIN_PORCH,GPIO.OUT)
GPIO.setup(PIN_FIREPLACE,GPIO.OUT)
FREQ = 100 # frequency in Hz
FIRE_FREQ = 30 # flickering effect
# Duty Cycle (0 <= dc <=100)
living = GPIO.PWM(PIN_LIVING, FREQ)
living.start(0)
porch = GPIO.PWM(PIN_PORCH, FREQ)
porch.start(0)
fire = GPIO.PWM(PIN_FIREPLACE, FIRE_FREQ)
fire.start(0)
# PubNub
pubnub = Pubnub(publish_key='demo', subscribe_key='demo')
channel = 'pi-house'
def _callback(m, channel):
print(m)
dc = m['brightness'] *10
if m['item'] == 'light-living':
living.ChangeDutyCycle(dc)
elif m['item'] == 'light-porch':
porch.ChangeDutyCycle(dc)
elif m['item'] == 'fireplace':
fire.ChangeDutyCycle(dc)
def _error(m):
print(m)
pubnub.subscribe(channels='pi-house', callback=_callback, error=_error)
try:
while 1:
pass
except KeyboardInterrupt:
GPIO.cleanup()
sys.exit(1)
Thanks!