13

I have the following code which gets me the inbox of my shared folder, and all of the emails inside. This code works great and will print the subject of the last email.

outlook = win32com.client.Dispatch("Outlook.Application").GetNamespace("MAPI")
recip = outlook.CreateRecipient("foo@bar.com")
inbox = outlook.GetSharedDefaultFolder(recip, 6)
messages = inbox.Items
message = messages.GetLast()
print (message.Subject)

I can access other parent folders in foo@bar.com's mailbox (like Sent), but I can't get any subfolders of a folder within the inbox, or deeper than that. So if I want inbox\subfolder1, how do I access that? Using Outlook 2013 if that matters. My main goal is to do:

message.Move(inbox\subfolder1)
nico
  • 179
  • 2
  • 3
  • 9

8 Answers8

22

Yeah its better to write it as the name of the folder instead of writing the folder numbers

Like my folder hierarchy is : Outlook_Mails > Inbox > Important

outlook = win32.com.client.Dispatch("Outlook.Application")
mapi = outlook.GetNamespace("MAPI")

your_folder = mapi.Folders['Outlook_Mails'].Folders['Inbox'].Folders['Important']
for message in your_folder.Items:
    print(message.Subject)
Sir Tesla
  • 320
  • 2
  • 10
6

This is the code I'm using to do a similar task.

outlook = win32com.client.Dispatch("Outlook.Application")
namespace = outlook.GetNamespace("MAPI")
root_folder = namespace.Folders.Item(1)
subfolder = root_folder.Folders['All'].Folders['Main Folder'].Folders['Subfolder']
messages = subfolder.Items

This finds the messages in the folder "All/Main Folder/Subfolder".

Jared Goguen
  • 8,772
  • 2
  • 18
  • 36
  • I love the idea for this, but do you know how to get it to work on a shared mailbox? I tried setting root_folder equal to outlook.GetSharedDefaultFolder(recip, 6) from my initial code, but no luck. – nico Nov 28 '16 at 17:32
  • @nico With that change does `root_folder` have a `Folders` property? It seems like that would set the inbox as `root_folder` so a subfolder would be found with `root_folder.Folders['Subfolder']`. If not, I have no idea, sorry. – Jared Goguen Nov 28 '16 at 18:09
  • Although, `GetSharedDefaultFolder` should return a `Folder` who's API can be found here: [Folder API](https://msdn.microsoft.com/en-us/library/office/ff863890.aspx). – Jared Goguen Nov 28 '16 at 18:12
  • setting root_folder equal to GetSharedDefaultFolder(recip, 6) does set it equal to the inbox, and printing root_folder prints "Inbox". If it's returning a Folder, shouldn't I be able to access inbox\subfolder? Forgive my ignorance, but I don't understand why. The Folder API shows that it has a Folders attribute. – nico Nov 28 '16 at 18:21
  • This is perfect and worked perfectly for me. Thank you! – Matt W. Mar 08 '18 at 14:38
3

Can't do that - Outlook caches shared default folders in the main OST file The subfolders are not cached. If the mailbox in question is added as a delegate store, you should be able to parse to the folder in question using Namespace.Folders or Namespace.Stores.

Otherwise you can use Redemption (I am its author) and its RDOSession.GetSharedDefaultFolder - the folder will be opened in the online mode with all of its subfolders (RDOFolder.Folders).

Dmitry Streblechenko
  • 62,942
  • 4
  • 53
  • 78
  • Well darn. That sucks. Thanks for the insight. Unfortunately I'm limited with what tools I can use, so I was trying to find a way to do this with just Python. – nico Nov 29 '16 at 12:00
2
def processfolder(folder):

    ignoredfolders = []
    
    if not folder.Name in ignoredfolders:
        print("processing", folder.Name)
        count=0
        for mail in folder.Items:
               savemsg(mail)
               count += 1

        print(count, "Mails in folder")
        for fld in folder.Folders:
            processfolder(fld)
Anonymous
  • 738
  • 4
  • 14
  • 36
Gerry
  • 21
  • 1
1

This is the way I did it. Have to add "Folders" attribute to each level down.

import win32com.client as client

outlook = client.Dispatch('Outlook.Application')
namespace = outlook.GetNameSpace('MAPI')
inbox = namespace.GetDefaultFolder(6)

for i in inbox.Folders:
    print('Top Folder is:', i)
    for folder in inbox.Folders[str(i)].Folders:
        print('2nd tier folder is:', folder)
        for nfolder in inbox.Folders[str(i)].Folders[str(folder)].Folders:
            print('3nd tier folder is:', nfolder)
Igor
  • 1,212
  • 12
  • 23
0

Sir Tesla. Actually, I followed up your code pattern & change it as per my current project. Please find the below specimen code.

import win32com.client
outlook = win32com.client.Dispatch("Outlook.application")
mapi = outlook.GetNamespace("MAPI")
FirstFMB = mapi.Folders['FirstFMB'].Folders['Inbox']
SecondFMB = mapi.Folders['SecondFMB'].Folders['Another_folder']

<Hence other loops & operations as per requirement>

Here I got to know, one thing. When we need to perform with some kind Function Mail Boxes then we just need to put the name under mapi.Folder[] then just go with the flow.

Sir Tesla your code pattern was helpful for me instead of using Folder number.

On another side, this technique helps me to append mail reading & taking action within a certain time frame.

Ozzius
  • 131
  • 2
  • 8
0
import win32com.client as win32

# new outlook object
outlook = win32.Dispatch("Outlook.Application")

# get user namespace *Important when reading email*
namespace = outlook.GetNamespace("MAPI")

# Default inbox folder either Folders.Item(1/2)
root_folder = namespace.Folders.Item(2)

# Use this function to display subfolders inside the current folder

def menu(outlookFolderItem):
    for i in range(0,20):
        try:
            print(i,outlookFolderItem.Folders(i).Name)
        except:
            pass

# example
menu(root_folder)

# navigate into the subfile by

sub_folder = root_folder.Folders(2).Folders(14)
-1

I took Jared Goguen's answer and modified it.

outlook = win32com.client.Dispatch("Outlook.Application").GetNamespace("MAPI")
inbox = outlook.GetDefaultFolder(6)
root_folder = inbox.Folders(6)
messages = root_folder.Items

Where inbox.Folders(6) uses the index of my subfolder of interest to identify it. I was able to successfully iterate through the messages in the subfolder using this message.

cole
  • 125
  • 9