![](/img/trans.png)
[英]Outlook RPC server unavailable after sending email through .Net app
[英]“RPC Server is unavailable” when exporting Outlook contacts to CSV
我正在将具有自定义表单的Outlook联系人从特定的Contacts文件夹导出为CSV。 此文件夹不是默认位置。 这是一个包含近7,000个联系人的大文件夹。 这是Office 365中的共享邮箱,但是由于自定义数据,我们无法使用Outlook或Graph API。
我的下面的代码工作正常,除了在遍历200-800个联系人之后,我收到此错误:“ RPC服务器不可用。(HRESULT的异常:0x800706BA)。”
我还尝试将文件夹导出到.pst并访问本地计算机上的该文件夹。 结果基本相同。 更新:我一直在任务管理器中观看Outlook.exe,它在崩溃前稳定地将其内存消耗增加到300MB左右。 我在运行Office 2010的笔记本电脑上尝试了相同的代码,但出现“内存不足”错误。
无论Outlook是打开还是关闭,我都会收到错误消息,但是在程序运行过程中关闭Outlook会立即触发此错误。 Outlook会在出现此错误后启动(或重新启动)。 我已经阅读了许多与该错误有关的SO帖子和文章,但是我不确定到底是怎么回事。 任何帮助表示赞赏。
更新:根据Dmitry Streblechenko的建议,代码已更新为for
循环,而不是foreach
循环。
using System;
using Microsoft.Office.Interop.Outlook;
using System.Text;
using System.IO;
using System.Runtime.InteropServices;
namespace OutlookContacts
{
class Program
{
static void Main(string[] args)
{
var encoding = Encoding.UTF8;
string csvPath = @"myCSVPath";
Application outlook = new Application();
NameSpace ns = outlook.GetNamespace("MAPI");
MAPIFolder sharedContacts;
string recipientName = "myEmail@myDomain";
StringBuilder headerRow = new StringBuilder();
Recipient recip = ns.CreateRecipient(recipientName);
StreamWriter writer = new StreamWriter(csvPath, false, encoding);
recip.Resolve();
if (recip.Resolved)
{
try
{
//EntryID and StoreID of my folder
sharedContacts =
ns.GetFolderFromID(
"myEntryID",
"myStoreID"
);
Items contacts = sharedContacts.Items;
//Writing header row
ContactItem first = contacts.GetFirst();
var properties = first.ItemProperties;
for(int i = 0; i < properties.Count; i++)
{
try
{
headerRow.Append(string.Format("\"{0}\",", properties[i].Name));
}
catch (System.Exception ex)
{
headerRow.Append(string.Format("{0},", ex.Message));
}
}
headerRow.AppendLine(Environment.NewLine);
WriteToCSV(writer, headerRow);
Console.WriteLine("Header row written;");
Marshal.ReleaseComObject(properties);
Marshal.ReleaseComObject(first);
//Writing Records
for (int i = 1; i <= contacts.Count; i++)
{
object o = contacts[i];
if (o is ContactItem)
{
ContactItem contact = (ContactItem)o;
if (contact != null)
{
Console.Write(contact.FullName);
StringBuilder dataRow = new StringBuilder();
ItemProperties contactProps = contact.ItemProperties;
for (int j = 0; j < contactProps.Count; j++)
{
ItemProperty property = contactProps[j];
try
{
if (property.Value == null)
{
string value = "null,";
dataRow.Append(value);
}
//else if (property.Name == "Attachments")
//{
// //Attachment file names
// string attachment = "";
// for (int k = 1; k < contact.Attachments.Count; k++)
// {
// attachment = (string.Format("\"{0}\"; ", contact.Attachments[k].FileName));
// dataRow.Append(attachment);
// }
// dataRow.Append(",");
//}
else
{
string value = property.Value.ToString();
value = value.Replace("\r\n\r\n\r\n", "\r\n")
.Replace("\r\n\r\n", "\r\n")
.Replace("\"", "'");
value = (string.Format("\"{0}\",", value));
dataRow.Append(value);
}
}
catch (System.Exception ex)
{
string value = string.Format("{0}: {1},", property.Name, ex.Message);
dataRow.Append(value);
}
Marshal.ReleaseComObject(property);
}
dataRow.Append(Environment.NewLine);
WriteToCSV(writer, dataRow);
Marshal.ReleaseComObject(contactProps);
Marshal.ReleaseComObject(contact);
}
Marshal.ReleaseComObject(o);
counter++;
Console.WriteLine(": Written " + counter);
}
}
}
catch (System.Exception ex)
{
Console.WriteLine(dataRow.ToString(), ex.Message);
Console.ReadKey();
}
}
}
static void WriteToCSV(StreamWriter writer, StringBuilder row)
{
var data = row.ToString();
writer.WriteAsync(data);
}
}
}
看起来您用完了RPC通道。 您需要避免使用foreach循环(它们倾向于保持引用所有集合成员,直到循环退出),并在完成处理后立即显式释放所有COM对象。
从我的头顶上:
for(int i = 1; i <= contacts.Count; i++)
{
obejct o = contacts[i];
ContactItem contact = o as ContactItem;
if (o != null)
{
ItemProperties properties = contact.ItemProperties;
StringBuilder newLine = new StringBuilder();
for (int j = 1; j <= properties.Count; j++)
{
ItemProperty property = properties[j];
var value = "";
if (property.Value == null)
{
value = "null,";
Console.WriteLine(value);
newLine.Append(value);
}
else
{
value = property.Value.ToString() + ",";
newLine.Append(value);
}
Marshal.ReleaseComObject(property);
}
newLine.Append(Environment.NewLine);
WriteToCSV(writer, newLine);
Marshal.ReleaseComObject(properties);
Marshal.ReleaseComObject(contact);
}
Marshal.ReleaseComObject(o);
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.