Exchange客户端之翼——WebDAV vs CDO(上)

这阵子一直在研究Exchange2003 Server以及相关客户端应用,我们在客户端不通过outlook而是以编程方式发送邮件。目前针对Exchange在客户端以编程方式发送邮件的方式主要有两种,一是WebDAV方式,二是CDO方式。由于自身的弱势所限,通常不单独使用WebDAV的方式而是将之与CDO结合使用,即所谓的混合方式。这两种方式虽然没有outlook那样成熟与强大,但给应用系统在客户端的安装部署提供了极大的灵活性和可伸缩性,无疑受到许多programmer的关注,我想将两种编程方式与outlook并成为Exchange server在客户端的双翼一点都不为过。(Exchange2003 Server被微软誉为完整、长期的企业消息和协作平台,其相关的详细信息可以浏览http://www.microsoft.com/china/exchange/default.mspx)。           本文将先对WebDAV的概念和原理进行概述,进而说明在客户端如何结合使用WebDAV和CDO以编程方式发送邮件,在下一篇文章中将单独介绍使用CDO编程实现邮件的发送。           究竟什么是WebDAV呢,也许你会到网上去搜索它,然而如果你已经安装了Exchange SDK就可以直接获得相关的说明。下面就将SDK中对WebDAV的介绍直接贴上来,因为比较浅显易懂,这里就不再进行翻译了,且以免有的高手骂我的英语太滥^_^。           WebDAV Items in the Exchange store can be accessed remotely by using the WebDAV protocol, defined in RFC 2518. This protocol extends the HTTP 1.1 protocol, defined by RFC 2616, to provide additional methods and capabilities. It provides a means to access both the contents of an item and an extensible set of associated properties. Some of the methods defined by the protocol are the MOVE Method, the COPY Method, the DELETE Method, and the MKCOL Method. The encoding format used to transfer item properties across the network is XML, defined in the World Wide Web Consortium (W3C) Recommendation REC-xml-20001006. When a URL in the Exchange store is entered in a Web browser, an XML formatted WebDAV protocol request is created and sent to the Microsoft® Exchange Server computer. When the server receives the request, it verifies the credentials of the client and automatically parses the XML for the requested data. The server then builds an XML WebDAV protocol response containing the appropriate properties and their values and sends the response back to the client. If the Web browser is able to parse XML, an XSL style sheet can be applied to the XML response and the data will be displayed in the browser. If the Web browser cannot parse XML, the information is displayed in HTML. See Authentication and Security Using WebDAV for more information. The following illustration shows how a client browser interacts with the Exchange store using WebDAV.                                          Microsoft Internet Explorer 5 and later provide the Microsoft XML (MSXML) Component Object Model (COM) component, a powerful XML parser and set of related tools. The XMLHTTPRequest COM class integrates with MSXML COM objects to simplify the management of client-side HTTP protocol requests and responses that contain XML bodies. The transformational capabilities of the MSXML component can easily cast the response XML data into HTML, which can then be displayed by the browser.            .NET中要使用WebDAV进行编程,需要添加引用Microsoft XML, 3.0,至于原因麻如果你认真阅读了上面的内容就不需要我多解释了(更直接的,看图上两个箭头的标注)。采用这种方式发送邮件不需要客户端安装outlook,也不需要引用其他与exchange或outlook有关的组件,部署比较简单方便,但是也存在两个明显的缺点:其一就是WebDAV方式本身并不支持附件发送,网上有人提出将附件以base64编码后嵌在mail body中发送,试了一下比较麻烦;其二就是不支持邮件的密送,即bcc的收件人是收不到邮件的。     查阅了一些资料,第二个缺点没有找出症结所在,只能说比较“妖”;第一个缺点倒是有相应的介绍,如下:      There is no mechanism to add an attachment in WebDAV.  You will need to create/recreate the item using a WebDAV PUT.  The text you would be putting would be the mime of the item, which also contains the attachment. It’s useful here to use CDOSYS to create a message and add an attachment – then extract the MIME from the message and use it for the WEBDAV PUT.  You will need a header of "translate" set to "f".         If the message already exists, you will need to, you must do a GET on the message stream, which will give you the message + attachments in a string.  Next, modify the stream to include a new attachment.  After this, the string can be used in a PUT statement to write the attachment.         我们知道,CDO方式发送附件非常方便,一个AddAttachment()方法就解决问题,并且支持多附件的发送。将CDO中所含的信息通过WebDAV发送就可以有效地解决附件的问题。其工作机制如下:         To send an email with WebDAV, you will you will need to create/recreate the item with a WEBDAV PUT using the MIME of the message.  It gets tricky when working with attachments.  To get around the complexity of sending an email with an attachment, you may want to look at using CDOSYS to build the message to send, then extract the MIME stream (MIME of the message in a string) of the resulting message.   For sending the message, you would use a PUT statement to write the stream to a file in the Drafts folder of the sending person’s mail box.  If you need to set specific properties not set by the MIME, you should do a PROPPATCH against the message in the Drafts folder.  Next, the code should use a WebDAV MOVE in order to place the message into the mailbox’s submission URL.  The Submission URL is a special url used for sending messages.  “/##DavMailSubmissionURI##" off of the root of the mailbox is the Submission URL.           最后我们给出一个WebDAV与CDO结合发送邮件的C#示例,希望能够给碰到相同问题的朋友一点帮助,并自这里仅给出关键的部分,因为俺可是签了保密协议的哈。         //添加引用Microsoft CDO for Windows 2000 Library ,Microsoft XML,3.0          //This will create a CDOSYS message,attach a file and return the Mime stream for use with   webdav          Private String BuildMessageAndGenerateMIMEStream()         {                CDO.IBodyPart oBodyPart;                CDO.Message oMessage = new CDO.Message();                CDO.Configuration oConfig = new CDO.Configuration;                ADODB.Fields oFields = oConfig.Fields;                string sFile,strMIMEStream;                ADODB.Stream oMIMEStream;                oMessage.Configuration = oConfig;                oMessage.To = "receiver@yourdomain.microsoft.com";                oMessage.From = "Administrator@yourdomain.microsoft.com";                oMessage.Subject = "my test";                oMessage.TextBody = "This is my test!";                oMessage.Update();                sFile = "C:/yourfilename,txt";                oBodyPart = oMessage.AddAttachment(sFile,userName,passWord);                oMIMEStream = oMessage.GetStream();                strMIMEStream = oMIMEStream.ReadText();                oMIMEStream = null;                oBodyPart = null;                oMessage = null;                return strMIMEStream;         }        //Used to put(wirte)an item to a file in a folder.           Private Bool DoWebdavPut(string mailFolder,string mailText,string userName,string passWord)          {                     MSXML2.XMLHTTP30 oXMLHttp = new MSXML2.XMLHTTP30();                      bool flag = false;                       int iStatus;                       string sStatus = String.Empty;                       string sResponse = String.Empty;                       oXMLHttp.Open("PUT",mailFolder,false,userName,passWord);                       oXMLHttp.setRequestHeader("translate","f");                       oXMLHttp.Send(mailText);//send the stream across                       iStatus = oXMLHttp.Status;                       sStatus = oXMLHttp.StatusText;                       if(iStatus >=200 && iStatus < 300)                       {                                Console.WriteLine("PUT:Success! Results =" + iStatus.ToString());                                 flag = true;                       }                      else if (iStatus == 401)                      {                              Console.WriteLine("PUT: You don't have permission to do the job!");                      }                      else                      {                               Console.WriteLine("PUT:Request Failed. Results = " + iStatus.ToString() + ":" +sStatus);                      }                      oXMLHttp = null;                      return flag;          }           //Used to move an item from one folder to another in the same store.          Private bool DoWebdavCopyMove(String sSourceURL,String sDestinationURL,bool isCopy,String userName,String passWord);         {                bool flag = false;                MSXML2.XMLHTTP30 oXMLHTTP = new MSXML2.XMLHTTP30 ();                String sVerb = String.Empty;                if(isCopy)                {                          sVerb = "COPY";                }                else                {                        sVerb = "MOVE";                }               oXMLHttp.Open(sVerb,sSourceURL,false,userName,passWord);                       }                       oXMLHttp.SetRequestHeader("Destination",sDestinationURL);               //send the stream across               oXMLHttp.Send();               if(oXMLHttp.Status >= 200 && oXMLHttp.Status < 300)               {                       Console.WriteLine("Success! Results = " + oXMLHttp.Status + ":" + oXMLHttp.statusText);                       flag = true;               }               else if(oXMLHttp.Status == 401)              {                       Console.WriteLine("you don't have permission to do the job!");              }              else             {                       Console.WriteLine("Request Failed.Results = " + oXMLHttp.Status + ":" + oXMLHttp.StatusText);             }             oXMLHttp = null;        }         Private void CreateMessageAndWebdavSubmit()         {                 String draftsFolder,submissionURL,attendItem,strMIMEStream,user,pwd;                 bool flag = false;                 user = "your username";                 pwd = "your password";                draftsFolder = "http://your exchange server name(IP)/exchange/useralias/Drafts/"+mailsubject+ ".EML";//if Exchange server is chinese version,change drafts to 草稿箱                submissionURL = "http://your exchange server name(IP)/exchange/useralias/##DavMailSubmissionURL##";                //use CDOSys to generate the message body parts and such                strMIMEStream  = BuildMessageAndGenerateMIMESteam();               flag = DoWebdavPut(draftsFolder,strMIMEStream,user,pwd);               if(flag)                {                        //At this point ,the email is in the drafts folder.If you don't want it sent automatically,you can                       //comment out the line below. If the line below does not execute,you can load the message                       //from outlook of OWA(outlook web access) and send it from there.                       flag = DoWebdavCopyMove(draftsFolder,submissionURL,false,user,pwd); // move it to submission!                }                              if(flag )                {                        Console.WriteLine("mail sending successfully!");               }         }
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 2
    评论
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值