As you have probably seen, CRM has the ability to roll-up information from child Entities to the parent Entity. Activities would be one such example: When you look at the Activities for an Account, you actually see Activities for both the main Account as well as all Activities for the Account's Contacts as well. A pretty great feature, if you ask me.
Anyway, the CRM SDK also has Roll-up messages that allow you to retrieve information in a similar manner. The following list shows the target classes for the Rollup message:
TargetRollupActivityPointerByAccount
TargetRollupActivityPointerByContact
TargetRollupActivityPointerByOpportunity
TargetRollupAnnotationByAccount
TargetRollupAnnotationByContact
TargetRollupAnnotationByOpportunity
TargetRollupOpportunityByAccount
TargetRollupOpportunityByContact
TargetRollupSalesOrderByAccount
TargetRollupSalesOrderByContact
I haven't worked through all of these messages, but I have tested the Activitypointer ( Activities ) and Annotation ( Notes ) messages, and they work exactly as you would expect.
I did have one problem when I first started playing around this morning: I couldn't make it work. No matter what I tried, I could not make the rollup message execute successfully. Luckily, Jonathan Randall, one of the Microsoft Online Support resources, had posted a solution to my exact problem, to another person back in April of 2006. His code is follows:
RollupResponse related = null; try { QueryExpression query = new QueryExpression(); query.EntityName = EntityName.activitypointer.ToString(); query.ColumnSet = new AllColumns(); TargetRollupActivityPointerByAccount activityRollup = new TargetRollupActivityPointerByAccount(); activityRollup.AccountId =
new Guid("69B242AE-0348-DB11-AAA0-00142A05B544");
activityRollup.Query = query;
RollupRequest rollup = new RollupRequest();
rollup.ReturnDynamicEntities=false;
rollup.RollupType=RollupType.Related;
rollup.Target=activityRollup;
related = (RollupResponse)service.Execute(rollup);
if (related.BusinessEntityCollection.BusinessEntities.Length >0)
{
string txtResults = string.Empty;
foreach (activitypointer pointer in
related.BusinessEntityCollection.BusinessEntities)
{
txtResults += pointer.subject + " : " +
pointer.description + " : " +
pointer.activitytypecode.Value.ToString() +
" : " +
pointer.statecode.ToString() +
Environment.NewLine;
}
MessageBox.Show(txtResults, "Activities");
}
}
catch (System.Web.Services.Protocols.SoapException err)
{
MessageBox.Show(err.Detail.OuterXml.ToString(), "Error");
}
So what is the big deal?
The problem I was having, was related to the formation of the Query field that is being passed to the Rollup message. Let's take the TargetRollupActivityPointerByAccount for example. This message has two fields: AccountId and Query.
It turns out that the Query field is a query on the Entity being rolled up, not on the parent Entity to which those records belong. In other words, given the above message, I would specify my Query parameters for the ActivityPointer Entity, not the Account Entity.
TargetRollupAnnotationByAccount works in a similar manner. We specify Query parameters for the Annotation Entity, not the Account Entity.
Once I understood that little fact, all of the other stuff made perfect sense.
Note: In the example above, we specify no expression filters so the query will return All of the activities.
Reference:




