6

Using the Core Service, is there any way to get information (ID at the minimum) about all the pages in the CMS?

I had tried recursing through structure groups but this takes hours as there are 50000+ pages. Currently I am getting this information by querying the database directly.

If there is a way would it be possible to do this for components, component templates etc?

For reference my recursion code is

static void Main(string[] args)
{
    using (var client = new Tridion2011CoreService.CoreServiceClient())
    {
        var ids = GetIDsRecursive(client, "tcm:10-234567-4");
    }
}

private static List<string> GetIDsRecursive(
    Tridion2011CoreService.CoreServiceClient client,
    string parentOrganisationalItemID,
    IEnumerable<Tridion2011CoreService.ItemType> itemTypes)
{
    var ids = new List<string>();

    var filter = new Tridion2011CoreService.OrganizationalItemItemsFilterData();

    var filterItemTypes = new List<Tridion2011CoreService.ItemType>();
    if (parentOrganisationalItemID.EndsWith("-2"))
    {
        filterItemTypes.Add(Tridion2011CoreService.ItemType.Folder);
    }
    else
    {
        filterItemTypes.Add(Tridion2011CoreService.ItemType.StructureGroup);
    }
    filter.ItemTypes = filterItemTypes.ToArray();

    var result1 = client.GetListXml(parentOrganisationalItemID, filter);

    foreach (System.Xml.Linq.XElement node in result1.Nodes())
    {
        var id = node.Attribute("ID").Value;
        ids.AddRange(GetIDsRecursive(client, id, itemTypes));
    }

    filter = new Tridion2011CoreService.OrganizationalItemItemsFilterData();
    filter.ItemTypes = itemTypes.ToArray();

    var result2 = client.GetListXml(parentOrganisationalItemID, filter);

    foreach (System.Xml.Linq.XElement node in result2.Nodes())
    {
        var id = node.Attribute("ID").Value;
        ids.Add(id);
    }

    return ids;
}
  • Consider timing what parts take the longest, but some trivial improvements would be assuming all child items in a folder or SG are the same as the parent (check in the first call rather than in the recursive method) and maybe create the filters outside of the method and simply re-use them. – Alvin Reyes Aug 18 '13 at 5:34
7

Do you need it for all publications, or only in scope of some publication ? You can try to use something next:

var itemTypes = new List<Tridion2011CoreService.ItemType>();
itemTypes.Add(Tridion2011CoreService.ItemType.Page);

var filter = new Tridion2011CoreService.RepositoryItemsFilterData();
filter.Recursive = true;
filter.ItemTypes = itemTypes.ToArray();

var listXml = client.GetListXml("tcm:0-10-1", filter);
// SDL Tridion 2013 (ICoreService2012) and later, can use GetList() as well

foreach (System.Xml.Linq.XElement node in listXml.Nodes())
{
    ...
}

If you need to get separate lists of components/templates/pages/etc - better specify all ItemType which you need and filter result list in the end.

  • Thanks. Your code didn't work straight away so I changed the call to return XML and it worked fine. Hope you don't mind me overwriting with what worked for me? It was the RepositoryItemsFilter that was the key. – Kevin Brydon Aug 16 '13 at 10:43
  • Tridion 2011 CoreService did not implement all GetList() methods, only GetListXml(). With 2013 this was fixed. – Nuno Linhares Aug 16 '13 at 11:52
  • Probably yes, but I didn't get, that it was Tridion 2011 :) Now I can see that in your code. – Syav4eg Aug 17 '13 at 5:33
  • I added a comment to clarify GetList() works as well if on 2013 and updated this somewhat related answer with the specific API versions: tridion.stackexchange.com/a/305/46. – Alvin Reyes Aug 18 '13 at 5:44
2

In 2013 SP1 the code is:

var itemTypes = new List<ItemType>();
itemTypes.Add(ItemType.Page);

var filter = new RepositoryItemsFilterData();
filter.Recursive = true;
filter.ItemTypes = itemTypes.ToArray();

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.