none
SPAlert.Filter not working RRS feed

  • Question

  • Can anybody help with SPAlert filters on Sharepoint 2013?

    If I set Filter property on SPAlert instance  the alert has not been sent.

    SPAlert newAlert = user.Alerts.Add(); SPAlertTemplateCollection alertTemplates = new SPAlertTemplateCollection( (SPWebService)(SPContext.Current.Site.WebApplication.Parent)); newAlert.AlertType = SPAlertType.List; newAlert.List = list; newAlert.Title = alertTitle; newAlert.DeliveryChannels = SPAlertDeliveryChannels.Email; newAlert.EventType = eventType; newAlert.AlertFrequency = SPAlertFrequency.Immediate; newAlert.AlertTemplate = alertTemplates[Constants.AlertTemplates.GenericListCustom];

    var wsm = new WorkflowServicesManager(web); var wss = wsm.GetWorkflowSubscriptionService(); var subscriptions = wss.EnumerateSubscriptionsByList(list.ID); bool assotiationExist = false; var guid = Constants.Workflows.ApprovalWF.Guid; foreach (var subs in subscriptions) { assotiationExist = subs.DefinitionId == guid; if (assotiationExist) { newAlert.Filter = "<Query><Eq><FieldRef Name=\"ApprovalStatus\"/><Value type=\"string\">Approved</Value></Eq></Query>"; } } newAlert.Update(false);





    • Edited by Nikod_r Monday, January 23, 2017 9:06 AM
    Sunday, January 22, 2017 3:30 PM

Answers

  • The problem was in line newAlert.EventType = eventType. eventType was SPEventType.Add. That was the reason of not sending alert after Workflow set the ApprovalStatus field to «Approved».

    I’ve modified algourithm. Now eventType is SPEventType.Modify and I added new field "IsNewAlertSent" to list. When event fires the first time then I send email and set the "IsNewAlertSent" field

    Final code is shown below.

    class UserAlertManager:

    ..
    newAlert.EventType = (eventType == SPEventType.Add? SPEventType.Modify: eventType);
    newAlert.AlertFrequency = SPAlertFrequency.Immediate;
    newAlert.AlertTemplate = alertTemplates[Constants.AlertTemplates.GenericListCustom];
    ..
               if (assotiationExist)
               {
                  newAlert.Filter = "<Query><Eq><FieldRef name=\"ApprovalStatus\"/><Value type=\"Text\">Approved</Value></Eq></Query>";
                  newAlert.Properties.Add("grcustomalert", "1"); 
                                            
                }
    ..
    newAlert.Update(false);

    class GRCustomAlertHandler:

    ... string subject = string.Empty; string body = string.Empty; bool grCustomAlert = Utils.IsSPAlertCustom(ahp.a); if (ahp.eventData[0].eventType == (int)SPEventType.Modify && grCustomAlert) { SPListItem item = list.GetItemById(ahp.eventData[0].itemId); var isNewAlertSentField = item.Fields.GetFieldByInternalName(Constants.Fields.IsNewAlertSent); if (isNewAlertSentField != null && (item[Constants.Fields.IsNewAlertSent] == null || !(bool)item[Constants.Fields.IsNewAlertSent])) { ... Utils.SendMail(web, new List<string> { ahp.headers["to"].ToString() }, subject, body); item[Constants.Fields.IsNewAlertSent] = true; using (new DisabledItemEventScope()) { item.SystemUpdate(false); } } }

    ...



    • Edited by Nikod_r Friday, February 3, 2017 8:35 AM
    • Marked as answer by Nikod_r Friday, February 3, 2017 8:35 AM
    Friday, February 3, 2017 8:33 AM

All replies

  • Hi

    base on your description and code, I think the problem is in the caml query.

    Try to add <Where> root node, and check your item field value to see if it is exactly same.


    顺其自然地勇往直前!—Justin Liu

    Monday, January 23, 2017 3:52 AM
  • Error on newAlert.Update(false):

    Cannot use filter <Where><Query><Eq><FieldRef Name="ApprovalStatus"/><Value type="string">Approved</Value></Eq></Query></Where>. Unknown operator present in the filter.

    Monday, January 23, 2017 7:06 AM
  • Hi Nikod,

    If need to apply filter to approval status field with CAML Query, we can do it like below:

     <Where>
          <Eq>
             <FieldRef Name='_ModerationStatus' />
             <Value Type='ModStat'>0</Value>
          </Eq>
       </Where>

    Note, the field internal name is _ModerationStatus and the value for this field is :

    Approved:0,

    Rejected:1,

    Pending:2

    More information:

    Internal Value for Approval Status

    Thanks

    Best Regards


    Please remember to mark the replies as answers if they help.
    If you have feedback for TechNet Subscriber Support, contact tnmff@microsoft.com

    Monday, January 23, 2017 10:16 AM
  • Thanks, Jerry.

    But I've got the same error : "Unknown operator present in the filter."

    Site column "ApprovalStatus" is my Text custom column.

    Tuesday, January 24, 2017 6:09 AM
  • it says "unknown operator", which means the caml string is not correct.

    based on your description, I think the caml string format is ok.

    You mentioned that the ApprovalStatus is your custom column, so I think the problem is <FieldRef Name=\"ApprovalStatus\"/>.

    Go to column setting of your custom column and see the url to find the internal name, replace to ApprovalStatus. I think it should work.


    顺其自然地勇往直前!—Justin Liu

    Wednesday, January 25, 2017 12:36 AM
  • No, Justin. Column name is correct:

    &Field=ApprovalStatus


    • Edited by Nikod_r Wednesday, January 25, 2017 6:24 AM
    Wednesday, January 25, 2017 6:23 AM
  • That is strange, you could try Title field first to get a valid caml, and then filter the approvalstatus.

    顺其自然地勇往直前!—Justin Liu

    Thursday, January 26, 2017 12:13 AM
  • Hi Nikod,

    If the Approval Status is a custom text field, then the value type is text and CAML Query would like below:

    <Where>
          <Eq>
             <FieldRef Name='ApprovalStatus' />
             <Value Type='Text'>test</Value>
          </Eq>
       </Where>

    Thanks

    Best Regards


    Please remember to mark the replies as answers if they help.
    If you have feedback for TechNet Subscriber Support, contact tnmff@microsoft.com


    Thursday, January 26, 2017 1:27 AM
  • Hi, Jerry.

    That's my code now:

    SPAlert newAlert = user.Alerts.Add();
    
    SPAlertTemplateCollection alertTemplates = new SPAlertTemplateCollection(
                                        (SPWebService)(SPContext.Current.Site.WebApplication.Parent));
    
    newAlert.AlertType = SPAlertType.List;
    newAlert.List = list;
    newAlert.Title = alertTitle;
    newAlert.DeliveryChannels = SPAlertDeliveryChannels.Email;
    newAlert.EventType = eventType;
    newAlert.AlertFrequency = SPAlertFrequency.Immediate;
    newAlert.AlertTemplate = alertTemplates[Constants.AlertTemplates.GenericListCustom];
    
    
    var wsm = new WorkflowServicesManager(web);
    var wss = wsm.GetWorkflowSubscriptionService();
    var subscriptions = wss.EnumerateSubscriptionsByList(list.ID);
    bool assotiationExist = false;
    
    var guid = Constants.Workflows.ApprovalWF.Guid;
    foreach (var subs in subscriptions)
    {
               assotiationExist = subs.DefinitionId == guid;
               if (assotiationExist)
               {
                  newAlert.Filter = "<Where><Eq><FieldRef Name=\"ApprovalStatus\"/><Value type=\"Text\">Approved</Value></Eq></Where>";
                                            
                }
    }
    
    newAlert.Update(false);

    But error again: "Cannot use filter <Where><Eq><FieldRef Name="ApprovalStatus"/><Value type="Text">Approved</Value></Eq></Where>. Unknown operator present in the filter." on last code line 

    newAlert.Update(false);

    There is information about using <Query> without <Where> in alert filter:

    https://blogs.msdn.microsoft.com/sharepointdeveloperdocs/2007/12/07/customizing-alert-notifications-and-alert-templates-in-windows-sharepoint-services-3-0/
    https://social.msdn.microsoft.com/Forums/sharepoint/en-US/b92a360c-3381-4cd1-b52d-95c1a0b02516/setting-filter-on-an-alert?forum=sharepointdevelopmentlegacy

    Still not working!

    • Edited by Nikod_r Friday, January 27, 2017 9:47 AM
    Thursday, January 26, 2017 4:19 PM
  • The problem was in line newAlert.EventType = eventType. eventType was SPEventType.Add. That was the reason of not sending alert after Workflow set the ApprovalStatus field to «Approved».

    I’ve modified algourithm. Now eventType is SPEventType.Modify and I added new field "IsNewAlertSent" to list. When event fires the first time then I send email and set the "IsNewAlertSent" field

    Final code is shown below.

    class UserAlertManager:

    ..
    newAlert.EventType = (eventType == SPEventType.Add? SPEventType.Modify: eventType);
    newAlert.AlertFrequency = SPAlertFrequency.Immediate;
    newAlert.AlertTemplate = alertTemplates[Constants.AlertTemplates.GenericListCustom];
    ..
               if (assotiationExist)
               {
                  newAlert.Filter = "<Query><Eq><FieldRef name=\"ApprovalStatus\"/><Value type=\"Text\">Approved</Value></Eq></Query>";
                  newAlert.Properties.Add("grcustomalert", "1"); 
                                            
                }
    ..
    newAlert.Update(false);

    class GRCustomAlertHandler:

    ... string subject = string.Empty; string body = string.Empty; bool grCustomAlert = Utils.IsSPAlertCustom(ahp.a); if (ahp.eventData[0].eventType == (int)SPEventType.Modify && grCustomAlert) { SPListItem item = list.GetItemById(ahp.eventData[0].itemId); var isNewAlertSentField = item.Fields.GetFieldByInternalName(Constants.Fields.IsNewAlertSent); if (isNewAlertSentField != null && (item[Constants.Fields.IsNewAlertSent] == null || !(bool)item[Constants.Fields.IsNewAlertSent])) { ... Utils.SendMail(web, new List<string> { ahp.headers["to"].ToString() }, subject, body); item[Constants.Fields.IsNewAlertSent] = true; using (new DisabledItemEventScope()) { item.SystemUpdate(false); } } }

    ...



    • Edited by Nikod_r Friday, February 3, 2017 8:35 AM
    • Marked as answer by Nikod_r Friday, February 3, 2017 8:35 AM
    Friday, February 3, 2017 8:33 AM