6

i need to do a script for imap backup but when i'm trying to connect to the imap server with my script i'm getting that error:

  File "c:\Users\Lenovo\Desktop\python\progettoscuola.py", line 5, in <module>  
    imapSrc = imaplib.IMAP4_SSL('mail.safemail.it')
  File "C:\Program Files\Python310\lib\imaplib.py", line 1323, in __init__      
    IMAP4.__init__(self, host, port, timeout)
  File "C:\Program Files\Python310\lib\imaplib.py", line 202, in __init__       
    self.open(host, port, timeout)
  File "C:\Program Files\Python310\lib\imaplib.py", line 1336, in open
    IMAP4.open(self, host, port, timeout)
  File "C:\Program Files\Python310\lib\imaplib.py", line 312, in open
    self.sock = self._create_socket(timeout)
  File "C:\Program Files\Python310\lib\imaplib.py", line 1327, in _create_socket
    return self.ssl_context.wrap_socket(sock,
  File "C:\Program Files\Python310\lib\ssl.py", line 512, in wrap_socket        
    return self.sslsocket_class._create(
  File "C:\Program Files\Python310\lib\ssl.py", line 1070, in _create
    self.do_handshake()
  File "C:\Program Files\Python310\lib\ssl.py", line 1341, in do_handshake      
    self._sslobj.do_handshake()
ssl.SSLError: [SSL: SSLV3_ALERT_HANDSHAKE_FAILURE] sslv3 alert handshake failure (_ssl.c:997)```
Yehor
  • 63
  • 1
  • 1
  • 3

1 Answers1

13

Python 3.10 increased the default security settings of the TLS stack by among other things prohibiting any ciphers which still use the RSA key exchange. RSA key exchange is long considered inferior since it does not provide forward secrecy and is therefore also no longer available in TLS 1.3. So in general the change in Python 3.10 can be considered an improvement.

But, some servers still require this obsolete key exchange and mail.safemail.it seems to be among these. Connecting to such servers with the newly hardened TLS settings will now fail, even if it succeeded with older versions of Python.

To make connections possible again it is necessary to use weaker security settings. For this specific server it can be done by falling back to the DEFAULT ciphers used by OpenSSL. The following code will create a new SSL context and use it for connecting to the host. The important part here is to use weaker settings using ctx.set_ciphers('DEFAULT') .

import imaplib
import ssl
ctx = ssl.create_default_context()
ctx.set_ciphers('DEFAULT')
imapSrc = imaplib.IMAP4_SSL('mail.safemail.it', ssl_context = ctx)
Steffen Ullrich
  • 114,247
  • 10
  • 131
  • 172
  • Ok, i did it and now i dont get that error, so thank you. But can i make something to make my code weaker because of `ctx.set_ciphers('DEFAULT')`? – Yehor Feb 06 '22 at 16:44
  • 1
    @Yehor: The actual cipher chosen for the connection uses RSA key exchange. This key exchange is considered obsolete since it does not provide forward secrecy, i.e. some attacker can sniff traffic and decrypt this sniffed traffic much later once they managed to steal the servers private key. You don't actually have a choice to use a more secure cipher though - only the choice between a weaker cipher or not being able to do a TLS connection with this server at all. Note though that for most purposes RSA key exchange is still sufficiently secure. – Steffen Ullrich Feb 06 '22 at 17:00
  • @SteffenUllrich, you're saying that the issue is observed b/c of the default RSA key exchange. However, when I setup the cipher to RSA, e.g.: `set_ciphers('RSA')` - the issue is also goes away. How comes? does setting RSA cipher also somehow sets better key exchange? (which would be confusing) – Dmitry Apr 18 '22 at 09:59
  • 2
    @Dmitry: *"you're saying that the issue is observed b/c of the default RSA key exchange"* - I'm saying that the server requires RSA key exchange while the client does not support RSA key exchange by default. Changing the client settings to allow RSA key exchange (by using DEFAULT or explicitly RSA) solves the problem, since the server now gets what it wants from the client. – Steffen Ullrich Apr 18 '22 at 12:17