I am hosting a website on Google Apps Engine and am trying to use Python's mail API to take POST data and send an email.
Here is my script:
from google.appengine.ext import webapp
from google.appengine.ext.webapp.util import run_wsgi_app
from google.appengine.api import mail
class SendEmail(webapp.RequestHandler):
def post(self):
name = self.request.get('name')
# self.response.out.write(name)
email = self.request.get('email')
tempSubject = self.request.get('subject')
msg = self.request.get('message')
if name is None:
self.response.out.write("Error: You did not enter a name.")
elif email is None:
self.response.out.write("Error: You did not enter an email.")
elif tempSubject is None:
self.response.out.write("Error: You did not enter a subject.")
elif msg is None:
self.response.out.write("Error: You did not enter a message.")
else:
_subject = "Msg from: " + name + "Re: " + tempSubject
message = mail.EmailMessage(sender = "foo#bar.com", to = "bar#foo.com", subject = _subject, body = msg, reply_to = email)
message.send()
def runApp():
application = webapp.WSGIApplication([('/email', SendEmail)], debug=True)
run_wsgi_app(application)
if __name__ == '__main__':
runApp()
And here is the traceback from the log on the server:
<type 'exceptions.NameError'>: name 'name' is not defined
Traceback (most recent call last):
File "/base/data/home/apps/s~alex-young/1.365202894602706277/email.py", line 5, in <module>
class SendEmail(webapp.RequestHandler):
File "/base/data/home/apps/s~alex-young/1.365202894602706277/email.py", line 14, in SendEmail
if name is None:
I ran the script locally with no errors, but once I try to run it on the server it keeps insisting the name variable I declared doesn't exist. Any idea why this happens?
Also, if I comment out that line, it says email doesn't exist, and so forth
As it turns out, sometimes I used spaces to indent and other times I used tabs. Python didn't like that. Here is the final code:
import cgi
from google.appengine.ext import webapp
from google.appengine.ext.webapp.util import run_wsgi_app
from google.appengine.api import mail
class SendEmail(webapp.RequestHandler):
def post(self):
name = self.request.get('name', '')
email = self.request.get('email', '')
tempSubject = self.request.get('subject', '')
msg = self.request.get('message', '')
if name is None:
self.response.out.write("Error: You did not enter a name.")
elif email is None:
self.response.out.write("Error: You did not enter an email.")
elif tempSubject is None:
self.response.out.write("Error: You did not enter a subject.")
elif msg is None:
self.response.out.write("Error: You did not enter a message.")
else:
_subject = "Message from: " + name + ", Re: " + tempSubject
msg += "\n\nI can be reached at "
msg += email
message = mail.EmailMessage(sender = "foo#bar.com", to = "bar#foo.com")
message.subject = _subject
message.body = msg
message.send()
self.redirect('/')
def runApp():
application = webapp.WSGIApplication([('/email', SendEmail)], debug=True)
run_wsgi_app(application)
if __name__ == '__main__':
runApp()
Related
I am trying to write a script so when an IP address can't be seen a message gets sent with a telegram letting me know which computer is offline
I have been able to get the telegram side working but i have not been able to pass the data from the main script where it is testing the ip address , at the moment i have test data in there but i would like it to send the error with the computer name
main.py
import socket
import ssl
from datetime import datetime
import pickle
import subprocess
import platform
class Server:
def __init__(self, name, port, connection, priority):
self.name = name
self.port = port
self.connection = connection.lower()
self.priority = priority.lower()
self.history = []
self.alert = False
def check_connection(self):
msg = ""
success = False
now = datetime.now().strftime("%d-%m-%Y %H:%M")
try:
if self.connection == "plain":
socket.create_connection((self.name, self.port), timeout=10)
msg = f"{self.name} is up. On port {self.port} with {self.connection}"
success = True
self.alert = False
elif self.connection == "ssl":
ssl.wrap_socket(socket.create_connection((self.name, self.port), timeout=10))
msg = f"{self.name} is up. On port {self.port} with {self.connection}"
success = True
self.alert = False
else:
if self.ping():
msg = f"{self.name} is up. On port {self.port} with {self.connection}"
success = True
self.alert = False
except socket.timeout:
msg = f"server: {self.name} timeout. On port {self.port}"
except (ConnectionRefusedError, ConnectionResetError) as e:
msg = f"server: {self.name} {e}"
except Exception as e:
msg = f"No Clue??: {e}"
if success == False and self.alert == False:
# Send Alert
self.alert = True
import tg_start
tg_start.send_message("Happy days")
self.create_history(msg, success, now)
def create_history(self, msg, success, now):
history_max = 100
self.history.append((msg, success, now))
while len(self.history) > history_max:
self.history.pop(0)
def ping(self):
try:
output = subprocess.check_output("ping -{} 1 {}".format('n' if platform.system().lower(
) == "windows" else 'c', self.name), shell=True, universal_newlines=True)
if 'unreachable' in output:
return False
else:
return True
except Exception:
return False
if __name__ == "__main__":
try:
servers = pickle.load(open("servers.pickle", "rb"))
except:
servers = [
# Server("ifmc-repserver", 80, "plain", "high"),
# Server("ifmc-repserver", 80, "plain", "high"),
# Server("ifmc-repserver", 465, "ssl", "high"),
# Server("ifmc-repserver", 80, "ping", "high"),
Server("ifmc-repserver", 80, "ping", "high")
]
for server in servers:
server.check_connection()
print(len(server.history))
print(server.history[-1])
pickle.dump(servers, open("servers.pickle", "wb"))
and tg_start.py
import requests
message = "global"
alert = ""
def send_message(text):
global alert
global message
print ("this is text messsage" + " " + text)
#text = "Superman"
alert = text
print("Sending ALERT ...")
token = "token"
chat_id = "chat_id"
print("test message" + " " + alert)
url_req = "https://api.telegram.org/bot" + token + "/sendMessage" + "?chat_id=" + chat_id + "&text=" + alert
print(url_req)
#results = requests.get(url_req)
results = requests.post(url_req) # this request is a post, not a get
print(results.json())
# text = "my name" + text
send_message(alert)
You code worked with a slight change, sendMessage require a POST request, not a GET request.
def send_message(text):
global alert
global message
print ("this is text messsage" + " " + text)
alert = text
print("Sending ALERT ...")
token = "token"
chat_id = "chat_id"
print("test message" + " " + alert)
url_req = f"https://api.telegram.org/bot{token}/sendMessage?chat_id={chat_id}&text={alert}"
print(url_req)
results = requests.post(url_req) # this request is a post, not a get
print(results.json())
# text = "my name" + text
i am very new to programming, i am supposed to count the number of unread eamails in my inbos usiong python. i am getting a name error saying that "mail" is not defined. i am not sure about the logic either. Here is the code:
import imaplib
<!-- begin snippet: js hide: false console: true babel: false -->
import datetime
import email
import getpass
def readmail():
mail = imaplib.IMAP4_SSL('imap.gmail.com', 993)
mypassword = getpass.getpass("Password: ")
address = '#mail.com'
mail.login(address, mypassword)
now = datetime.date.today()
mail.select("inbox")
print("Checking for new e-mails for ", address, ".")
typ, messageIDs = mail.search(now, "UNSEEN")
messageIDsString = str(messageIDs[0], encoding='utf8')
listOfSplitStrings = messageIDsString.split(" ")
print (len(listOfSplitStrings))
Fix code indentation
import imaplib
import datetime
import email
import getpass
def readmail():
mail = imaplib.IMAP4_SSL('imap.gmail.com', 993)
mypassword = getpass.getpass("Password: ")
address = '#mail.com'
mail.login(address, mypassword)
now = datetime.date.today()
mail.select("inbox")
print("Checking for new e-mails for ", address, ".")
typ, messageIDs = mail.search(now, "UNSEEN")
messageIDsString = str(messageIDs[0], encoding='utf8')
listOfSplitStrings = messageIDsString.split(" ")
print (len(listOfSplitStrings))
if __name__=="__main__":
readmail()
I have a script that alerts me by mail when a phrase changes on a web page. I tried many things, but I can't fix the isAvailable() function: the script says "not available" every time, whether or not I give it an available server. Have you any clues?
# CONFIG
TARGET_KIMSUFI_ID = "160sk1" # something like 160sk1
TARGET_DESCR = ""
EMAIL_FROM_ADDRS = ""
EMAIL_TO_ADRS = ""
EMAIL_SMTP_LOGIN = EMAIL_FROM_ADDRS
EMAIL_SMTP_PASSWD = ""
EMAIL_SMTP_SERVER = ""
# CODE
import urllib.request
import smtplib
import time
def isAvailable():
rawPageContent = urllib.request.urlopen("https://www.kimsufi.com/en/servers.xml").read()
rawPageContent = str(rawPageContent)
poz = rawPageContent.find(TARGET_KIMSUFI_ID)
row = rawPageContent[poz:]
poz = row.find("</tr>")
row = row[:poz]
searchText = "Currently being replenished"
poz = row.find(searchText)
return poz != -1
def sendEmailWithMessageAvailable():
msg = "From: KIMSUFI HUNTER <"+EMAIL_FROM_ADDRS+">\r\n"+\
"To: "+EMAIL_TO_ADRS+"\r\n"+\
"Subject: [KIMSUFI] "+TARGET_DESCR+" is now AVAILABLE!\r\n"+\
"\r\n"+\
"kimsufi-hunter.py has detected that "+TARGET_DESCR+" is now ["+time.ctime()+"] available!\r\n"+\
"https://www.kimsufi.com/en/\r\n"
server = smtplib.SMTP(EMAIL_SMTP_SERVER)
server.starttls()
server.login(EMAIL_SMTP_LOGIN,EMAIL_SMTP_PASSWD)
server.sendmail(EMAIL_FROM_ADDRS, EMAIL_TO_ADRS, msg)
server.quit()
while True:
if isAvailable():
print(time.ctime() + " -- KIMSUFI "+TARGET_DESCR+" not available")
nextSleep = 5 #5secs
else:
print(time.ctime() + " -- KIMSUFI "+TARGET_DESCR+" AVAILABLE!!! -- sleeping for 5 minutes")
sendEmailWithMessageAvailable()
nextSleep = 5*60 #5mins
time.sleep(nextSleep)
Your isAvailable() function returns True if the website is available, False otherwise. You should change the if statement to:
if not isAvailable():
...
i am a python beginner and i'd like to get some help from you.
Recently i wrote a program which is about email spamming(retrieving data from a config file) using the 'smtp' module which i can't use very well so when i ran the program, it says this:
enter any key to exit
enter 'spam' to spam an email
Enter: spam
Running..Running..Running..Running..Running..Running..Running..Traceback (most recent call last):
File "C:\Users\Leon\Desktop\Progetti\Gdaze\Gdaze.py", line 61, in <module>
emailSetupAndGo(getData()[0], getData()[1], getData()[2], getData()[3], getData()[4], getData()[5])
File "C:\Users\Leon\Desktop\Progetti\Gdaze\Gdaze.py", line 46, in emailSetupAndGo
server = smtplib.SMPT('smtp.gmail.com:587')
AttributeError: module 'smtplib' has no attribute 'SMPT'
After seeing this error i searched it and found out, on stackoverflow, a solution, but it worked just for people who named the file email.py.
Here you are the source code(I also think i made a mistake with the .split(' ') to delete the spaces) so you can tell me what the error is:
import smtplib
import sys
def getData():
#GETTING DATA FROM THE FILE
configFile = open('config.txt', 'rt')
usernameLine = configFile.readline()
passwordLine = configFile.readline()
nLine = configFile.readline()
fromemailLine = configFile.readline()
toemailLine = configFile.readline()
msgLine = configFile.readline()
configFile.close()
if "<yourgmail's>" in usernameLine:
sys.stderr.write("NoSettings ERROR: modify the config.txt file before you run the program.")
elif "<yourgmail's>" in passwordLine:
sys.stderr.write("NoSettings ERROR: modify the config.txt file before you run the program.")
elif "<int>" in nLine:
sys.stderr.write("NoSettings ERROR: modify the config.txt file before you run the program.")
elif "<youremail>" in fromemailLine:
sys.stderr.write("NoSettings ERROR: modify the config.txt file before you run the program.")
elif "<emailtospam>" in toemailLine:
sys.stderr.write("NoSettings ERROR: modify the config.txt file before you run the program.")
elif "<msg>" in msgLine:
sys.stderr.write("NoSettings ERROR: modify the config.txt file before you run the program.")
else:
sys.stdout.write("Running..")
#DECLARING THE MAIN VARIABLES
u = str(usernameLine[11:])
pw = str(passwordLine[11:])
n = str(nLine[27:])
fromemail = str(fromemailLine[12:])
toemail = str(toemailLine[10:])
msg = str(msgLine[10:])
#DELETING SPACES IN THE FILE TO STORE CORRECTLY THE DATA
u.split(" ")
pw.split(" ")
n.split(" ")
fromemail.split(" ")
toemail.split(" ")
msg.split(" ")
data = [u, pw, n, fromemail, toemail, msg]
return data
def emailSetupAndGo(n, username, password, fromemail, toemail, message):
server = smtplib.SMPT('smtp.gmail.com:587')
server.starttls()
server.login(username, password)
for i in n:
server.sendmail(fromemail, toemail, message)
server.quit()
def help():
sys.stdout.write("enter any key to exit\nenter 'spam' to spam an email\n")
while True:
help()
entered = input("Enter: ")
if entered == 'spam':
getData()
emailSetupAndGo(getData()[0], getData()[1], getData()[2], getData()[3], getData()[4], getData()[5])
else:
break
And here you are the config file:
username = <yourgmail's>
password = <yourgmail's>
number of emails to spam = <int>
fromemail = <youremail>
toemail = <emailtospam>
message = <msg>
Background:
I would like to integrate yowsup to my home automation project. I have seen a simple sample on how to receive messages and after some minor changes it is working fine.
Issue:
My problem starts when it comes to integrate the send message feature. Those are the two files I am using:
run.py
from layer import EchoLayer
from yowsup.layers.auth import YowAuthenticationProtocolLayer
from yowsup.layers.protocol_messages import YowMessagesProtocolLayer
from yowsup.layers.protocol_receipts import YowReceiptProtocolLayer
from yowsup.layers.protocol_acks import YowAckProtocolLayer
from yowsup.layers.protocol_presence import YowPresenceProtocolLayer
from yowsup.layers.network import YowNetworkLayer
from yowsup.layers.coder import YowCoderLayer
from yowsup.common import YowConstants
from yowsup.layers import YowLayerEvent
from yowsup.stacks import YowStack, YOWSUP_CORE_LAYERS
from yowsup import env
CREDENTIALS = ("phone", "pwd")
if __name__ == "__main__":
layers = (
EchoLayer,
(YowAuthenticationProtocolLayer, YowMessagesProtocolLayer, YowReceiptProtocolLayer, YowAckProtocolLayer, YowPresenceProtocolLayer)
) + YOWSUP_CORE_LAYERS
stack = YowStack(layers)
# Setting credentials
stack.setProp(YowAuthenticationProtocolLayer.PROP_CREDENTIALS, CREDENTIALS)
# WhatsApp server address
stack.setProp(YowNetworkLayer.PROP_ENDPOINT, YowConstants.ENDPOINTS[0])
stack.setProp(YowCoderLayer.PROP_DOMAIN, YowConstants.DOMAIN)
stack.setProp(YowCoderLayer.PROP_RESOURCE, env.CURRENT_ENV.getResource())
# Sending connecting signal
stack.broadcastEvent(YowLayerEvent(YowNetworkLayer.EVENT_STATE_CONNECT))
# Program main loop
stack.loop()
layer.py
from yowsup.layers.interface import YowInterfaceLayer, ProtocolEntityCallback
from yowsup.layers.protocol_messages.protocolentities import TextMessageProtocolEntity
from yowsup.layers.protocol_receipts.protocolentities import OutgoingReceiptProtocolEntity
from yowsup.layers.protocol_acks.protocolentities import OutgoingAckProtocolEntity
from yowsup.layers.protocol_presence.protocolentities import PresenceProtocolEntity
import threading
import logging
logger = logging.getLogger(__name__)
class EchoLayer(YowInterfaceLayer):
#ProtocolEntityCallback("message")
def onMessage(self, messageProtocolEntity):
#send receipt otherwise we keep receiving the same message over and over
print str(messageProtocolEntity.getFrom()) + ' - ' + str(messageProtocolEntity.getBody())
receipt = OutgoingReceiptProtocolEntity(messageProtocolEntity.getId(), messageProtocolEntity.getFrom())
self.toLower(receipt)
#ProtocolEntityCallback("send_message")
def sendMessage(self, destination, message, messageProtocolEntity):
outgoingMessageProtocolEntity = TextMessageProtocolEntity(
message,
to = destination + "#s.whatsapp.net")
self.toLower(outgoingMessageProtocolEntity)
#ProtocolEntityCallback("receipt")
def onReceipt(self, entity):
ack = OutgoingAckProtocolEntity(entity.getId(), "receipt", "delivery")
self.toLower(ack)
# List of (jid, message) tuples
PROP_MESSAGES = "org.openwhatsapp.yowsup.prop.sendclient.queue"
def __init__(self):
super(EchoLayer, self).__init__()
self.ackQueue = []
self.lock = threading.Condition()
#ProtocolEntityCallback("success")
def onSuccess(self, successProtocolEntity):
self.lock.acquire()
for target in self.getProp(self.__class__.PROP_MESSAGES, []):
phone, message = target
if '#' in phone:
messageEntity = TextMessageProtocolEntity(message, to = phone)
elif '-' in phone:
messageEntity = TextMessageProtocolEntity(message, to = "%s#g.us" % phone)
else:
messageEntity = TextMessageProtocolEntity(message, to = "%s#s.whatsapp.net" % phone)
self.ackQueue.append(messageEntity.getId())
self.toLower(messageEntity)
self.lock.release()
#ProtocolEntityCallback("ack")
def onAck(self, entity):
self.lock.acquire()
if entity.getId() in self.ackQueue:
self.ackQueue.pop(self.ackQueue.index(entity.getId()))
if not len(self.ackQueue):
logger.info("Message sent")
#raise KeyboardInterrupt()
self.lock.release()
Questions:
Where am I supposed to call the send_message method, so I can send messages wherever I need it?
Is there a regular event (triggering every second or something) which I could use to send my messages?
#ProtocolEntityCallback("send_message")
def sendMessage(self, destination, message, messageProtocolEntity):
outgoingMessageProtocolEntity = TextMessageProtocolEntity(
message,
to = destination + "#s.whatsapp.net")
self.toLower(outgoingMessageProtocolEntity)
In the avove code sendMessage to be called, protocolEntity.getTag() == "send_message" has to be True. You don't need it to send message.
layer.py
from yowsup.layers.interface import YowInterfaceLayer, ProtocolEntityCallback
from yowsup.layers.protocol_messages.protocolentities import TextMessageProtocolEntity
from yowsup.layers.protocol_receipts.protocolentities import OutgoingReceiptProtocolEntity
from yowsup.layers.protocol_acks.protocolentities import OutgoingAckProtocolEntity
from yowsup.layers.protocol_presence.protocolentities import PresenceProtocolEntity
import threading
import logging
logger = logging.getLogger(__name__)
recv_msg = []
class EchoLayer(YowInterfaceLayer):
def __init__(self):
super(EchoLayer, self).__init__()
self.ackQueue = []
self.lock = threading.Condition()
#ProtocolEntityCallback("message")
def onMessage(self, messageProtocolEntity):
if messageProtocolEntity.getType() == 'text':
recv_msg.append((messageProtocolEntity.getFrom(),messageProtocolEntity.getBody()))
#send receipt otherwise we keep receiving the same message over and over
receipt = OutgoingReceiptProtocolEntity(messageProtocolEntity.getId(), messageProtocolEntity.getFrom())
self.toLower(receipt)
#ProtocolEntityCallback("receipt")
def onReceipt(self, entity):
ack = OutgoingAckProtocolEntity(entity.getId(), "receipt", "delivery")
self.toLower(ack)
# List of (jid, message) tuples
PROP_MESSAGES = "org.openwhatsapp.yowsup.prop.sendclient.queue"
#ProtocolEntityCallback("success")
def onSuccess(self, successProtocolEntity):
self.lock.acquire()
for target in self.getProp(self.__class__.PROP_MESSAGES, []):
phone, message = target
if '#' in phone:
messageEntity = TextMessageProtocolEntity(message, to = phone)
elif '-' in phone:
messageEntity = TextMessageProtocolEntity(message, to = "%s#g.us" % phone)
else:
messageEntity = TextMessageProtocolEntity(message, to = "%s#s.whatsapp.net" % phone)
self.ackQueue.append(messageEntity.getId())
self.toLower(messageEntity)
self.lock.release()
#ProtocolEntityCallback("ack")
def onAck(self, entity):
self.lock.acquire()
if entity.getId() in self.ackQueue:
self.ackQueue.pop(self.ackQueue.index(entity.getId()))
if not len(self.ackQueue):
self.lock.release()
logger.info("Message sent")
raise KeyboardInterrupt()
self.lock.release()
To send message define a function send_message in the stack run.py. You can also import run.py and use it's function from other script.
from layer import EchoLayer, recv_msg
CREDENTIALS = ("phone", "pwd")
def send_message(destination, message):
'''
destination is <phone number> without '+'
and with country code of type string,
message is string
e.g send_message('11133434343','hello')
'''
messages = [(destination, message)]
layers = (EchoLayer,
(YowAuthenticationProtocolLayer,
YowMessagesProtocolLayer,
YowReceiptProtocolLayer,
YowAckProtocolLayer,
YowPresenceProtocolLayer)
) + YOWSUP_CORE_LAYERS
stack = YowStack(layers)
stack.setProp(EchoLayer.PROP_MESSAGES, messages)
stack.setProp(YowAuthenticationProtocolLayer.PROP_PASSIVE, True)
# Setting credentials
stack.setProp(YowAuthenticationProtocolLayer.PROP_CREDENTIALS, CREDENTIALS)
# WhatsApp server address
stack.setProp(YowNetworkLayer.PROP_ENDPOINT, YowConstants.ENDPOINTS[0])
stack.setProp(YowCoderLayer.PROP_DOMAIN, YowConstants.DOMAIN)
stack.setProp(YowCoderLayer.PROP_RESOURCE, env.CURRENT_ENV.getResource())
# Sending connecting signal
stack.broadcastEvent(YowLayerEvent(YowNetworkLayer.EVENT_STATE_CONNECT))
try:
# Program main loop
stack.loop()
except AuthError as e:
print('Authentication error %s' % e.message)
sys.exit(1)
def recv_message():
layers = ( EchoLayer,
(YowAuthenticationProtocolLayer, YowMessagesProtocolLayer,
YowReceiptProtocolLayer, YowAckProtocolLayer,
YowPresenceProtocolLayer)
) + YOWSUP_CORE_LAYERS
stack = YowStack(layers)
# Setting credentials
stack.setProp(YowAuthenticationProtocolLayer.PROP_CREDENTIALS, CREDENTIALS)
# WhatsApp server address
stack.setProp(YowNetworkLayer.PROP_ENDPOINT, YowConstants.ENDPOINTS[0])
stack.setProp(YowCoderLayer.PROP_DOMAIN, YowConstants.DOMAIN)
stack.setProp(YowCoderLayer.PROP_RESOURCE, env.CURRENT_ENV.getResource())
# Sending connecting signal
stack.broadcastEvent(YowLayerEvent(YowNetworkLayer.EVENT_STATE_CONNECT))
try:
# Program main loop
stack.loop()
except AuthError as e:
print('Authentication error %s' % e.message)
sys.exit(1)
if __name__ == '__main__':
if len(sys.argv) == 1:
print('%s send number message\nrecv\n' % sys.argv[0])
sys.exit(1)
if sys.argv[1] == 'send':
try:
send_message(sys.argv[2],sys.argv[3])
except KeyboardInterrupt:
print('closing')
sys.exit(0)
if sys.argv[1] == 'recv':
try:
recv_message()
except KeyboardInterrupt:
print('closing')
sys.exit(0)
for m in recv_msg:
print('From %s:\n%s\n' % m)
Now you can send message by calling send_message('1234567890','Howdy') and recieve message by calling recv_message().