Absent Member.
Absent Member.

[archive] Reading mail

[Migrated content. Thread originally posted on 06 August 2007]


Does anyone have any experience of reading email from an exchange server?

We have a customer who would like us to write a program to read emails from a fixed email address, extract the attachment which would be an XML file and process it.
We're currently sending emails with out product in 2 different forms.
One which uses Outlook for one off emails, and another which uses SMTP through an exchange server for batches of emails like statements, invoices etc.

Any help/advice would be very much appreciated.


5 Replies
Absent Member.
Absent Member.

RE: [archive] Reading mail

Reading mail using Microsoft Outlook COM interface should be pretty straight forward.
What may be confusing is how to actually access it. The way it is organized in Outlook is that everything is in folders, so you have to enumerate the mail folder.
Consider this for a starter, and see where it takes you.

       PROGRAM-ID. FindContact.
       CONFIGURATION                SECTION.
           COPY    "MSOutlook.def".
       DATA        DIVISION.
       WORKING-STORAGE              SECTION.
       77  olApp                    HANDLE OF Application.
       77  olNs                     HANDLE OF Namespace.
       77  olItem                   HANDLE OF MailItem.
       77  olMail                   HANDLE OF MAPIFolder.
       77  olAttachlist            HANDLE OF Attachments.
       77  Filename PIC X(1024).
       77  Numbers PIC 9(3).
           CREATE  Application      OF Outlook
                   HANDLE           IN olApp.
           MODIFY  olApp            GetNameSpace("MAPI")
                   GIVING           olNs.
           MODIFY  olNs             Logon().
          MODIFY  olNs
                  GIVING           olMail.
          INITIALIZE               olItem
      *Look for contact by name
          MODIFY  olMail
                  Items::Find("[Subject] = 'XML'")
                  GIVING           olItem.
    IF      olItem           = 0
            DISPLAY          MESSAGE BOX "Not found" ICON 3
        INQUIRE          olItem Attachments IN olAttachList
        INQUIRE          olAttachlist Count IN Numbers
        PERFORM UNTIL Numbers = 0
          INQUIRE        olAttachList Item(Numbers)::FileName IN Filename
          MODIFY         olAttachList Item(Numbers)::SaveAsFile(FileName)
          SUBTRACT     1 FROM Numbers
           DESTROY olAttachlist.
           DESTROY olItem.
           DESTROY olMail.
           DESTROY olNs.
           DESTROY olApp.

I am sure you have a lot of questions to the above, but digest it a bit, see what you can figure out yourself and we can see if we can make the last mile together.

Sorry for the bad formatting.
Absent Member.
Absent Member.

RE: [archive] Reading mail

OK Gisle,

After getting over the initial shock your sample was most helpfull.

So far I can now

go through all unread mails in my inbox finding any that have an attachment
save the attachment

But I can't figure out the logon element.
I suppose I'll need to logon to outlook as a different user, but I'm completely lost with that section.
I've ran the Axdefgen utility which I downloaded from the forum.
It suggests the following sample code
* This program is generated by AxDefTool.
* This is an example for the syntax of ActiveX.
* For more details, read the specific ActiveX Manual.

copy "c:\copy\outlook.def".

working-storage section.

* Attention: The field definition may be different.

77 H-_NameSpace handle of @_NameSpace.

* @Profile: VARIANT
77 W-Var-Profile usage handle.
* @Password: VARIANT
77 W-Var-Password usage handle.
* @ShowDialog: VARIANT
77 W-Var-ShowDialog usage handle.
* @NewSession: VARIANT
77 W-Var-NewSession usage handle.

procedure division.

*Create the ActiveX
display @_NameSpace
line 2 col 2 lines 10 size 30
license-key " "
handle in H-_NameSpace

*Setup for variables
call "C$SETVARIANT" using "A", W-Var-Profile
call "C$SETVARIANT" using "A", W-Var-Password
call "C$SETVARIANT" using "A", W-Var-ShowDialog
call "C$SETVARIANT" using "A", W-Var-NewSession

*Code for Method
modify H-_NameSpace @Logon (
* by name Profile W-Var-Profile
* by name Password W-Var-Password
* by name ShowDialog W-Var-ShowDialog
* by name NewSession W-Var-NewSession

Is this trying to tell me that I have the profile/password etc as variables in the code and then call the C$SETVARIANT to get handles to pass to outlook?

Thanks for the initial help.

Absent Member.
Absent Member.

RE: [archive] Reading mail

Well done Shaun! According to office documentation, you should get along with this:

myNameSpace.[B]Logon[/B] "myProfile", "myPassword", True, True

In the above context I presume it would be like:

MODIFY olNs [B]Logon([/B]"Shaun", "ShaunPwd", 0, 1)

Some words about the parameters:

    • "Shaun" obviously is your username. Change it accordingly, this usually is the same as you use to logon to the computer.
    • "ShaunPwd" is the password thereof.
    • 0 (false) is whether to show the logon dialog or not. As I assume this will be a batch program, we will certainly not show any dialog. However, for testing purposes you might want to? (if not for anything else, then you can test your username and password if you get a problem with them as parameters, this way you eliminate that as being the source of any problem). To show the dialog, set this one to 1 (true).
    • 1 (true) is whether you want to start a new session or not. If you try to start Outlook several times by clicking the icon in the explorer, you probably know that you just get back to the existing one? By setting this to 1 (true), any exisiting sessions will be ignored and a new will be started. If you are fine with using any existing (if there is none, a new will be started), set this to 0 (false). It is no problem using an existing one.
    A word at the end; When you read documentation, don't get focused on the datatypes. ACUCOBOL-GT does all the conversion for you, just think of whether you should have a string or a numeric and create them as COBOL data items and use them directly.

    When you are all set and ready, if you had the time, it would be great if you could share a sample program with us!
Absent Member.
Absent Member.

RE: [archive] Reading mail


Haven't done anything with logging on as a different user as yet.
This is hopefully a cut and paste without my screen which is used to show Unread & Read inbox items.

I'm still learning so go easy.

One thing I'm unsure off though is destroying handles, so if someone could tell me if this is right or wrong then it would be appreciated.

Absent Member.
Absent Member.

RE: [archive] Reading mail

This is great stuff Shaun, no need to be humble, you have clearly dug up a lot of stuff on your own.

Yes, destroying handles are important. When you are done with a handle, you should destroy it, otherwise the reference count stays put and the COM object will not destroy when you eventually destroy the application.

This is important because you would otherwise (if you run the application multiple times) fill up your memory with copies of Word, Excel, Outlook whatever it is you run.

Note however, Outlook is a special case, as you typically reuse an existing instance of Outlook and Outlook itself connects to external services like Messenger, it will not go away when you destroy it, but as long as you reuse existing instance this is not a problem.

So, rule of tumb on handles; When done, DESTROY them, and in the order you created them.
The opinions expressed above are the personal opinions of the authors, not of Micro Focus. By using this site, you accept the Terms of Use and Rules of Participation. Certain versions of content ("Material") accessible here may contain branding from Hewlett-Packard Company (now HP Inc.) and Hewlett Packard Enterprise Company. As of September 1, 2017, the Material is now offered by Micro Focus, a separately owned and operated company. Any reference to the HP and Hewlett Packard Enterprise/HPE marks is historical in nature, and the HP and Hewlett Packard Enterprise/HPE marks are the property of their respective owners.