EWS:编辑 RequiredAttendees 时 'Set action is invalid for property'
EWS: 'Set action is invalid for property' when editing RequiredAttendees
在将此作为重复项关闭之前,请查看其他类似标题的问题,该问题没有答案,他只是将其标记为已回答并离开了。
每当我尝试在约会中编辑 RequiredAttendees
属性 时,我都会从 EWS manged API 收到这个可爱的描述性错误。
Set action is invalid for property.
查看异常详细信息表明确实是 RequiredAttendees
属性 导致了问题,但我不知道为什么。
我用来连接服务的凭据是会议组织者的凭据,我什至尝试过假冒用户,但没有成功。绞尽脑汁想弄清楚这里出了什么问题。
以下是导致问题的更新例程的相关部分。
PropertySet props = new PropertySet(
AppointmentSchema.Start,
AppointmentSchema.End,
AppointmentSchema.Id,
AppointmentSchema.Organizer,
AppointmentSchema.Subject,
AppointmentSchema.Body,
AppointmentSchema.RequiredAttendees);
props.RequestedBodyType = BodyType.Text;
Appointment appointment = Appointment.Bind(_service, new ItemId(appointmentId), props);
if (IsResource(appointment.Organizer.Address) && appointment.Organizer.Address != resourceId)
{
/*
* removed for brevity, no attendee manipulation here
*/
}
else
{
List<Attendee> remove = new List<Attendee>();
foreach (var attendee in appointment.RequiredAttendees)
{
if (IsResource(attendee.Address) && attendee.Address != resourceId)
{
remove.Add(attendee);
}
}
remove.ForEach(a => appointment.RequiredAttendees.Remove(a));
if (!appointment.RequiredAttendees.Any(a => a.Address == resourceId))
{
appointment.RequiredAttendees.Add(resourceId);
}
}
/*
* removed for brevity, no attendee manipulation here
*/
if (IsAvailable(resourceId, startTime, endTime, appointmentId))
appointment.Update(ConflictResolutionMode.AlwaysOverwrite, SendInvitationsOrCancellationsMode.SendToAllAndSaveCopy);
else
throw new RoomUnavailableException();
请求跟踪:
<Trace Tag = "EwsRequest" Tid="14" Time="2017-09-25 20:20:24Z" Version="15.00.0847.030">
<?xml version = "1.0" encoding="utf-8"?>
<soap:Envelope xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:m="http://schemas.microsoft.com/exchange/services/2006/messages" xmlns:t="http://schemas.microsoft.com/exchange/services/2006/types" xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
<soap:Header>
<t:RequestServerVersion Version = "Exchange2013" />
</ soap:Header>
<soap:Body>
<m:UpdateItem ConflictResolution = "AlwaysOverwrite" SendMeetingInvitationsOrCancellations="SendToAllAndSaveCopy">
<m:ItemChanges>
<t:ItemChange>
<t:ItemId Id = "AAMkAGEwYWRjZjA3LWNlZjAtNDI2Ny05ZjQwLWUzYWZjOThhMjkzNwBGAAAAAABWdX+yf6THTpO/1LYpoG6xBwD6lEwS6u8XQbDhIlTh/X/UAAAAAAENAAD6lEwS6u8XQbDhIlTh/X/UAAAi3oSdAAA=" ChangeKey="DwAAABYAAAD6lEwS6u8XQbDhIlTh/X/UAAAi3ocU" />
<t:Updates>
<t:SetItemField>
<t:FieldURI FieldURI = "calendar:RequiredAttendees" />
< t:CalendarItem>
<t:RequiredAttendees>
<t:Attendee>
<t:Mailbox>
<t:Name>Exchange Test</t:Name>
<t:EmailAddress>etest @supertester.com</t:EmailAddress>
<t:RoutingType>SMTP</t:RoutingType>
<t:MailboxType>Mailbox</t:MailboxType>
</t:Mailbox>
</t:Attendee>
<t:Attendee>
<t:Mailbox>
<t:EmailAddress>redroom @supertester.com</t:EmailAddress>
</t:Mailbox>
</t:Attendee>
</t:RequiredAttendees>
</t:CalendarItem>
</t:SetItemField>
</t:Updates>
</t:ItemChange>
</m:ItemChanges>
</m:UpdateItem>
</soap:Body>
</soap:Envelope>
</Trace>
响应跟踪:
<Trace Tag = "EwsResponse" Tid="14" Time="2017-09-25 20:20:24Z" Version="15.00.0847.030">
<?xml version = "1.0" encoding="utf-8"?>
<s:Envelope xmlns:s="http://schemas.xmlsoap.org/soap/envelope/">
<s:Header>
<h:ServerVersionInfo MajorVersion = "15" MinorVersion="1" MajorBuildNumber="225" MinorBuildNumber="41" Version="V2_48" xmlns:h="http://schemas.microsoft.com/exchange/services/2006/types" xmlns="http://schemas.microsoft.com/exchange/services/2006/types" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" />
</s:Header>
<s:Body xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema">
<m:UpdateItemResponse xmlns:m="http://schemas.microsoft.com/exchange/services/2006/messages" xmlns:t="http://schemas.microsoft.com/exchange/services/2006/types">
<m:ResponseMessages>
<m:UpdateItemResponseMessage ResponseClass = "Error" >
<m:MessageText>Set action is invalid for property.</m:MessageText>
<m:ResponseCode>ErrorInvalidPropertySet</m:ResponseCode>
<m:DescriptiveLinkKey>0</m:DescriptiveLinkKey>
<m:MessageXml>
<t:FieldURI FieldURI = "calendar:RequiredAttendees" />
</m:MessageXml>
<m:Items />
</m:UpdateItemResponseMessage>
</m:ResponseMessages>
</m:UpdateItemResponse>
</s:Body>
</s:Envelope>
</Trace>
请注意,"RequiredAttendees" object 只有在开会时才会填写。
在您的 else 语句中添加此检查
if(appointment.IsMeeting)
{
List<Attendee> remove = new List<Attendee>();
foreach (var attendee in appointment.RequiredAttendees)
{
if (IsResource(attendee.Address) && attendee.Address != resourceId)
{
remove.Add(attendee);
}
}
remove.ForEach(a => appointment.RequiredAttendees.Remove(a));
if (!appointment.RequiredAttendees.Any(a => a.Address == resourceId))
{
appointment.RequiredAttendees.Add(resourceId);
}
}
预约会议信息属性MSDN link
非常感谢 Glen Scales 为我指明了正确的方向。
当我检索约会时,我使用了以下代码:
CalendarFolder calendar = CalendarFolder.Bind(_service, new FolderId(WellKnownFolderName.Calendar, resourceId), PropertySet.IdOnly);
CalendarView cView = new CalendarView(startDate, endDate, _maxAppointments);
cView.PropertySet = new PropertySet(PropertySet.IdOnly);
FindItemsResults<Appointment> appointments = calendar.FindAppointments(cView);
其中resourceId
为会议室邮箱地址,并非会议组织者。
不允许编辑非原始约会的与会者,这就是给我错误的原因。为了更新与会者,我必须使用以下代码检索组织者的约会(大量借用 this post):
appointment = FindOrganizerAppointment(appointment);
/// <summary>
/// Finds the related Appointment.
/// </summary>
/// <param name="appointment">The appointment whose original is to be found.</param>
/// <returns></returns>
private Appointment FindOrganizerAppointment(Appointment appointment)
{
try
{
Impersonate(appointment.Organizer.Address);
var filter = new SearchFilter.IsEqualTo
{
PropertyDefinition = new ExtendedPropertyDefinition
(DefaultExtendedPropertySet.Meeting, 0x03, MapiPropertyType.Binary),
Value = GetObjectIdStringFromUid(appointment.ICalUid)
};
var view = new ItemView(1) { PropertySet = new PropertySet(BasePropertySet.FirstClassProperties) };
return _service.FindItems(WellKnownFolderName.Calendar, filter, view).Items[0] as Appointment;
}
catch (Exception e)
{
throw e;
}
finally
{
DisableImpersonation();
}
}
/// <summary>
/// Gets the object id string from uid.
/// <remarks>The UID is formatted as a hex-string and the GlobalObjectId is displayed as a Base64 string.</remarks>
/// </summary>
/// <param name="id">The uid.</param>
/// <returns></returns>
private static string GetObjectIdStringFromUid(string id)
{
var buffer = new byte[id.Length / 2];
for (int i = 0; i < id.Length / 2; i++)
{
var hexValue = byte.Parse(id.Substring(i * 2, 2), System.Globalization.NumberStyles.AllowHexSpecifier);
buffer[i] = hexValue;
}
return Convert.ToBase64String(buffer);
}
在将此作为重复项关闭之前,请查看其他类似标题的问题,该问题没有答案,他只是将其标记为已回答并离开了。
每当我尝试在约会中编辑 RequiredAttendees
属性 时,我都会从 EWS manged API 收到这个可爱的描述性错误。
Set action is invalid for property.
查看异常详细信息表明确实是 RequiredAttendees
属性 导致了问题,但我不知道为什么。
我用来连接服务的凭据是会议组织者的凭据,我什至尝试过假冒用户,但没有成功。绞尽脑汁想弄清楚这里出了什么问题。
以下是导致问题的更新例程的相关部分。
PropertySet props = new PropertySet(
AppointmentSchema.Start,
AppointmentSchema.End,
AppointmentSchema.Id,
AppointmentSchema.Organizer,
AppointmentSchema.Subject,
AppointmentSchema.Body,
AppointmentSchema.RequiredAttendees);
props.RequestedBodyType = BodyType.Text;
Appointment appointment = Appointment.Bind(_service, new ItemId(appointmentId), props);
if (IsResource(appointment.Organizer.Address) && appointment.Organizer.Address != resourceId)
{
/*
* removed for brevity, no attendee manipulation here
*/
}
else
{
List<Attendee> remove = new List<Attendee>();
foreach (var attendee in appointment.RequiredAttendees)
{
if (IsResource(attendee.Address) && attendee.Address != resourceId)
{
remove.Add(attendee);
}
}
remove.ForEach(a => appointment.RequiredAttendees.Remove(a));
if (!appointment.RequiredAttendees.Any(a => a.Address == resourceId))
{
appointment.RequiredAttendees.Add(resourceId);
}
}
/*
* removed for brevity, no attendee manipulation here
*/
if (IsAvailable(resourceId, startTime, endTime, appointmentId))
appointment.Update(ConflictResolutionMode.AlwaysOverwrite, SendInvitationsOrCancellationsMode.SendToAllAndSaveCopy);
else
throw new RoomUnavailableException();
请求跟踪:
<Trace Tag = "EwsRequest" Tid="14" Time="2017-09-25 20:20:24Z" Version="15.00.0847.030">
<?xml version = "1.0" encoding="utf-8"?>
<soap:Envelope xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:m="http://schemas.microsoft.com/exchange/services/2006/messages" xmlns:t="http://schemas.microsoft.com/exchange/services/2006/types" xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
<soap:Header>
<t:RequestServerVersion Version = "Exchange2013" />
</ soap:Header>
<soap:Body>
<m:UpdateItem ConflictResolution = "AlwaysOverwrite" SendMeetingInvitationsOrCancellations="SendToAllAndSaveCopy">
<m:ItemChanges>
<t:ItemChange>
<t:ItemId Id = "AAMkAGEwYWRjZjA3LWNlZjAtNDI2Ny05ZjQwLWUzYWZjOThhMjkzNwBGAAAAAABWdX+yf6THTpO/1LYpoG6xBwD6lEwS6u8XQbDhIlTh/X/UAAAAAAENAAD6lEwS6u8XQbDhIlTh/X/UAAAi3oSdAAA=" ChangeKey="DwAAABYAAAD6lEwS6u8XQbDhIlTh/X/UAAAi3ocU" />
<t:Updates>
<t:SetItemField>
<t:FieldURI FieldURI = "calendar:RequiredAttendees" />
< t:CalendarItem>
<t:RequiredAttendees>
<t:Attendee>
<t:Mailbox>
<t:Name>Exchange Test</t:Name>
<t:EmailAddress>etest @supertester.com</t:EmailAddress>
<t:RoutingType>SMTP</t:RoutingType>
<t:MailboxType>Mailbox</t:MailboxType>
</t:Mailbox>
</t:Attendee>
<t:Attendee>
<t:Mailbox>
<t:EmailAddress>redroom @supertester.com</t:EmailAddress>
</t:Mailbox>
</t:Attendee>
</t:RequiredAttendees>
</t:CalendarItem>
</t:SetItemField>
</t:Updates>
</t:ItemChange>
</m:ItemChanges>
</m:UpdateItem>
</soap:Body>
</soap:Envelope>
</Trace>
响应跟踪:
<Trace Tag = "EwsResponse" Tid="14" Time="2017-09-25 20:20:24Z" Version="15.00.0847.030">
<?xml version = "1.0" encoding="utf-8"?>
<s:Envelope xmlns:s="http://schemas.xmlsoap.org/soap/envelope/">
<s:Header>
<h:ServerVersionInfo MajorVersion = "15" MinorVersion="1" MajorBuildNumber="225" MinorBuildNumber="41" Version="V2_48" xmlns:h="http://schemas.microsoft.com/exchange/services/2006/types" xmlns="http://schemas.microsoft.com/exchange/services/2006/types" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" />
</s:Header>
<s:Body xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema">
<m:UpdateItemResponse xmlns:m="http://schemas.microsoft.com/exchange/services/2006/messages" xmlns:t="http://schemas.microsoft.com/exchange/services/2006/types">
<m:ResponseMessages>
<m:UpdateItemResponseMessage ResponseClass = "Error" >
<m:MessageText>Set action is invalid for property.</m:MessageText>
<m:ResponseCode>ErrorInvalidPropertySet</m:ResponseCode>
<m:DescriptiveLinkKey>0</m:DescriptiveLinkKey>
<m:MessageXml>
<t:FieldURI FieldURI = "calendar:RequiredAttendees" />
</m:MessageXml>
<m:Items />
</m:UpdateItemResponseMessage>
</m:ResponseMessages>
</m:UpdateItemResponse>
</s:Body>
</s:Envelope>
</Trace>
请注意,"RequiredAttendees" object 只有在开会时才会填写。
在您的 else 语句中添加此检查
if(appointment.IsMeeting)
{
List<Attendee> remove = new List<Attendee>();
foreach (var attendee in appointment.RequiredAttendees)
{
if (IsResource(attendee.Address) && attendee.Address != resourceId)
{
remove.Add(attendee);
}
}
remove.ForEach(a => appointment.RequiredAttendees.Remove(a));
if (!appointment.RequiredAttendees.Any(a => a.Address == resourceId))
{
appointment.RequiredAttendees.Add(resourceId);
}
}
预约会议信息属性MSDN link
非常感谢 Glen Scales 为我指明了正确的方向。
当我检索约会时,我使用了以下代码:
CalendarFolder calendar = CalendarFolder.Bind(_service, new FolderId(WellKnownFolderName.Calendar, resourceId), PropertySet.IdOnly);
CalendarView cView = new CalendarView(startDate, endDate, _maxAppointments);
cView.PropertySet = new PropertySet(PropertySet.IdOnly);
FindItemsResults<Appointment> appointments = calendar.FindAppointments(cView);
其中resourceId
为会议室邮箱地址,并非会议组织者。
不允许编辑非原始约会的与会者,这就是给我错误的原因。为了更新与会者,我必须使用以下代码检索组织者的约会(大量借用 this post):
appointment = FindOrganizerAppointment(appointment);
/// <summary>
/// Finds the related Appointment.
/// </summary>
/// <param name="appointment">The appointment whose original is to be found.</param>
/// <returns></returns>
private Appointment FindOrganizerAppointment(Appointment appointment)
{
try
{
Impersonate(appointment.Organizer.Address);
var filter = new SearchFilter.IsEqualTo
{
PropertyDefinition = new ExtendedPropertyDefinition
(DefaultExtendedPropertySet.Meeting, 0x03, MapiPropertyType.Binary),
Value = GetObjectIdStringFromUid(appointment.ICalUid)
};
var view = new ItemView(1) { PropertySet = new PropertySet(BasePropertySet.FirstClassProperties) };
return _service.FindItems(WellKnownFolderName.Calendar, filter, view).Items[0] as Appointment;
}
catch (Exception e)
{
throw e;
}
finally
{
DisableImpersonation();
}
}
/// <summary>
/// Gets the object id string from uid.
/// <remarks>The UID is formatted as a hex-string and the GlobalObjectId is displayed as a Base64 string.</remarks>
/// </summary>
/// <param name="id">The uid.</param>
/// <returns></returns>
private static string GetObjectIdStringFromUid(string id)
{
var buffer = new byte[id.Length / 2];
for (int i = 0; i < id.Length / 2; i++)
{
var hexValue = byte.Parse(id.Substring(i * 2, 2), System.Globalization.NumberStyles.AllowHexSpecifier);
buffer[i] = hexValue;
}
return Convert.ToBase64String(buffer);
}