Why is Outlook application.Session null? - vsto

application.Session is null but should have an object, and does for other users on the same machine.
When trying to access Globals.ThisAddIn.outlookApplication.Session I get a NullReferenceException on application.Session.
Redemption.RDOSession session = Redemption.RedemptionLoader.new_RDOSession();
session.MAPIOBJECT = Globals.ThisAddIn.outlookApplication.Session.MAPIOBJECT;
The same add-in works for other users on the same machine. This callback is hit from a click event on a ribbon button in Outlook. The user has a logged in session with Exchange and can interact with Exchange server normally.

This issue ended up being a corrupt user.settings file.

Related

Outlook Redemption - add-in Control throws IAccessible.accDoDefaultAction error only when user locked

We have an add-in that is intended to be used when a user is remotely logged into a server. They open outlook, start a process with the add-in, then leave their session logged in but disconnect their session. The server is setup to never go to sleep and to leave the user logged in the entire time. As expected we can reconnect and outlook is still open and running just fine. Or at least that used to be the case...
We are using Redemption in the add-in to trigger a button on a 3rd party ribbon control as part of the process. This was working fine for months. It still works fine when using the app. However if you are disconnected from the RDP session or if you simply lock the screen with CTRL-ALT-Delete, it throws the following error when it tries to execute the control.
System.Runtime.InteropServices.COMException (0x80004005): Error in
IAccessible.accDoDefaultAction: MAPI_E_CALL_FAILED at
Redemption.ISafeRibbonControl.Execute()
Here is the code it is running through at that time:
Redemption.SafeExplorer sExplorer = new Redemption.SafeExplorer();
sExplorer.Item = Application.ActiveExplorer();
Redemption.SafeRibbon Ribbon = sExplorer.Ribbon;
Ribbon.ActiveTab = "RIBBONTABNAMEHERE";
ISafeRibbonControls Controls = Ribbon.Controls;
Redemption.SafeRibbonControl Control = Controls.Item("CONTROLNAMEHERE");
Control.Execute(); //<--HERE IS WHERE IT DIES
Marshal.ReleaseComObject(sExplorer.Item);
Marshal.ReleaseComObject(sExplorer);
Marshal.ReleaseComObject(Controls);
Marshal.ReleaseComObject(Control);
Marshal.ReleaseComObject(Ribbon);
I've tried a million things but I can't figure out why executing a control without the user connected even if they are logged in still no longer works. This worked for a long time!

Automatically Closing Outlook Windows via Script/Macro

I'm hoping someone on here can point me in the right direction with some expertise. I have a situation with a client's outlook where we need to close any open draft windows after a new message/draft is opened. Ideally after the 4th new window has opened.
Any "new message" window that opens after this we need the script to close 1st window that opened. Either killing the process, or something similar.
Recently have been looking into Outlook macros, but am unsure if they will help in this instance. (Maybe they are?). Being more familiar with Powershell, figured we could start there.
Looking to get help writing a powershell script, macro, etc to do this on the backend.
The Outlook object model provides all the required events, methods and properties for that. So, VBA macros is the right choice if you don't need to distribute the solution on multiple machines. Otherwise, you need to consider developing a COM add-in instead (for example, a VSTO based one should work for you). See Walkthrough: Create your first VSTO Add-in for Outlook for more information.
You can handle the NewInspector event which is fired whenever a new inspector window is opened, either as a result of user action or through program code. The event occurs after the new Inspector object is created but before the inspector window appears.
You can also check the number of opened inspector windows in Outlook by using the Inspectors.Count property which returns a long indicating the count of objects in the specified collection.
Finally, the Inspector.Close method closes the Inspector and optionally saves changes to the displayed Outlook item. For example, a VBA sample which closes the active inspector instance:
Sub CloseItem()
Dim myinspector As Outlook.Inspector
Dim myItem As Outlook.MailItem
Set myinspector = Application.ActiveInspector
Set myItem = myinspector.CurrentItem
myItem.Close olSave
End Sub

The RPC server is unavailable (outlook in vb.net)

I am developing little application. It's purpose is on button click generate some email and open outlook "new email" window with this template. I am using Outlook interop 14. On application start I create New Outlook.Application() instance. This creates outlook.exe process.
My method for generating and open email:
Private Sub GenerateEmail(...)
...
'this line throws RPC exception when no outlook.exe process exists
Dim OutlookEmail As Outlook.MailItem = CType(OutlApp.CreateItem(Outlook.OlItemType.olMailItem), Outlook.MailItem)
...
OutlookEmail.Display()
...
End Sub
When I run an application, outlook.exe process starts. I click generate email, outlook opens window BUT when I close this "new email" window it also terminates outlook.exe process. And this is problem becasue second time I want to generate an email I am getting an error "The RPC server is unavailable". The question is how to close the window but not terminate outlook process. Btw I am getting the same error also when I am try to second time create a new instance of Outlook.Application (after terminating a previous one).
Outlook quits (which can take some time) when its last visible window closes. To prevent that from happening, retrieve a MAPIFolder object (e.g. using Application.Session.GetDefaultFolderFolder(olFolderInbox)) and store the Explorer object returned by calling MAPIFolder.GetExplorer() in a global/class variable. The Explorer object does not have to be made visible.

Mail listener not seeing new mail when the terminal is locked

I have Outlook VBA code that reads all incoming mails.
This code uses the MailItem to go through each mail looking at sender, to, subject and for attachments.
The heart of the code uses the urn:schemas feature that does a sql query on the inbox.
Thus if a new mail arrives the process that fires looks at the whole inbox every time and not just that mail. (The inbox is kept tidy and items are moved when processed.)
The heart of the query looks like this:
Dim Filter as String
Filter = "urn:schemas:mailheader:subject like '%That report - %'"
Dim iMailMatch As Object
Set iMailMatch = Inbox.items.Find(Filter)
The problem is that (occasionally) when the machine is locked (not logged out), the macro will fire on a new mail event, but it won't find anything even though there are mails which match.
When I unlock the terminal and a new mail arrives - the process fires and it picks up/processes mails successfully that it previously didn't see.
The problem is only apparent when the terminal is locked. Thus I can only think that it has to do with kind of trust privileges.
There are times is does fire successfully when the terminal is locked, but it appears to be only when a mail arrives soon after the terminal is locked.
Do not search. NewMailEx event passes the entry id of the new item to your event handler - open the item using Namespace.GetItemFromID, then read the MailItem.Subject property.

In vb.net when calling a method from an instance of Outlook.Application, a pop up halts code execution

We have a vb.net windows application that creates an instance of Outlook.Application to open an email .MSG file, and save it as a .HTML by calling the Outlook.Application SaveAs() method.
However, sometimes the call to .SaveAs() causes a popup to appear, for example when saving a .MSG that is digitally signed, there is a confirmation popup.
This popup causes the code execution to halt until the user interacts and clicks YES or NO on the pop up. Since our application runs on a server and requires no user interaction this causes the application to halt periodically until a technician logs into the server and clicks 'yes' on the popup.
Is there a way to avoid this pop up, or have 'YES' automatically get selected?
I've tried investigating the documentation for Outlook.Application but of course the documentation is very lacking on MSDN.
Here is some example vb.net code:
outlookapp = CreateObject("Outlook.Application")
Dim olItem As Object = outlookapp.CreateItemFromTemplate("C:\msg\message.msg")
olItem.SaveAs("C:\html\convertedmessage.html", 5)
If message.msg is digitally signed, when calling SaveAs() to save it as an HTML file, you get a pop up that the MSG is digitally signed, this halts the code until you click yes or no.
Note: Outlook objects do not support the DisplayAlerts flag of Word objects.
Firstly, Outlook is not designed to be used in a service or a server side application with no user present.
In your particular case, you can do the following:
1 Use Extended MAPI (C++ or Delphi only) to open the MSG file (OpenIMsgOnIStg etc.), then construct the HTML file explicitly in your code.
2 Parse the MSG file (its format is documented) or use one of several commercial components (such as the one from Aspose) to read the MSG files.
3 Use Redemption (I am its author) and its RDOSession.GetMessageFromMsgFile / RDOMail.SaveAs(..., olHTML) methods to open the MSG file and perform the conversion.
dim Session As RDOSession = CreateObject("Redemption.RDOSession")
dim Msg As RDOMail = Session.GetMessageFromMsgFile("C:\msg\message.msg")
Msg.SaveAs("C:\html\convertedmessage.html", 5)