2009-01-20 128 views
36

我只是想知道是否可以發送會議請求給沒有在服務器上安裝Outlook並使用COM Interop(我想避免在服務器上不惜一切代價)的人。在沒有Outlook的情況下發送Outlook會議請求?

我們在Windows 2003域中擁有Exchange 2003,所有用戶都是域用戶。我想我可以發送'圍繞iCal/vCal或其他東西,但我想知道是否有一個適當的標準方式通過Exchange發送會議請求沒有Outlook?

這是C#/ .net,如果它很重要。

+1

的時候,你選擇了等待的時間讓我認爲我的建議不完全是你想到的。你有沒有起作用? – Tomalak 2009-01-23 10:53:55

+1

我剛纔沒有時間去測試它。對它的快速測試似乎奏效,並且我發送了一個Outlook會議邀請函到一個啓用了POP3的帳戶以獲得「原始轉儲」。這兩位對我來說足夠好,因爲我只需要發送會議,但不關心回覆 – 2009-01-23 13:42:29

+1

無論如何,您的回答非常有幫助,非常感謝! – 2009-01-23 13:43:31

回答

47

發送會議請求到Outlook(有它識別)的方式是這樣的:

  • 準備iCalendar文件,一定要設置這些附加屬性,如Outlook需要他們:
  • 準備multipart/alternative郵件:
    • 1部分:text/html(或任何你喜歡) - 這是顯示爲「普通」郵件閱讀器或一個回落和含有事件摘要以人類可讀形式提供
    • 第2部分:text/calendar; method=REQUEST保存了ics文件的內容(頭文件method參數必須與ics中的方法相匹配)。注意正確的文本編碼,聲明charset標題參數不會受到傷害。第3部分:可選地,附加.ics文件本身,所以普通郵件閱讀器可以爲用戶提供點擊的東西。 Outlook並不需要附件,因爲它只是讀取text/calendar部件。
  • 發送郵件給outlook用戶。如果一切正常,郵件將顯示爲會議請求,並在接受時附帶出席按鈕並在用戶日曆中自動輸入。
  • 設置處理響應的內容(他們將轉到會議組織者)。我還沒有能夠讓自動跟蹤用戶跟蹤Exchange郵箱,因爲事件不會存在於組織者日曆中。 Outlook需要UID和SEQUENCES來匹配它的期望,但是用你編寫的UID很難工作。

如需幫助瞭解ics文件格式的詳細信息和特性,請務必訪問iCalendar Specification Excerpts by Masahide Kanzaki。它們在黑暗中是一道亮光,遠勝於通過RFC 2445啃咬你的方式。但是,再一次,也許有一個方便的.NET庫存在。

3

下面的代碼會以這樣的方式發送會議請求Outlook將呈現接受/拒絕按鈕。

請注意,每次會議的UID必須是唯一的,我使用了GUID。

另請注意,您需要更換CREATED,DTSTART,DTEND,DTSTAMP,最後修改。這些是UTC日期/時間。

var m = new MailMessage(); 

    m.Subject = "Meeting"; 

    m.Body = ""; 

    string iCal = 
@"BEGIN:VCALENDAR 
PRODID:-//Microsoft Corporation//Outlook 14.0 MIMEDIR//EN 
VERSION:2.0 
METHOD:PUBLISH 
X-MS-OLK-FORCEINSPECTOROPEN:TRUE 
BEGIN:VEVENT 
CLASS:PUBLIC 
CREATED:20140423T045933Z 
DESCRIPTION:desc 
DTEND:20140430T080000Z 
DTSTAMP:20140423T045933Z 
DTSTART:20140430T060000Z 
LAST-MODIFIED:20140423T045933Z 
LOCATION:location... 
PRIORITY:5 
SEQUENCE:0 
SUMMARY;LANGUAGE=en-us:Summary... 
TRANSP:OPAQUE 
UID:D8BFD357-88A7-455C-86BC-C2CECA9AC5C6 
X-MICROSOFT-CDO-BUSYSTATUS:BUSY 
X-MICROSOFT-CDO-IMPORTANCE:1 
X-MICROSOFT-DISALLOW-COUNTER:FALSE 
X-MS-OLK-AUTOFILLLOCATION:FALSE 
X-MS-OLK-CONFTYPE:0 
BEGIN:VALARM 
TRIGGER:-PT60M 
ACTION:DISPLAY 
DESCRIPTION:Reminder 
END:VALARM 
END:VEVENT 
END:VCALENDAR"; 

    using (var iCalView = AlternateView.CreateAlternateViewFromString(iCal, new System.Net.Mime.ContentType("text/calendar"))) 
    { 
     m.AlternateViews.Add(iCalView); 

     var c = new SmtpClient(); 

     // Send message 
     c.Send(m); 
    } 

這裏假設你有你的配置文件配置本地SMTP服務器:

<system.net> 
    <mailSettings> 
     <smtp deliveryMethod="Network" from="[email protected]"> 
     <network defaultCredentials="true" host="smtp.example.local" /> 
     </smtp> 
    </mailSettings> 
    </system.net> 
5

iCalendar是一個偉大的通用解決方案,以及DDay.iCal庫是做到這一點的好方法從.NET,但我相信Exchange Web Services(EWS)是在原始問題(Exchange,C#/。NET)的上下文中更好的解決方案。

如果您使用.NET語言(例如C#),則應使用EWS Managed API包裝器,這大大簡化了使用EWS的工作。

the docs,這裏是如何使用EWS託管API來創建一個會議,並請求發送到受邀者:

// Create the appointment. 
Appointment appointment = new Appointment(service); 

// Set properties on the appointment. Add two required attendees and one optional attendee. 
appointment.Subject = "Status Meeting"; 
appointment.Body = "The purpose of this meeting is to discuss status."; 
appointment.Start = new DateTime(2009, 3, 1, 9, 0, 0); 
appointment.End = appointment.Start.AddHours(2); 
appointment.Location = "Conf Room"; 
appointment.RequiredAttendees.Add("[email protected]"); 
appointment.RequiredAttendees.Add("[email protected]"); 
appointment.OptionalAttendees.Add("[email protected]"); 

// Send the meeting request to all attendees and save a copy in the Sent Items folder. 
appointment.Save(SendInvitationsMode.SendToAllAndSaveCopy); 
3

您可以使用iCal Standard (RFC 5545)

您發送的郵件會議請求到Outlook不能以這種方式發送待辦事項。 您可以發送「預約」,但這些會在outlook中顯示爲必須「盲目」接受的.ics附件。

會議請求出現在outlook中,預覽效果不錯,可以接受或拒絕。 發送程序可能會在發送後修改或取消會議。

它easieset創建與DDay.iCal .Net Library

下面的代碼有效iCal項目是一個完整的工作示例。它使用有效的iCal會議請求構建一個字符串並通過郵件發送。

的代碼創建一個電子郵件與:

  • 純文本正文簡單的郵件客戶端
  • HTML體在現代的郵件客戶端diplay
  • 的iCal會議要求爲AlternateView(將在Outlook中顯示)
  • 的iCal會議請求作爲附件(可使用在非Outlook的郵件客戶端)

的代碼顯示瞭如何添加:

  • 說明文字爲HTML,看起來前景更好
  • 優先級,能見度(公共/私有/保密)
  • 可選的組織者(會在Outlook中,而不是郵件發件人顯示)
  • 可選出席者
  • 可選鬧鐘
  • 可選附件參加會議。將在Outlook的日曆上顯示

一些重要的細節:

  • 郵件發送者(或可選的組織者)和電子郵件的接收方必須是不同的,以使前景這項工作
  • 中的.ics和方法
  • 方法在Mime.ContentType必須匹配
  • 會議必須位於未來在Outlook這項工作
  • 請在.ics部分必須是MIME郵件的最後alternateView部分

關於途觀的具體細節解釋.ics文件詳見[MS-OXCICAL]: iCalendar to Appointment Object Conversion Algorithm

我們將使用這些組件:

using System; 
using System.IO; 
using System.Net.Mail; 
using DDay.iCal; 
using DDay.iCal.Serialization.iCalendar; 

對於DDay.iCal其足夠的下載DDay.iCal binary Files。如果您想添加一些功能,最好查看DDay.iCal源代碼,因爲文檔已過時,並且源代碼包含非常完整的測試,可以體驗其所有功能。

const string filepath = @"C:\temp\ical.test.ics"; 
// use PUBLISH for appointments 
// use REQUEST for meeting requests 
const string METHOD = "REQUEST"; 

// Properties of the meeting request 
// keep guid in sending program to modify or cancel the request later 
Guid uid = Guid.Parse("2B127C67-73B3-43C5-A804-5666C2CA23C9"); 
string VisBetreff = "This is the subject of the meeting request"; 
string TerminVerantwortlicherEmail = "[email protected]"; 
string bodyPlainText = "This is the simple iCal plain text msg"; 
string bodyHtml = "This is the simple <b>iCal HTML message</b>"; 
string location = "Meeting room 101"; 
// 1: High 
// 5: Normal 
// 9: low 
int priority = 1; 
//===================================== 
MailMessage message = new MailMessage(); 

message.From = new MailAddress("[email protected]"); 
message.To.Add(new MailAddress(TerminVerantwortlicherEmail)); 
message.Subject = "[VIS-Termin] " + VisBetreff; 

// Plain Text Version 
message.Body = bodyPlainText; 

// HTML Version 
string htmlBody = bodyHtml; 
AlternateView HTMLV = AlternateView.CreateAlternateViewFromString(htmlBody, 
    new System.Net.Mime.ContentType("text/html")); 

// iCal 
IICalendar iCal = new iCalendar(); 
iCal.Method = METHOD; 
iCal.ProductID = "My Metting Product";    

// Create an event and attach it to the iCalendar. 
Event evt = iCal.Create<Event>(); 
evt.UID = uid.ToString(); 

evt.Class = "PUBLIC"; 
// Needed by Outlook 
evt.Created = new iCalDateTime(DateTime.Now); 

evt.DTStamp = new iCalDateTime(DateTime.Now); 
evt.Transparency = TransparencyType.Transparent; 

// Set the event start/end times 
evt.Start = new iCalDateTime(2014, 10, 3, 8, 0, 0); 
evt.End = new iCalDateTime(2014, 10, 3, 8, 15, 0); 
evt.Location = location; 

//var organizer = new Organizer("[email protected]"); 
//evt.Organizer = organizer; 

// Set the longer description of the event, plain text 
evt.Description = bodyPlainText; 

// Event description HTML text 
// X-ALT-DESC;FMTTYPE=text/html 
var prop = new CalendarProperty("X-ALT-DESC"); 
prop.AddParameter("FMTTYPE", "text/html"); 
prop.AddValue(bodyHtml); 
evt.AddProperty(prop); 

// Set the one-line summary of the event 
evt.Summary = VisBetreff; 
evt.Priority = priority; 

//--- attendes are optional 
IAttendee at = new Attendee("mailto:[email protected]"); 
at.ParticipationStatus = "NEEDS-ACTION"; 
at.RSVP = true; 
at.Role = "REQ-PARTICIPANT"; 
evt.Attendees.Add(at); 

// Let’s also add an alarm on this event so we can be reminded of it later. 
Alarm alarm = new Alarm(); 

// Display the alarm somewhere on the screen. 
alarm.Action = AlarmAction.Display; 

// This is the text that will be displayed for the alarm. 
alarm.Summary = "Upcoming meeting: " + VisBetreff; 

// The alarm is set to occur 30 minutes before the event 
alarm.Trigger = new Trigger(TimeSpan.FromMinutes(-30)); 

//--- Attachments 
string filename = "Test.docx"; 

// Add an attachment to this event 
IAttachment attachment = new DDay.iCal.Attachment(); 
attachment.Data = ReadBinary(@"C:\temp\Test.docx"); 
attachment.Parameters.Add("X-FILENAME", filename); 
evt.Attachments.Add(attachment); 

iCalendarSerializer serializer = new iCalendarSerializer(); 
serializer.Serialize(iCal, filepath); 

// the .ics File as a string 
string iCalStr = serializer.SerializeToString(iCal); 

// .ics as AlternateView (used by Outlook) 
// text/calendar part: method=REQUEST 
System.Net.Mime.ContentType calendarType = 
    new System.Net.Mime.ContentType("text/calendar"); 
calendarType.Parameters.Add("method", METHOD); 
AlternateView ICSview = 
    AlternateView.CreateAlternateViewFromString(iCalStr, calendarType); 

// Compose 
message.AlternateViews.Add(HTMLV); 
message.AlternateViews.Add(ICSview); // must be the last part 

// .ics as Attachment (used by mail clients other than Outlook) 
Byte[] bytes = System.Text.Encoding.ASCII.GetBytes(iCalStr); 
var ms = new System.IO.MemoryStream(bytes); 
var a = new System.Net.Mail.Attachment(ms, 
    "VIS-Termin.ics", "text/calendar"); 
message.Attachments.Add(a);  

// Send Mail 
SmtpClient client = new SmtpClient(); 
client.Send(message); 

這裏ReadBinary()函數:

private static byte[] ReadBinary(string fileName) 
{ 
    byte[] binaryData = null; 
    using (FileStream reader = new FileStream(fileName, 
     FileMode.Open, FileAccess.Read)) 
    { 
     binaryData = new byte[reader.Length]; 
     reader.Read(binaryData, 0, (int)reader.Length); 
    } 
    return binaryData; 
} 

其最簡單的配置SmtpClient在配置文件中是這樣的:

<configuration> 
    ... 
    <system.net> 
    <mailSettings> 
     <smtp> 
     <network host="mysmtp.server.com" port="25" userName="mySmtpUserName" password="myPassword" /> 
     </smtp> 
    </mailSettings> 
    </system.net> 
    ... 
相關問題