Чтение всех компонентов из папки и подпапки

Я работаю над Tridon 2009, используя .NET Templating С# 2.0.

Мне нужно прочитать все компоненты из папки и ее подпапки.

Если в моем коде я пишу:

OrganizationalItem imageFolder = 
    (OrganizationalItem)m_Engine.GetObject(comp.OrganizationalItem.Id);  

Я могу прочитать все компоненты в подпапке из того места, где присутствует компонент индикатора, но я не могу прочитать другие компоненты, присутствующие в папке, где присутствует индикатор.

Но если я напишу

OrganizationalItem imageFolder = (OrganizationalItem)m_Engine.GetObject(
                                comp.OrganizationalItem.OrganizationalItem.Id);  

то я могу читать только папку, в которой присутствует индикаторный компонент.

Ниже мой код.

XmlDocument doc = xBase.createNewXmlDocRoot("ImageLibrary");
XmlElement root = doc.DocumentElement;


Filter filter = new Filter();
Component comp = this.GetComponent();

filter.Conditions["ItemType"] = ItemType.Folder;
filter.Conditions["Recursive"] = "true";

OrganizationalItem imageFolder = 
       (OrganizationalItem)m_Engine.GetObject(comp.OrganizationalItem.Id);            
XmlElement itemList = imageFolder.GetListItems(filter);

foreach (XmlElement itemImg in itemList)
{
    filter.Conditions["ItemType"] = ItemType.Component;
    filter.Conditions["BasedOnSchema"] = comp.Schema.Id;

    OrganizationalItem imgFolder = 
       (OrganizationalItem)m_Engine.GetObject(itemImg.GetAttribute("ID")
       .ToString());
    XmlElement imageLibs = imgFolder.GetListItems(filter);

    doc = this.createImageNodes(imageLibs, doc, filter, comp);
    foreach (XmlElement imglib in imageLibsList)
    {
        XmlElement imageroot = doc.CreateElement("Image");
        XmlElement uploadeddateNode = doc.CreateElement("DateUploaded");
        Component imgComp =    
                (Component)m_Engine.GetObject(imglib.GetAttribute("ID"));
    }
}

Пожалуйста, предложите.


person user1678234    schedule 29.09.2012    source источник


Ответы (3)


Я вижу много лишнего кода в вашем фрагменте по вопросу «Чтение всех компонентов из папки и подпапки».

Но отвечая на сам вопрос, когда вы делаете:

OrganizationalItem imageFolder = (OrganizationalItem)m_Engine.GetObject(comp.OrganizationalItem.Id);

Вы не можете читать компоненты, присутствующие в этой папке, потому что ранее вы установили фильтр для папок только в следующей строке:

filter.Conditions["ItemType"] = ItemType.Folder;

Решение:

Если вы хотите получить все компоненты в папке «компонент индикатора» и ниже, вам необходимо установить фильтр при первом поиске следующим образом:

filter.Conditions["Recursive"] = "true";
filter.Conditions["ItemType"] = ItemType.Component;
filter.Conditions["BasedOnSchema"] = comp.Schema.Id;

И выполните поиск:

OrganizationalItem imageFolder = (OrganizationalItem)m_Engine.GetObject(comp.OrganizationalItem.Id);            
XmlElement itemList = imageFolder.GetListItems(filter);
person Puntero    schedule 29.09.2012
comment
Огромное спасибо. Сегодня у меня нет времени, чтобы исправить это. Я проверю это и вернусь к вам. Еще раз спасибо - person user1678234; 30.09.2012

Довольно базовые вещи. Старайтесь избегать использования класса Filter, так как он устарел в 2009 году, и используйте GetListItems как можно чаще, так как выборка списков ВСЕГДА быстрее.

public class GetComponentsInSameFolder : ITemplate
{
    public void Transform(Engine engine, Package package)
    {
        TemplatingLogger log = TemplatingLogger.GetLogger(GetType());
        if (package.GetByName(Package.ComponentName) == null)
        {
            log.Info("This template should only be used with Component Templates. Could not find component in package, exiting");
            return;
        }
        var c = (Component)engine.GetObject(package.GetByName(Package.ComponentName));
        var container = (Folder)c.OrganizationalItem;
        var filter = new OrganizationalItemItemsFilter(engine.GetSession()) { ItemTypes = new[] { ItemType.Component } };

        // Always faster to use GetListItems if we only need limited elements
        foreach (XmlNode node in container.GetListItems(filter))
        {
            string componentId = node.Attributes["ID"].Value;
            string componentTitle = node.Attributes["Title"].Value;
        }

        // If we need more info, use GetItems instead
        foreach (Component component in container.GetItems(filter))
        {
            // If your filter is messed up, GetItems will return objects that may
            // not be a Component, in which case the code will blow up with an
            // InvalidCastException. Be careful with filter.ItemTypes[]
            Schema componentSchema = component.Schema;
            SchemaPurpose purpose = componentSchema.Purpose;
            XmlElement content = component.Content;
        }
    }
}
person Nuno Linhares    schedule 01.10.2012

Я думаю, вы захотите собрать подпапки и рекурсивно вызвать свою функцию для каждой из них, что похоже на то, чего вы пытаетесь достичь.

Эта функция называется createImageNodes() и где вы устанавливаете imageLibsList?

Похоже, вы рассматриваете каждый элемент как папку в своем первом цикле, а как насчет компонентов?

person Alvin Reyes    schedule 29.09.2012
comment
Да, мне нужно прочитать все компоненты, где присутствует мой индикаторный компонент. Также прочитайте все компоненты в папках и подпапках, где присутствует индикатор. - person user1678234; 30.09.2012