Python To Send Emails Via Outlook Express

Discussion in 'Python' started by ian@kirbyfooty.com, Dec 20, 2004.

  1. Guest

    Hi,
    I'm a newbie (oh no I can here you say.... another one...)

    How can I get Python to send emails using the default windows email
    client (eg outlook express)?

    I thought I could just do the following

    import win32com.client

    s = win32com.client.Dispatch('CDO.Message')
    s.From = ""
    s.To = ""
    s.Subject = "The subject"
    s.Send

    .... but nothing happens.

    What am I doing wrong? Does anyone have some sample code to share with
    me please?

    Thank you!

    Ian Cook

    (freeware author of Kirby Alarm And Task Scheduler www.kirbyfooty.com)
    , Dec 20, 2004
    #1
    1. Advertising

  2. Ganesan R Guest

    >>>>> "ian" == ian <> writes:

    > import win32com.client


    > s = win32com.client.Dispatch('CDO.Message')
    > s.From = ""
    > s.To = ""
    > s.Subject = "The subject"
    > s.Send


    > ... but nothing happens.


    > What am I doing wrong? Does anyone have some sample code to share with
    > me please?


    Try s.Send().

    Ganesan
    Ganesan R, Dec 20, 2004
    #2
    1. Advertising

  3. Guest

    Hi Ganesan
    I tried changing s.Send to s.Send(). It now comes up with an exception
    error..

    The details are below.

    Ian

    Traceback (most recent call last):
    File
    "C:\Python23\Lib\site-packages\pythonwin\pywin\framework\scriptutils.py",
    line 307, in RunScript
    debugger.run(codeObject, __main__.__dict__, start_stepping=0)
    File
    "C:\Python23\Lib\site-packages\pythonwin\pywin\debugger\__init__.py",
    line 60, in run
    _GetCurrentDebugger().run(cmd, globals,locals, start_stepping)
    File
    "C:\Python23\Lib\site-packages\pythonwin\pywin\debugger\debugger.py",
    line 595, in run
    exec cmd in globals, locals
    File "D:\MyPython\emailtest.py", line 7, in ?
    s.Send()
    File
    "C:\Python23\lib\site-packages\win32com\gen_py\CD000000-8B95-11D1-82DB-00C04FB1625Dx0x1x0.py",
    line 686, in Send
    return self._oleobj_.InvokeTypes(158, LCID, 1, (24, 0), (),)
    com_error: (-2147352567, 'Exception occurred.', (0, None, 'The server
    rejected one or more recipient addresses. The server response was: 554
    <>: Relay access denied\r\n', None, 0, -2147220977),
    None)
    , Dec 20, 2004
    #3
  4. <> wrote:

    > I tried changing s.Send to s.Send(). It now comes up with an exception
    > error..


    > com_error: (-2147352567, 'Exception occurred.', (0, None, 'The server
    > rejected one or more recipient addresses. The server response was: 554
    > <>: Relay access denied\r\n', None, 0, -2147220977),
    > None)


    sure looks like you managed to talk to the mail program, but your mail
    server thinks you're trying to send faked mails. your local mail admins
    can probably help you sort this one out.

    (googling for "Relay access denied" could also help)

    </F>
    Fredrik Lundh, Dec 20, 2004
    #4
  5. Guest

    Thanks Fredrik,
    That was my first impression too.

    But all I want to do is use Python to instruct Outlook Express to send
    an email.
    That way the user would not have to do any setting up etc of the mail
    server properties etc and Outlook Express will magage all the
    connection side of things.

    I have seen other python scripts that will talk to Excel etc but so far
    (despite a lot of searching) I cannot see how Python can talk to
    Outlook Express.

    I know I can do this in Clarion by accessing MapiSendEmail but because
    I'm new to Python I don't know how to do it in Python. I'm really
    impressed with the power of Python. It seems just about anything you
    can think of is there already so I know th eanswer is out there
    somewhere!

    Can this be done using Python? Does anyone have a sample script please?
    Pretty please?? <grin>

    Ian
    , Dec 20, 2004
    #5
  6. Keith Dart Guest

    wrote:
    > Hi Ganesan
    > I tried changing s.Send to s.Send(). It now comes up with an exception
    > error..
    >
    > The details are below.


    Looks like the COM part works, but sending mail has an error from the
    SMTP host. But, slightly off topic, FYI, Python can send email directly
    with the email and snmplib modules.


    --
    -- ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
    Keith Dart <>
    public key: ID: F3D288E4
    =====================================================================
    Keith Dart, Dec 20, 2004
    #6
  7. <> wrote:

    > But all I want to do is use Python to instruct Outlook Express to send
    > an email.


    and you succeeded -- the error message you saw came from the mail server, not
    outlook itself. your problem is that the server didn't like the mail you sent; checking
    the server configuration (or just the server logs) can help you figure out why.

    have you tried different From/To settings, btw?

    </F>
    Fredrik Lundh, Dec 20, 2004
    #7
  8. Max M Guest

    wrote:
    > Thanks Fredrik,
    > That was my first impression too.
    >
    > But all I want to do is use Python to instruct Outlook Express to send
    > an email.



    Which you did! From the look of the traceback.

    But your mailserver is configured in such a way that you cannot send
    mail from your machine using those email adresse, or you don't log on
    with the correct credentials.


    --

    hilsen/regards Max M, Denmark

    http://www.mxm.dk/
    IT's Mad Science
    Max M, Dec 20, 2004
    #8
  9. Guest

    Hi Keith
    Thanks for your reply.

    I am aware of the smtplib module and it works very well! (refer script
    below)

    The problem is that I have a developed a freeware application called
    Kirby Alarm And Task Scheduler (see www.kirbyfooty.com).
    The program can pop up a note, run a program, play a sound, or send an
    email at whatever intervals the user wants..
    When it comes to sending emails the user has the option of sending them
    via smtp, or via there email client (eg outlook express). I prefer the
    send method as this makes setting up the email parameters a lot easier
    for the user.
    As the program is used by over 16,000 people around the world I don't
    want to complicate things by asking them to enter the mail server
    properties.

    Because Python is so powerful I want to develop a suite of applications
    in Python that Kirby Alarm can run.
    Things like FTP, Backup, Speech etc would be excellent


    There has to be a way for Python to send emails via Outlook Express....

    Kind regards
    Ian

    PS Here is the working script for sending emails via SMTP..

    -----------------------------------------------------------------------------------------------------------------

    # Import smtplib for the actual sending function
    import os
    import sys
    import smtplib
    import mimetypes
    from email.Encoders import encode_base64
    from email.MIMEAudio import MIMEAudio
    from email.MIMEBase import MIMEBase
    from email.MIMEImage import MIMEImage
    from email.MIMEMultipart import MIMEMultipart
    from email.MIMEText import MIMEText


    FROM = ''
    TO = ';'
    SUBJECT = 'This is the subject'
    MSGBODY = 'This the body of the message '
    ATTACHSTR =
    'c:/ian.txt;c:/c55/footytip/2003finalresults.txt;c:/snap.jpg'
    MAILSERVER = 'insert mail server'
    port = 25
    username = 'insert username'
    password = 'insert password'

    # trim the strings of any leading or trailing spaces
    FROM = FROM.strip()
    TO = TO.strip()
    SUBJECT = SUBJECT.strip()
    MSGBODY = MSGBODY.strip()
    ATTACHSTR = ATTACHSTR.strip()
    MAILSERVER = MAILSERVER.strip()
    username = username.strip()
    password = password.strip()

    # function to attach files
    def getAttachment(path, filename):
    ctype, encoding = mimetypes.guess_type(path)
    if ctype is None or encoding is not None:
    ctype = 'application/octet-stream'
    maintype, subtype = ctype.split('/', 1)
    fp = open(path, 'rb')
    if maintype == 'text':
    attach = MIMEText(fp.read(),_subtype=subtype)
    elif maintype == 'message':
    attach = email.message_from_file(fp)
    elif maintype == 'image':
    attach = MIMEImage(fp.read(),_subtype=subtype)
    elif maintype == 'audio':
    attach = MIMEAudio(fp.read(),_subtype=subtype)
    else:
    print maintype, subtype
    attach = MIMEBase(maintype, subtype)
    attach.set_payload(fp.read())
    encode_base64(attach)
    fp.close
    attach.add_header('Content-Disposition', 'attachment',
    filename=filename)
    return attach

    #Connect to server
    print 'Connecting to mail server ', MAILSERVER
    try:
    s = smtplib.SMTP(MAILSERVER,port)
    #s.set_debuglevel(1)
    except:
    print 'ERROR: Unable to connect to mail server', MAILSERVER
    sys.exit(1)

    #login to server
    if password <> '':
    print 'Logging into mail erver'
    try:
    s.login(username,password)
    except:
    print 'ERROR: Unable to login to mail server', MAILSERVER
    print 'Please recheck your password'
    sys.exit(1)

    # get list of email addresses to send to
    ToList = TO.split(';')
    print 'Sending email to ', ToList

    # set up email parameters
    msg = MIMEMultipart()
    msg['From'] = FROM
    msg['To'] = TO
    msg['Subject'] = SUBJECT
    msg.attach(MIMEText(MSGBODY))


    # get list of file attachments
    AttachList = ATTACHSTR.split(';')
    for file in AttachList:
    try:
    attach = getAttachment(file,os.path.basename(file))
    msg.attach(attach)
    except:
    print 'Error attaching ',file
    pass


    # send email
    s.sendmail(FROM, ToList, msg.as_string())
    s.quit()
    s.close()

    print 'done'
    -----------------------------------------------------------------------------------------
    , Dec 20, 2004
    #9
  10. Guest

    Hi Fredrik,
    Thank you for the suggestion.

    I tried different from/to settings and guess what? The mail came thru.

    The script is now..
    import win32com.client

    s = win32com.client.Dispatch('CDO.Message')
    s.From = "" (was
    "")
    s.To = "" (was
    "")
    s.Subject = "The subject"
    s.Send()


    My problem is thought, the message is still not being sent via Outlook
    Express.
    What am I missing?
    Thanks again for your help so far!!

    Kind regards
    Ian
    , Dec 20, 2004
    #10
  11. Ganesan R Guest

    >>>>> "ian" == ian <> writes:

    > But all I want to do is use Python to instruct Outlook Express to send an
    > email. That way the user would not have to do any setting up etc of the
    > mail server properties etc and Outlook Express will magage all the
    > connection side of things.


    Are you sure CDO.Message uses OE configuration to send mail? The examples of
    CDO.Message usage that I see on the net appear to explicitly load some
    configuration. Try this for example,

    cdoSourceOutlookExpress = 2
    s.Configuration.Load(cdoSourceOutlookExpress)

    before s.Send(). It looks like by default CDO.Message() will use the local
    IIS "Virtual SMTP Server" which refuses to relay by default.

    Ganesan
    Ganesan R, Dec 20, 2004
    #11
  12. Guest

    Hi Ganesan

    Wow, I'm REALLY impressed with the high level of support in this forum.
    (Another great reason to continue learning Python <grin>

    I tried what you suggested.
    After trying a different from/to address the message is sent. But it is
    NOT sent via Outlook Express.

    I would appreciate any other suggestions.

    Thanks in advance


    The script is now..

    import win32com.client

    s = win32com.client.Dispatch('CDO.Message')
    s.From = ""
    s.To = ""
    s.Subject = "The subject"
    cdoSourceOutlookExpress = 2
    s.Configuration.Load(cdoSourceOutlookExpress)
    s.Send()
    , Dec 20, 2004
    #12
  13. Ganesan R Guest

    >>>>> "ian" == ian <> writes:

    > Hi Ganesan
    > Wow, I'm REALLY impressed with the high level of support in this forum.
    > (Another great reason to continue learning Python <grin>


    Well, I am a Linux guy myself. I experimented with win32com a bit a couple
    of weeks back, so I am trying my ideas on you ;-).

    > I tried what you suggested. After trying a different from/to address the
    > message is sent. But it is NOT sent via Outlook Express.


    s.Configuration.Load(cdoSourceOutlookExpress) only loads the OutlookExpress
    configuration. It does not use Outlook Express to send. I am surprised why
    your original from and to address settings didn't work after calling the
    Load() method.

    I did some more reading. Unlike Outlook which you can automate by getting
    the application object using CreateObject("Outlook.Application") and
    automate it, Outlook Express is not a COM server.

    Ganesan
    Ganesan R, Dec 20, 2004
    #13
  14. Steve Holden Guest

    wrote:

    > Hi Fredrik,
    > Thank you for the suggestion.
    >
    > I tried different from/to settings and guess what? The mail came thru.
    >
    > The script is now..
    > import win32com.client
    >
    > s = win32com.client.Dispatch('CDO.Message')
    > s.From = "" (was
    > "")
    > s.To = "" (was
    > "")
    > s.Subject = "The subject"
    > s.Send()
    >
    >
    > My problem is thought, the message is still not being sent via Outlook
    > Express.
    > What am I missing?
    > Thanks again for your help so far!!
    >
    > Kind regards
    > Ian
    >

    Unfortunately Outlook Express isn't programmable in the same way as
    Outlook. I used to use it because this property gave it a certain degree
    of immunity from macro viruses (back in the days when Outlook came
    configured to open any Office document it came across).

    About the next you can do is to add your email address as a Cc and then
    file the messages when you receive them, I suspect.

    Why the insistence on using Outlook Express, is you don;t mind me asking?

    regards
    Steve
    (who almost always uses smtplib)
    --
    Steve Holden http://www.holdenweb.com/
    Python Web Programming http://pydish.holdenweb.com/
    Holden Web LLC +1 703 861 4237 +1 800 494 3119
    Steve Holden, Dec 20, 2004
    #14
  15. Guest

    Hi Steve,
    > Why the insistence on using Outlook Express, is you don;t mind me

    asking?
    Good question.
    The problem is that I have a developed a freeware application called
    Kirby Alarm And Task Scheduler (see www.kirbyfooty.com).
    The program can pop up a note, run a program, play a sound, or send an
    email at whatever intervals the user wants..

    When it comes to sending emails the user has the option of sending them
    via smtp, or via there email client (eg outlook express).
    I prefer the send method as this makes setting up the email parameters
    a lot easier for the user.
    As the program is used by over 16,000 people around the world I don't
    want to complicate things by asking them to enter the mail server
    properties.
    I have written Kirby Alarm in Clarion. It can currently send the email
    via outlook express by calling MapiSendMail.

    I wanted to do the same thing in Python so I can build up a suite of
    useful utilities and therefore try an keep the program size relatively
    small.

    Ian
    , Dec 20, 2004
    #15
  16. Max M Guest

    wrote:
    > Hi Steve,


    > When it comes to sending emails the user has the option of sending them
    > via smtp, or via there email client (eg outlook express).
    > I prefer the send method as this makes setting up the email parameters
    > a lot easier for the user.



    If Outlook Express cannot be automated through COM, you are in abind.
    Maybe you should shange your tactics.

    What about just fetching the settings from the client?

    That way the send function will be the same, and you can control it. But
    the server settings could be fetched from the different clients.

    It is probably much simpler to find those than it is to use them as the
    sender.

    Most email clients can fetch the settings from other mail clients, so
    it's been done before.

    --

    hilsen/regards Max M, Denmark

    http://www.mxm.dk/
    IT's Mad Science
    Max M, Dec 20, 2004
    #16
  17. Guest

    Hi Max,
    Thanks for the suggestion. I'm always open to new ideas.

    Can you please tell me how to retrieve the default account settings
    from Outlook Express?

    Ian
    , Dec 20, 2004
    #17
  18. Ganesan R Guest

    >>>>> "ian" == ian <> writes:

    > Hi Max,
    > Thanks for the suggestion. I'm always open to new ideas.


    > Can you please tell me how to retrieve the default account settings
    > from Outlook Express?


    s.Configuration.Load(2) is supposed to do exactly that. I have no clue
    why that didn't work for you :-(.

    Ganesan
    Ganesan R, Dec 21, 2004
    #18
  19. Guest

    Hi Ganesan,
    I'm on the verge of giving up <sigh>
    I don't suppose you could write a small script to send the email for me
    via the default windows email client. I will then try running your
    script and my end to see if it works ok.
    I may have missed something and would really appreciate your help.
    Thanks in advance
    Ian
    , Dec 21, 2004
    #19
  20. Ganesan R Guest

    >>>>> "ian" == ian <> writes:

    > Hi Ganesan,
    > I'm on the verge of giving up <sigh>
    > I don't suppose you could write a small script to send the email for me
    > via the default windows email client.


    I can see no easy way to do this. Though you can access the default mail
    client using a registry key (I don't have enough win32 programming
    experience to do this), there is no guarantee that the email client is a COM
    server. Even Outlook Express is not a COM server. What if the user has
    configured Eudora or something like that?

    The best we can do is use Outlook Express settings and send the mail.

    > I will then try running your script and my end to see if it works ok. I
    > may have missed something and would really appreciate your help.


    The final script that you pasted:

    =====
    import win32com.client

    s = win32com.client.Dispatch('CDO.Message')
    s.From = ""
    s.To = ""
    s.Subject = "The subject"
    cdoSourceOutlookExpress = 2
    s.Configuration.Load(cdoSourceOutlookExpress)
    s.Send()
    =====

    works fine for me. According to CDO.Message documentation, if IIS is
    installed that configuration will be used by default, followed by OE
    configuration. I don't have IIS installed, so the script picked up the OE
    configuration automatically for me. Here's a variation of the above
    script.

    ======
    import win32com.client

    s = win32com.client.Dispatch('CDO.Message')
    c = win32com.client.Dispatch('CDO.Configuration')
    cdoSourceOutlookExpress = 2
    c.Load(cdoSourceOutlookExpress)
    s.Configuration = c
    s.From = ""
    s.To = ""
    s.Subject = "The subject"

    s.Send()
    ======

    If that doesn't help, I give up :-(.

    Ganesan
    Ganesan R, Dec 21, 2004
    #20
    1. Advertising

Want to reply to this thread or ask your own question?

It takes just 2 minutes to sign up (and it's free!). Just click the sign up button to choose a username and then you can ask your own questions on the forum.
Similar Threads
  1. Curt_C [MVP]
    Replies:
    0
    Views:
    597
    Curt_C [MVP]
    Apr 29, 2004
  2. Replies:
    2
    Views:
    763
    Toby Inkster
    Oct 13, 2005
  3. Lenard Lindstrom
    Replies:
    3
    Views:
    535
  4. Andrew Thompson
    Replies:
    0
    Views:
    488
    Andrew Thompson
    Dec 7, 2006
  5. Jack
    Replies:
    5
    Views:
    428
Loading...

Share This Page