简体   繁体   中英

How to allow programmatic access to Outlook with python?

I am looking for a solution to override Outlook's warning:

在此处输入图像描述

What I want is to allow access do the api for 10 minutes by operating on the window pop-up in a separate thread (window suspends main thread). Please note that workarounds related to Redemption library, updating Trust Center Settings or Registry are non-applicable in my working environment.

The code at this point detects the window, chooses the "10 minutes" option from the dropdown but it fails to set focus to "Allow" button and finally perform a click on it.

class OutlookAccess_Watcher(QRunnable):


   def __init__(self):
       super().__init__()

   def run(self):

       while True:
        
            if win32gui.FindWindowEx(win32gui.FindWindow(None, "Microsoft Outlook"), 0, "Static", "DAL=on"):
                window = win32gui.FindWindow(None, "Microsoft Outlook")
                combo_btn = win32gui.FindWindowEx(window, 0, "Button", "&Allow access for")

                if win32gui.SendMessage(combo_btn, BM_GETCHECK, 0, 0):
                     combo_box = get_combobox_id(objects_window_finder(window))
                     win32gui.SendMessage(combo_box, win32con.CB_SETCURSEL, 3, 0)
                     allow_btn = win32gui.FindWindowEx(window, 0, "Button", "Allow")
                     win32gui.SendMessage(allow_btn, BM_CLICK, 0, 0)
                     break
                else:
                    win32gui.SendMessage(combo_btn, BM_CLICK, 0, 0)
            else:
               time.sleep(1)

def run():
    base = olBase() # class carrying the outlook app object obtained by win32com.client.gencache.EnsureDispatch("Outlook.Application")
    mail = base.get_items()[0] # -> list of original mails objects (COM)
    
    threadpool = QThreadPool()
    threadpool.start(OutlookAccess_Watcher())

    try:
        body = mail.Body # warning appears and stops main thread here

    except:
        pass

    print(body)



 if __name__ == '__main__':
    run()

Thank you everybody for all your support. I managed to achieve my goal by performing a click (mouse event) on the button. Updated code below in case somebody struggles with this in the future.

class OutlookAccess_Watcher(QRunnable):

    def __init__(self):
        super().__init__()


    def run(self):

        while True:

            if win32gui.FindWindowEx(win32gui.FindWindow(None, "Microsoft Outlook"), 0, "Static", "DAL=on"):
                window = win32gui.FindWindow(None, "Microsoft Outlook")
                combo_btn = win32gui.FindWindowEx(window, 0, "Button", "&Allow access for")

                if win32gui.SendMessage(combo_btn, BM_GETCHECK, 0, 0):
                
                    combo_box = get_combobox_id(objects_window_finder(window))
                    win32gui.SendMessage(combo_box, win32con.CB_SETCURSEL, 3, 0)
                    allow_btn = win32gui.FindWindowEx(window, 0, "Button", "Allow")

                    windll.user32.BlockInput(True) # blocking user
                    mouse_X, mouse_Y = win32gui.GetCursorPos() # getting cursor original postion

                    allow_X, allow_Y,_,_ = win32gui.GetWindowRect(allow_btn) # getting posotion of Allow button

                    win32api.SetCursorPos((allow_X,allow_Y)) # moving cursor to Allow button location

                    # performing click
                    win32api.mouse_event(win32con.MOUSEEVENTF_LEFTDOWN,
                    allow_X,allow_Y,0,0)
                
                    win32api.mouse_event(win32con.MOUSEEVENTF_LEFTUP,
                    allow_X,allow_Y,0,0)


                    win32api.SetCursorPos((mouse_X, mouse_Y)) # restoring original position
                    windll.user32.BlockInput(False) # unblocking user
                    break

                else:
                    win32gui.SendMessage(combo_btn, BM_CLICK, 0, 0)
            else:
                time.sleep(1)

It seems you are faced with an Outlook security issue. It can also be a prompt issued by Outlook if you try to access any protected property or method. You get the security prompts/exceptions because Outlook is configured on the client computer in one of the following ways:

  • Uses the default Outlook security settings (that is, no Group Policy set up)
  • Uses security settings defined by Group Policy but does not have programmatic access policy applied
  • Uses security settings defined by Group Policy which is set to warn when the antivirus software is inactive or out of date

You can create a group policy to prevent security prompts from displaying if any up-to-date antivirus software is installed on the system or just turn these warning off (which is not really recommended).

Read more about that in the Security Behavior of the Outlook Object Model article.

Also you may consider using a low-level code on which Outlook is built and which doesn't give security issues - Extended MAPI. Consider using any third-party wrappers around that API such as Redemption . If that is not an option, take a look at the Outlook Security Manager component which allows suppressing Outlook security issues at runtime on the fly.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM