Chapter 15 ■ IMap
270
b'(\HasNoChildren) "/" "Travel"'
b'(\HasNoChildren) "/" "Work"'
b'(\Noselect \HasChildren) "/" "[Gmail]"'
b'(\HasChildren \HasNoChildren) "/" "[Gmail]/All Mail"'
b'(\HasNoChildren) "/" "[Gmail]/Drafts"'
b'(\HasChildren \HasNoChildren) "/" "[Gmail]/Sent Mail"'
b'(\HasNoChildren) "/" "[Gmail]/Spam"'
b'(\HasNoChildren) "/" "[Gmail]/Starred"'
b'(\HasChildren \HasNoChildren) "/" "[Gmail]/Trash"'
But things fall apart when you turn to the results of the list() method. First, you will be returned its status code
as the plain string 'OK', so code that uses imaplib has to check incessantly on whether the code is 'OK' or whether
it indicates an error. This is not terribly Pythonic, because Python programs can usually run without doing error
checking and be secure in the knowledge that an exception will be thrown if anything goes wrong.
Second, imaplib provides no help in interpreting the results! The list of e-mail folders in this IMAP account uses
all sorts of protocol-specific quoting: each item in the list names the flags set on each folder, then it designates the
character used to separate folders and subfolders (the slash character, in this case), and finally it supplies the quoted
name of the folder. But all of this is returned to raw data, requiring you to interpret strings like the following:
(\HasChildren \HasNoChildren) "/" "[Gmail]/Sent Mail"
Third, the output is a mix of different sequences: the flags are still uninterpreted byte strings, while each delimiter
and folder name has been decoded to a real Unicode string.
So, unless you want to implement several details of the protocol yourself, you will want a more capable IMAP
client library.
IMAPClient
Fortunately, a popular and battle-tested IMAP library for Python does exist, and it is available for easy installation
from the Python Package Index. Menno Smits, a friendly Python programmer, wrote the IMAPClient package, and it in
fact uses the Python Standard Library imaplib behind the scenes to do its work.
If you want to try out IMAPClient, try installing it in a “virtualenv,” as described in Chapter 1. Once installed, you
can use the python interpreter in the virtual environment to run the program, as shown in Listing 15-3.
Listing 15-3. Listing IMAP Folders with IMAPClient
#!/usr/bin/env python3
Foundations of Python Network Programming, Third Edition
https://github.com/brandon-rhodes/fopnp/blob/m/py3/chapter15/open_imap.py
Opening an IMAP connection with the powerful IMAPClient
import getpass, sys
from imapclient import IMAPClient
def main():
if len(sys.argv) != 3:
print('usage: %s hostname username' % sys.argv[0])
sys.exit(2)