I recently purchased a Raspberry Pi to run some Python scripts, but when I ported it the function I wrote to send emails through Windows Live suddenly started handing out an SSL error after successful handshake, specifically:
error:1408F10B:SSL routines:SSL3_GET_RECORD:wrong version number
After extensive searching around, I found many people with the same error, but all in vastly different situations. The most relevant thing I could find was that it seemed to be an issue with a specific version of OpenSSL, but I could find nothing about the version running on my Pi (1.0.1e).
The function (which works perfectly fine on Win7):
def wlive(adr_to, adr_fro, adr_pass, adr_subj, adr_file):
saveout = smtplib.stderr
logger = open('wlive.log', 'w')
smtplib.stderr = logger
msg = MIMEMultipart()
msg['Subject'] = adr_subj
msg['From'] = adr_fro
msg['To'] = adr_to
if adr_file != None:
# subtype recognition based on extension
filext = os.path.splitext(adr_file)[1]
if filext == '.png':
subt = 'png'
else:
subt = 'jpeg'
fp = open(adr_file, 'rb')
img = MIMEImage(fp.read(), subt)
fp.close()
msg.attach(img)
try:
server = smtplib.SMTP('smtp.live.com', 587)
server.set_debuglevel(1)
server.ehlo()
server.starttls()
server.login(adr_fro, adr_pass)
server.sendmail(adr_fro, adr_to, msg.as_string())
server.quit()
return True
except Exception, e:
print 'wlive exception:\n\n', str(e)
return False
smtplib.stderr = saveout
logger.close()
I'm running the fully updated and upgraded Raspbian "Wheezy" image, and Python 2.7.3
I encountered this problem yesterday. First thing to try is to change the account from which you want to send an email to some other provider: try gmail, for instance. In my case it started working instantly.
If it's also the case for you (Microsoft's fault?), try another thing with windows live account (similar to the one suggested in the comment):openssl s_client -connect smtp.live.com:587 -starttls smtp -crlf -ign_eof
then type:
ehlo
auth login
In my case nothing happened. No answer, only read timeout. This time try:
openssl s_client -connect smtp.live.com:587 -starttls smtp -crlf -ign_eof -no_tls1_2
Then:
ehlo
auth login
I got an answer immediately. If it's still your case, there's a little problem. I haven't found any way to specify such a parameter (which versions of tls to prevent from being used). What I found is that in python 3.3 you can give an additional context argument instarttls and you should be able to define some cipher parameters in this context. List of options can be found here.
I must admit that it was easier for me to just use the gmail account than to get python 3.3 (on rpi you've got 3.2 with no possibility of specifying the context), not being even sure if it will help. However, I hope that this information helps you somehow.
Related
I am trying to send emails with gmail using the smtp module for an amazon price tracker. A few days ago, it was working perfectly but today it came up with this error:
File "C:\Users\61409\AppData\Local\Programs\Python\Python39\lib\smtplib.py", line 755, in starttls
raise SMTPNotSupportedError(
smtplib.SMTPNotSupportedError: STARTTLS extension not supported by server.
This is the code that originally worked but gives the error:
import smtplib
def send_email():
server = smtplib.SMTP('smtp.gmail.com', 587)
server.ehlo()
server.starttls()
server.ehlo()
server.login('xxxxxxxx#gmail.com', '*password*')
subject = f'The price of your product has fallen'
body = f'Check the amazon link - {URL}'
msg = f"Subject: {subject}\n\n{body}"
server.sendmail(
'xxxxxxx#gmail.com',
'xxxxxxx#gmail.com',
msg
)
print('The email has been sent')
server.quit()
I have tried making another gmail account and using SSL (importing ssl too) but the other gmail account comes up with the same problem and when using SSL, it comes up with a SMTP AUTH problem (unable to solve this too). I have allowed less secure apps but the same problem still occurs. I have also tried removing the first server.ehlo() and I have also tried using the server.set_debuglevel(1) but both do not work. I have also tried using with stmplib.SMTP(*Host*, *Port*) as server: and I have tried just using SMTP without using SSl and TLS at all but both answers do not work. Most of the answers removed the smtplib.SMTPNotSupportedError: STARTTLS extension not supported by server. but other problems occured such as smtplib.SMTPServerDisconnected: Connection unexpectedly closed which happened numerous times with other answers. I tried researching on solutions to the connection unexpectedly closing but none of those answers worked too.
These are the answers I have tried:
SMTPException: STARTTLS extension not supported by server
smtplib.SMTPNotSupportedError: STARTTLS extension not supported by server
Python 2: SMTPServerDisconnected: Connection unexpectedly closed
Python3 SMTP 'Connection unexpectedly closed'
https://www.reddit.com/r/Python/comments/5grxy8/python_smtplib_connection_unexpectedly_closed/daumi2m/
How to send an email with Python?
How can I fix this problem?, am I missing something?? Will I need to use another module or library to send emails??? I apologise if this is a repeat question with a viable answer. I also apologise if one of the answers I mentioned as not working does actual work except I screwed up the code.
smtplib.SMTPNotSupportedError: STARTTLS extension not supported by server.
The SMTP connection to the server does not seem to offer the STARTTLS extension, at least as seen from the perspective of the client. This extension is announced inside the response to the initial EHLO command of the client:
$ telnet smtp.gmail.com 587
...
Connected to smtp.gmail.com.
Escape character is '^]'.
220 smtp.gmail.com ESMTP h9sm19557267wre.24 - gsmtp
EHLO mail.example.com
250-smtp.gmail.com at your service, ...
250-SIZE 35882577
250-8BITMIME
250-STARTTLS <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<
...
Given that smtp.gmail.com definitely supports this extension it is likely that there is some man in the middle somewhere in path of the connection, which rewrites the traffic to something like this:
220 smtp.gmail.com ESMTP h9sm19557267wre.24 - gsmtp
EHLO mail.example.com
250-smtp.gmail.com at your service, ...
250-SIZE 35882577
250-8BITMIME
250-XXXXXXXA <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<
...
Here the response of the server is changed to no longer show support for STARTTLS, in the hope that the client continues without encryption and thus the mail can be analyzed be the man in the middle. Such man in the middle are typically corporate firewalls like Cisco ASA but can also be ISP or local antivirus products.
A few days ago, it was working perfectly but today it came up with this error:
Check if there were any changes regarding local security products (antivirus) or its settings or if there are changes to your environment (corporate firewall, different network you use ...).
I had the same problem: smtplib working properly and then returning this same error, without any change in the server (outlook).
It just so happens that I had refactored my code, and the function that sent the email was deeper in the modules.
If I used the old way, it worked!
When I turned off the anti-virus (AVG in my case), all worked just fine!
So, for some reason, the code refactoring made the sending procedure to be caught by anti-virus.
I started a little Raspberry project and stuck with sending a simple E-Mail. Gmail smtp is set up. The code works fine from Thonny (although it sends the E-Mal only for the first receiver and not both), but when I trigger it from the terminal (python report.py), I get the following Error:
Traceback (most recent call last):
File "report.py", line 15, in <module>
with smtplib.SMTP_SSL(smtp_server, port, context=context) as server:
TypeError: __init__() got an unexpected keyword argument 'context'
As I mentioned above, from Thonny it is working. I plan to trigger some script like this time scheduled through Crontab. I set up the Crontab file, but it does nothing, I assume because it makes an error every time.
Thank you for help in advance!
The report.py content:
import smtplib, ssl
port = 465 # For SSL
smtp_server = "smtp.gmail.com"
sender_email = "****#gmail.com"
receiver_email = "****#gmail.com,xxxx#gmail.com"
password = "****"
message = """\
Subject: Hi there
This message is sent from Python."""
context = ssl.create_default_context()
with smtplib.SMTP_SSL(smtp_server, port, context=context) as server:
server.login(sender_email, password)
server.sendmail(sender_email, receiver_email, message)
The context argument to smtplib.SMTP_SSL was added in Python 3.3.
Thonny uses a built-in Python3.7 interpreter, but many Unix-like operating systems' default Python interpreter is Python 2.x. Explicitly call the script with Python 3 to prevent the error:
python3 report.py
In one of my projects I have to create python application to send email reports from local machine, using external smtp infrastructure.
I am using python 2.7.13 (latest at the moment) on local windows computer for testing and aws EC2 windows instance for production (same python version).
The code is: (simplified version)
s = smtplib.SMTP('smtp.host.com', 587)
s.ehlo()
s.starttls()
s.ehlo()
s.login('email#domain.com', 'password');
s.sendmail(from_to, from_to, m.as_string())
s.quit()
Everything works great on local computer, but while running on amazon ec2, I'm getting:
smtplib.SMTPRecipientsRefused: {'email#domain.com': (450, '4.7.1 <MY-INSATNCE-ID.aws-region.compute.internal>: Helo command rejected: Host not found')}
The problem is (was) that EC2 instance has configured local FQDN. It was bound to internal domain name system, therfore remote smtp server was not able to resolve and confirm it.
On the other hand, local computer used unknown FQDN passing only its local ip, which was ok for smtp server. I'm not sure if it is not a security issue.
The problem may be solved by adding local_hostname parameter to SMTP constructor.
Square brackets are obligatory.
s = smtplib.SMTP('smtp.host.com', 587)
to
s = smtplib.SMTP('smtp.host.com', 587, '[127.0.0.1]')
I have a python function to send an email notification. I have included the login call to authenticate with my local SMTP server, however emails are being returned stating '553-mail rejected because your IP is in the PBL'. Further reading on https://www.spamhaus.org/pbl reveals that apparently I am not being prevented from sending email, I am simply required to authenticate first.
I have tried base64 encoding to avoid sending the password as plain text without success.
I have also looked at the Pysasl library, but I am a little unsure how I might use this for authenticating with my SMTP server.
Would anyone have any guidance as to the correct use of either base64 encoding, the pysasl library or if a better method exists for satisfying the correct authentication requirements?
My code is below.
def emailNotify(self,userid):
SMTPserver = 'localhost'
sender = '***' # blanked
username = '***' # blanked
receiver = '***' # blanked
pwd = '***' # blanked
text_subtype = 'plain'
msg = 'requested data was posted to dashboard for '+userid
subject = 'confirmation of POST\'d data for '+userid
try:
msg = MIMEText(msg, text_subtype)
msg['Subject'] = subject
msg['From'] = sender
conn = smtplib.SMTP(SMTPserver)
conn.login(username, pwd)
try:
conn.sendmail(sender, receiver, msg.as_string())
finally:
conn.quit()
except:
print('message sending failed')
Thanks in advance.
You have 2 ways of building a program for sending mail:
build a bullet proof solution:
analyze what server announces as its capabilities
choose the one that better meets your requirement
use that authentication method
actually send the mail
simply that means that you have to implement code for reading and decoding what the server returns (which can be weird) and also all various authentication methods, not speaking of TLS
use a custom connection method adapted to that server
read the documentation of the server to know what it declares to support
test it manually first through a mere telnet connection then in an interactive Python session (idle is enough here, but you can choose your prefered Python shell)
carefully program the way you have just tested - but leave relevant error messages in cases the server capabilities change...
IMHO much simpler...
as indicated by the title I am having trouble sending an email via my gmail account through a python application.I have searched online for a solution but nothing seems to solve it and I thought I might ask here.
My code is the following:
FROMADDR = "myemail#gmail.com"
LOGIN = FROMADDR
PASSWORD = "mypass"
TOADDRS = "varis81#hotmail.com"
msg = "Test message"
server = smtplib.SMTP('smtp.gmail.com', 587)
server.set_debuglevel(1)
server.ehlo()
server.starttls()
server.login(LOGIN, PASSWORD)
server.sendmail(FROMADDR, TOADDRS, msg)
server.quit()
print "E-mail succesfully sent"
I get the message:
socket.error: [Errno 10060] A connection attempt failed because the connected party did not properly respond after a period of time, or established connection failed because connected host has failed to respond
I tried different ports but it doesn't work also.I also tried hotmail but it causes the same problem.I am using Python 2.7 (don't ask :) ) on a Windows 7 machine developing on Eclipse using PyDev.
Any help would be great!
Thank you in advance.
I'm using the same construct on one of my servers. My code is below.
The only difference is the extra .ehlo() after '.starttls()`. This should not be the issue; from the RFC:
5.2 Result of the STARTTLS Command
The client SHOULD send an EHLO command as the first
command after a successful TLS negotiation.
According to the RFC, the server should not sever a connection if the client does not send ehlo after starttls, but Google could be more restrictive on their SMTP server. I'd check that first. (I've seen providers tighten down on these kinds of conditions to reduce spam, see Mailinator's 2007 writeup for instance.)
It could also be filtered ports - try running the code in the REPL and confirm which line is exceptioning, if it's the connect() you'll know it's network. If it's after, it's likely your usage of smtplib.
Of note, I also experienced occasional unclean shutdowns, resulting in the try/except around .close().
import smtplib
s = smtplib.SMTP()
s.connect("smtp.gmail.com")
s.ehlo()
s.starttls()
s.ehlo()
s.login("from#gmail.com", "frompass")
s.sendmail("fromname#gmail.com", toAddr, bytes)
try:
s.close()
except: pass
Well, since I cant post comments yet I'll have to attempt an answer..
Judging by this: Python SMTP Errno 10060
Perhaps a timeout would help?