I'm trying to rerun my script after it has finished running
preferably after 30 seconds i have tried some methods but can't find out how to continue with my code
my code:
import os.path
import os
import sys
import smtplib
import time
from email.mime.image import MIMEImage
from email.mime.multipart import MIMEMultipart
from email.mime.text import MIMEText
from PIL import ImageGrab
def enviar_email():
email = 'x.com'
password = 'x'
subject = 'This is the subject'
message = 'This is my message'
file_location = 'ss1.jpg'
msg = MIMEMultipart()
msg['x'] = email #sender
msg['x'] = email #receiver
msg['Subject'] = subject
msg.attach(MIMEText(message, 'plain'))
# Setup the attachment
filename = os.path.basename(file_location)
attachment = open(file_location, "rb").read()
image = MIMEImage(attachment, name=filename)
msg.attach(image)
# Attach the attachment to the MIMEMultipart object
# msg.attach(part)
server = smtplib.SMTP('smtp.gmail.com', 587)
server.starttls()
server.login(email, password)
text = msg.as_string()
server.sendmail(email, email, text)
server.quit()
def main():
imagem = ImageGrab.grab()
imagem.save('ss1.jpg', 'jpeg')
enviar_email()
print("Taking screenshot...")
if _name_ == '_main_':
main()
time.sleep(10)
os.execl(sys.executable, sys.executable, *sys.argv)
i tried adding:
time.sleep(10)
os.execl(sys.executable, sys.executable, *sys.argv)
but the script did not restart any advice how i can make it so that it restarts the script ?
You can call main() function again after time.sleep(10). Try this:
if _name_ == '_main_':
main()
time.sleep(10)
main()
Use the while loop :
if __name__=='__main__':
while True:
do_something()
You can even pair it with a try/except block like this :
if __name__=='__main__':
while True:
try:
do_something()
except:
print('Error Occured in running the script, Rerunning...')
This will prevent the script from abruptly stopping in case of an error.
For re running the script a specific number of times, you can define a count variable and break it when it matches a value, like this:
if __name__=='__main__':
count=0
no_of_runs=5
while True:
try:
if count==no_of_runs:
break
else:
do_something()
count+=1
except:
print('Error occured, Rerunning...')
pass
You can use schedule library for this purpose.
#!pip install schedule
import schedule
import time
while True:
# Checks whether a scheduled task
# is pending to run or not
schedule.your_function()
time.sleep(1)
Related
The below script is a working prototype of a script that runs on a rasberry pi and its job is to grab files from a specified folder on a flashdrive when plugged in. After that point it emails the files as attachments. Now, everything works perfect, but not logically in the way I want. I have a really janky while True: loop with janky sleep timers to kind delay some things. Ideally I need help developing a way for all of this to happen only ONCE per usb drive plug in. Then it would go into "Idle mode" waiting for the next stick. As of now, without my added sleep timers, It would just continually run over and over. I've been stuck trying to logically figure out a way to make it work how I would like.
Thanks in advance!
import smtplib, ssl
import shutil
import os
from time import sleep
from distutils import dir_util
from psutil import disk_partitions
from datetime import datetime
from datetime import date
from email.mime.text import MIMEText
from email.mime.multipart import MIMEMultipart
from email.mime.application import MIMEApplication
now = datetime.now()
current_time = now.strftime("%H:%M:%S")
today = date.today()
day = today.strftime("%B %d, %Y")
def CopyFilesFromSD():
try:
dir_util.copy_tree(driver+'/REDACTED', '/home/pi/Desktop/Transferred Files')
print("Files Succesfully Copied")
if 'rw' in opts:
with open(driver+'/Transfer_Log_REDACTED.txt', 'a', encoding = 'utf-8') as fp:
fp.write("\nFiles Succesfully Transferred to REDACTED on " + day + " at " + current_time)
except:
print("Device unmounted during transfer process!")
sleep(10)
def SendFiles():
dir_path = "/home/pi/Desktop/Transferred Files/"
files = os.listdir(dir_path)
msg = MIMEMultipart()
msg['To'] = "REDACTED"
msg['From'] = "REDACTED"
msg['Subject'] = "REDACTED"
password = "REDACTED"
body = MIMEText('Test.', 'html', 'utf-8')
msg.attach(body)
for f in files:
file_path = os.path.join(dir_path, f)
attachment = MIMEApplication(open(file_path, "rb").read(), _subtype="txt")
attachment.add_header('Content-Disposition','attachment', filename=f)
msg.attach(attachment)
context = ssl.create_default_context()
with smtplib.SMTP_SSL("REDACTED", 465, context=context) as server:
server.login(msg['From'], password)
server.sendmail(
msg['From'], msg['To'], msg.as_string()
)
shutil.rmtree(dir_path, ignore_errors = False)
sleep(5)
while True:
sleep(1)
for item in disk_partitions():
if 'nodev' in item.opts:
driver, opts = item.mountpoint, item.opts
CopyFilesFromSD()
SendFiles()
break
else:
continue
break
Answered by iScripters in the comment section:
https://betterprogramming.pub/how-to-run-a-python-script-on-insertion-of-a-usb-device-2e86d38dcdb
This will allow for the python script to only be ran when USB insertion is detected. No need to have a constant running program looking for drives.
tried it before and it worked don't know what happend..
at first it should read a text file. and I've tried reading and printing it manually and it worked so that part is ok. I think. but every time I try to send the message I get an empty message
import smtplib as s
#file settings
filename = open("D:\pythonscripts\hey_hey.txt", 'a+')
content = filename.read()
#recivers list
recivers = ['somemail#gmail.com']
#tries to send the message
def send_mail(username, password, msg):
#connects to smtp gmail server
server = s.SMTP('smtp.gmail.com:587')
server.starttls()
server.login(username, password)
try:
server.sendmail(username, recivers[0], msg)
print("massage sent")
except:
server.close()
print("error while sending the massage\nquitung server...")
send_mail('somemail#gmail.com', 'ferari_car', content)
Try this instead:
filename = open("D:\\pythonscripts\\hey_hey.txt", 'r') # r, not a+, and escape the backslashes
a+ opens the file for appending, which puts the file position at the end of the file. So when you try to read it, you'll get nothing.
hey all thank you for helping me out. evenchely I managed to send the message with the text file as an attachment instead of the message's body..
import smtplib as s
from os.path import basename
from email.mime.application import MIMEApplication
from email.mime.multipart import MIMEMultipart
from email.mime.text import MIMEText
from email.utils import COMMASPACE, formatdate
#file settings
filename = open("D:\\pythonscripts\\hey_hey.txt", 'r')
content= filename.read()
print(content)
#recivers list
recivers = ['somemail#gmail.com']
#tries to send the message
def send_mail(username, password, message, send_to, subject):
#message settings
msg = MIMEMultipart()
msg['From'] = username
msg['To'] = COMMASPACE.join(send_to)
msg['Date'] = formatdate(localtime=True)
msg['Subject'] = subject
msg.attach(MIMEText(message))
#connects to smtp gmail server
server = s.SMTP('smtp.gmail.com:587')
server.starttls()
server.login(username, password)
try:
server.sendmail(username, send_to, msg.as_string())
print("massage sent")
except:
server.close()
print("error while sending the massage\nquitung server...")
send_mail('othermail#gmail.com', 'ferari_car', content, recivers[0], "the mail stuff")
I have captured image using webcam and when i press button it sends mail.I use while loop as shown in below code,this code is running perfectly but problem is this program send so many image(also send earlier capured image)while we stop the program to run,so there are so many images attached in one mail only.Now i want program continuonsly running in raspberry pi but still it should be mail only last captured image so what i have to do changes for that?
Thanks in advance.
This is my code:
import smtplib
import time
import subprocess
from email.MIMEMultipart import MIMEMultipart
from email.MIMEBase import MIMEBase
from email.MIMEText import MIMEText
from email.MIMEImage import MIMEImage
import RPi.GPIO as GPIO
# Define these once; use them twice!
strFrom = 'example#gmail.com'
strTo = 'example#gmail.com'
#create email
# Create the root message and fill in the from, to, and subj$
msgRoot = MIMEMultipart()
msgRoot['Subject'] = 'subject'
msgRoot['From'] = strFrom
msgRoot['To'] = strTo
GPIO.setmode(GPIO.BCM)
GPIO.setup(4, GPIO.IN)
print "press button to send email"
while True:
input=GPIO.input(4)
if input == True:
print "button pressed"
subprocess.Popen(["fswebcam","-r 640x480", "capture.jpg"])
time.sleep(2)
# This example assumes the image is in the current
# directory
fp = open('capture.jpg', 'rb')
msgImage = MIMEImage(fp.read())
fp.close()
msgRoot.attach(msgImage)
# send mail
s = smtplib.SMTP('smtp.gmail.com',587)
s.starttls()
s.login('example#gmail.com' , 'password')
s.sendmail(strFrom, strTo,msgRoot.as_string())
s.close()
print "Email sent"
time.sleep(0.2)
msgRoot.attach(msgImage)
msgRoot.set_payload(msImage) #Such modified
Because you are using the same copy of the annex has been superimposed on the upswing
I am writing a script for a surveillance camera. I have programmed it to take a picture when motion is detected (PIR sensor) then attach the photo to an email, to a chosen recipient. However because I am running this without a screen, mouse or keyboard attached I had no way to turn the device off without pulling the plug! so I created a script to turn off the computer on a button press(this works fine on its own) however, because the rest of the code is in a loop I don't know where to place it. Keeping in mind I need to be able to turn it off any where in the code.
If you have any ideas they would be appreciated
Thanks
James
import os, re
import sys
import smtplib
import RPi.GPIO as GPIO
import time
import picamera
inport os
from email.mime.image import MIMEImage
from email.mime.multipart import MIMEMultipart
from email.mime.text import MIMEText
import time
import RPi.GPIO as gpio
GPIO.setmode(GPIO.BCM)
GPIO_PIR = 4
print ("PIR Module Test (CTRL-C to exit)")
GPIO.setup(GPIO_PIR,GPIO.IN)
Current_State = 0
Previous_State = 0
try:
print ("Waiting for PIR to settle ...")
while GPIO.input(GPIO_PIR)==1:
Current_State = 0
print (" Ready")
while True :
Current_State = GPIO.input(GPIO_PIR)
surv_pic = open('/home/pi/Eaglecam/surveillance.jpg', 'wb')
if Current_State==1 and Previous_State==0:
print(" Motion detected!")
with picamera.PiCamera() as cam:
cam.capture(surv_pic)
surv_pic.close()
print(' Picture Taken')
SMTP_SERVER = 'smtp.gmail.com'
SMTP_PORT = 587
sender = '**************'
password = "**********"
recipient = '**************'
subject = 'INTRUDER DETECTER!!'
message = 'INTRUDER ALLERT!! INTRUDER ALERT!! CHECK OUT THIS PICTURE OF THE INTRUDER! SAVE THIS PICTURE AS EVIDENCE!'
directory = "/home/pi/Eaglecam/"
def main():
msg = MIMEMultipart()
msg['Subject'] = 'INTRUDER ALERT'
msg['To'] = recipient
msg['From'] = sender
files = os.listdir(directory)
jpgsearch = re.compile(".jpg", re.IGNORECASE)
files = filter(jpgsearch.search, files)
for filename in files:
path = os.path.join(directory, filename)
if not os.path.isfile(path):
continue
img = MIMEImage(open(path, 'rb').read(), _subtype="jpg")
img.add_header('Content-Disposition', 'attachment', filename=filename)
msg.attach(img)
part = MIMEText('text', "plain")
part.set_payload(message)
msg.attach(part)
session = smtplib.SMTP(SMTP_SERVER, SMTP_PORT)
session.ehlo()
session.starttls()
session.ehlo
session.login(sender, password)
session.sendmail(sender, recipient, msg.as_string())
session.quit()
if __name__ == '__main__':
print(' Email Sent')
Previous_State=1
elif Current_State==0 and Previous_State==1:
print(" Ready")
Previous_State=0
time.sleep(0.01)
import time
import RPi.GPIO as gpio
except KeyboardInterrupt:
print('Quit')
GPIO.cleanup()
Here is the shutdown section of the script. Where would I place this in the loop?
gpio.setmode(gpio.BCM)
gpio.setup(7, gpio.IN, pull_up_down=gpio.PUD_UP)
buttonReleased = True
while buttonReleased:
gpio.wait_for_edge(7, gpio.FALLING)
buttonReleased = False
for i in range(1):
time.sleep(0.1)
if gpio.input(7):
buttonReleased = True
break
Two separate scripts would be unnecessary for this project.
You can do this a couple ways.
Create a global boolean variable called shutdownButton or whatever. Use a callback function for the GPIO pin, and set shutdownButton = True in the callback. And then change your main loop to be while not shutdownButton: instead of while True:.
You could just change your main loop to while gpio.input(7): instead of while True: (assuming you are pulling the pin up and then grounding it down with your switch).
And then finally just add a shutdown like os.system('sudo shutdown -h now') or call some other script you want to run to clean it up. The point is you just need a function to break out of your main loop when the button has been pressed and then shut down your pi at the end of the program.
There are other ways to do this also (I personally like the kernel patches from Adafruit that allow a power switch configuration to be added to /etc/modprobe.d...) but I only listed methods that applied directly to your question.
Hi Guys I have been working on this code for quite a while but once the code has sensed motion, taken a picture and sent it off as an email attachment it works once but once the state returns to ready it comes up with this error but I can't understand why. I apologise for including the whole code because although the error states line 43 I'm not to sure what's causing it to go wrong.
any suggestions would be greatly appreciated. I am a beginner in python programming so I may be missing something very obvious. By the way I'm running this on a raspberry pi for anyone who would like to test out the code.
Thanks
import os, re
import sys
import smtplib
import RPi.GPIO as GPIO
import time
import picamera
from email.mime.image import MIMEImage
from email.mime.multipart import MIMEMultipart
from email.mime.text import MIMEText
GPIO.setmode(GPIO.BCM)
GPIO_PIR = 4
print "PIR Module Test (CTRL-C to exit)"
GPIO.setup(GPIO_PIR,GPIO.IN)
Current_State = 0
Previous_State = 0
cam = picamera.PiCamera()
try:
print "Waiting for PIR to settle ..."
while GPIO.input(GPIO_PIR)==1:
Current_State = 0
print " Ready"
while True :
Current_State = GPIO.input(GPIO_PIR)
if Current_State==1 and Previous_State==0:
print " Motion detected!"
cam.capture('/home/pi/Eaglecam/surveillance.jpg')
print('picture taken')
cam.close()
SMTP_SERVER = 'smtp.gmail.com'
SMTP_PORT = 587
sender = '*******************'
password = "secret!!"
recipient = '*********************'
subject = 'INTRUDER DETECTER!!'
message = 'INTRUDER ALLERT!! INTRUDER ALERT!! CHECK OUT THIS PICTURE OF THE INTRUDER! SAVE THIS PICTURE AS EVIDENCE!'
directory = "/home/pi/Eaglecam/"
def main():
msg = MIMEMultipart()
msg['Subject'] = 'INTRUDER ALERT'
msg['To'] = recipient
msg['From'] = sender
files = os.listdir(directory)
jpgsearch = re.compile(".jpg", re.IGNORECASE)
files = filter(jpgsearch.search, files)
for filename in files:
path = os.path.join(directory, filename)
if not os.path.isfile(path):
continue
img = MIMEImage(open(path, 'rb').read(), _subtype="jpg")
img.add_header('Content-Disposition', 'attachment', filename=filename)
msg.attach(img)
part = MIMEText('text', "plain")
part.set_payload(message)
msg.attach(part)
session = smtplib.SMTP(SMTP_SERVER, SMTP_PORT)
session.ehlo()
session.starttls()
session.ehlo
session.login(sender, password)
session.sendmail(sender, recipient, msg.as_string())
session.quit()
if __name__ == '__main__':
print(' Email Sent')
Previous_State=1
elif Current_State==0 and Previous_State==1:
print " Ready"
Previous_State=0
time.sleep(0.01)
except KeyboardInterrupt:
print " Quit"
GPIO.cleanup()
Here is the Error:
Traceback (most recent call last):
File "/home/pi/Python/hi2.py", line 43, in <module>
cam.capture('/home/pi/Eaglecam/surveillance.jpg')
File "/usr/lib/python2.7/dist-packages/picamera/camera.py", line 1446, in capture
camera_port, output_port = self._get_ports(use_video_port, splitter_port)
File "/usr/lib/python2.7/dist-packages/picamera/camera.py", line 708, in _get_ports
self._camera[0].output[self.CAMERA_CAPTURE_PORT]
TypeError: 'NoneType' object has no attribute '__getitem__'
Try not persisting your cam object...picamera flushes and closes as it sees fit so you may be having problems calling the object repeatedly with the code you are using. Also, you are calling the .close() method on your cam object after if takes the first picture. I might accomplish this like so:
surv_pic = open('/home/pi/Eaglecam/surveillance.jpg', 'wb')
if Current_State==1 and Previous_State==0:
print " Motion detected!"
with picamera.PiCamera() as cam:
##if camera is not producing pictures because it is not warmed up yet uncomment the next two lines
##cam.start_preview()
##time.sleep(2)
cam.capture(surv_pic)
surv_pic.close()
SMTP_SERVER = 'smtp.gmail.com'
## continue as is from here