Send email with CDO 2000

It's simple and convenient to send unattended email with CDO 2000 as long as there's a SMTP server available.

Note 1 Uses CDO 2000 class for sending emails

Note 2 Any email address can include "Display Name" in format below. How it's displayed depends on an email client.

"Display Name"<>

This is sample code. Add error handling and adjust to your requirements as necessary.

* Replace addresses with real ones before running the code
loMail = NEWOBJECT("Cdo2000", "Cdo2000.fxp")
WITH loMail
	.cServer = ""
	* Uncomment following lines and fill your credentials 
	*	if your SMTP server requires basic authentication
	*.nAuthenticate = 1 	&& cdoBasic
	*.cUserName = "myusername"
	*.cPassword = "mypassword"
	.cFrom = ""
	.cTo = ","
	.cSubject = "CDO 2000 email"
	* Uncomment next lines to send HTML body
	*.cHtmlBody = "<html><body><b>This is an HTML body<br>" + ;
	*		"It'll be displayed by most email clients</b></body></html>" 	
	.cTextBody = "This is a text body." + CHR(13) + CHR(10) + ;
			"It'll be displayed if HTML body is not present or by text only email clients"
	* Attachments are optional
	* .cAttachment = "myreport.pdf, myspreadsheet.xls"
IF loMail.Send() > 0
	FOR i=1 TO loMail.GetErrorCount()
		? i, loMail.Geterror(i)
	* Clear errors
	? "Email sent."


Hi, Sergey,

Thanks so much for the example CDO200 stuff you have posted.

I have one problem. Using the cHtmlBodyURL property, I can successfully place the contents of an HTML file I created in Visual Foxpro code into the body of the sent message. However, this only works the first time through (in a Visual Fox session). If I try to run it again, I get "file access denied" when trying to re-create my HTML file by using SET ALTERNATE TO. It seems CDO2000 is keeping a lock on the file. If I quit Fox, and come back in and run the program, it works fine.

I have tried all sorts of RELEASE and CLOSE commands in the program, but nothing works.

Any ideas on what I'm missing?




Did you try to release CDO object?


In another gem you wrote about using Gmail and CDO2000, I found TWO solutions to the problem.

In my program, I set "savefile" to a file name, then used SET ALTERNATE to write the HTML code to it (and closing it properly!). Then, either one of the following works, AND allows the creation of the file and SEND to be performed consecutive times without the dreaded "File Access denied".

1. .cHtmlBody = FILETOSTR(savefile) && this works! No mysterious file lock on savefile afterwards

2. .cHtmlBodyUrl = "file://" + FULLPATH(savefile) && this also works, no mysterious file lock on savefile afterwards

For some reason, using just the file name (savefile) in the cHTMLBodyURL causes the weird lock on savefile afterwards.

Thanks for all your help, Sergey.

Hi Sergey,

Thanks for your code. It works well for English contents but Chinese characters will become garbage. Is there any way to fix the problem?

Ben Tam

What changes do I need if they require additional authentication and it is different than their normal login and password?



Hi Don,

The CDO 2000 supports only following three types of authentication:

  • cdoAnonymous, value 0. Do not authenticate.
  • cdoBasic, value 1. Use basic clear-text authentication. When using this option you have to provide the user name and password through the sendusername and sendpassword fields.
  • cdoNTLM, value 2. The current process security context is used to authenticate with the service.

Hi Sergey

Is it possible to create a number of email messages to different people with different attachments etc. and then just call the Send() method once to send all the messages?


Hi Simon,

You'll have to call Send() once per each email. There's no batch mode.

Love the code. I know this sounds petty and non-important, but I have seen winsock ole objects which do this easily and imagine it may be easy to impliment into the cdo stuff you have here. Is there a way to show an alternative name for the to and from section instead of the email address? (i.e. from IT Department instead of

Will this code send email even if one of the To email address is bad?

Does it class support SSL or STARTTLS

CDO 2000 class supports SSL - lUseSSL property.

Hello Sergy,
I can send with gmail, comcast, and yahoo, but not with SmarterMail.
I've tried 465 & 25 and other combinations.
Receive error "1429 # send # 183 # 0x00000213 The transport failed to connect to the server"
I'm certain my credentials are correct.
Any advice on what else to try?

Hi Dave,

I have no knowledge of SmarterMail. What are the instructions to connect SMTP clients to it?


I am your fan.
This is a brilliant procedure.

Keep up the good work and all the best.


When I use this (code lightly modified), the received attachment filenames are in upper case. The filenames that I specified were in mixed case. How do I preserve the case?


Most likely, FULLPATH() in the code that processes attachments is a culprit.

I have the code working. How do I submit it to you?

What is the copyright status of your code? I understand free-to-use, but do you claim copyright and if so, what?

Hi Gene,

You can use code any way you see fit. I would appreciate if you mention where it originates but it's not a requirement.

1) Yes, fullpath() is the culprit. In a test program, I got the path added and still kept the case of the filename with:
The case of the directory names is still uppered, but that does not matter as those are not sent. Feel free to use this.

2) In your test with the fullpath(), I think that you are assuming that there is only one attachment. For my use, it will be common that this is incorrect.

3) You have a typo "attacment".

I may rework your class a bit. If I do, I will send you a copy.

Hi Gene,

Thank you for taking time to let me know.

1) Yes it will preserve the case of file name

2) The code process each attachment separately in a loop

3) Corrected


I want to write emails from my VFP app to Gmail's Draft box/folder instead of sending the email immediately. I want my users to be able edit their out-going emails in Gmail before sending. Is this possible with CDO2000? If it is, how is it done?

Thank you.

I have used your code but receiving error
1 Error : : 1429 # send # 185 # 0x00000220 The "SendUsing" configuration value is invalid.

I've been using this cdo2000 code ( with gmail) for years and suddenly last week it stopped working. tried restarting everything with no luck. also tried using yahoo with no luck. with gmail I get error code 1429 and 187 - with yahoo i get error 1429 and 191.
I found article stating error 1429 means windows registry has "irregular entries" - not sure what/how this happened - but how do i fix this?

thanks for any help you can provide!

Add new comment

Filtered HTML

  • Allowed HTML tags: <a> <em> <strong> <cite> <code> <ul> <ol> <li> <dl> <dt> <dd>
  • Lines and paragraphs break automatically.
  • Web page addresses and e-mail addresses turn into links automatically.

Plain text

  • No HTML tags allowed.
  • Web page addresses and e-mail addresses turn into links automatically.
  • Lines and paragraphs break automatically.
By submitting this form, you accept the Mollom privacy policy.