Невозможно удалить документы в приложении documentum с помощью DFC

Я написал следующий код с подходом, описанным в EMC DFC 7.2 Development Guide. С помощью этого кода я могу удалить только 50 документов, хотя записей больше. Перед удалением беру дамп id объекта. Я не уверен, есть ли какие-либо ограничения для IDfDeleteOperation. Поскольку это удаляет только 50 документов, я попытался использовать команду удаления DQL, даже там она ограничена 50 документами. Я пытался использовать методы destory() и destroyAllVersions(), которые есть в документе, даже это не сработало для меня. Я написал все в основном методе.

import com.documentum.com.DfClientX;
import com.documentum.com.IDfClientX;
import com.documentum.fc.client.*;
import com.documentum.fc.common.DfException;
import com.documentum.fc.common.DfId;
import com.documentum.fc.common.IDfLoginInfo;
import com.documentum.operations.IDfCancelCheckoutNode;
import com.documentum.operations.IDfCancelCheckoutOperation;
import com.documentum.operations.IDfDeleteNode;
import com.documentum.operations.IDfDeleteOperation;

import java.io.BufferedWriter;
import java.io.FileWriter;

public class DeleteDoCAll {

    public static void main(String[] args) throws DfException {
       System.out.println("Started...");

        IDfClientX clientX  = new DfClientX();
        IDfClient dfClient = clientX.getLocalClient();
        IDfSessionManager sessionManager = dfClient.newSessionManager();
        IDfLoginInfo loginInfo = clientX.getLoginInfo();
        loginInfo.setUser("username");
        loginInfo.setPassword("password");
        sessionManager.setIdentity("repo", loginInfo);

        IDfSession dfSession = sessionManager.getSession("repo");
        System.out.println(dfSession);

        IDfDeleteOperation delo = clientX.getDeleteOperation();
        IDfCancelCheckoutOperation cco = clientX.getCancelCheckoutOperation();

       try {
           String dql = "select r_object_id from my_report where folder('/Home', descend);
           IDfQuery idfquery = new DfQuery();
           IDfCollection collection1 = null;

           try {
               idfquery.setDQL(dql);
               collection1 = idfquery.execute(dfSession, IDfQuery.DF_READ_QUERY);
               int i = 1;
               while(collection1 != null && collection1.next()) {
                   String r_object_id = collection1.getString("r_object_id");

                   StringBuilder attributes = new StringBuilder();

                   IDfDocument iDfDocument = (IDfDocument)dfSession.getObject(new DfId(r_object_id));
                   attributes.append(iDfDocument.dump());

                   BufferedWriter writer = new BufferedWriter(new FileWriter("path to file", true));
                   writer.write(attributes.toString());
                   writer.close();

                   cco.setKeepLocalFile(true);
                   IDfCancelCheckoutNode cnode;


                   if(iDfDocument.isCheckedOut()) {
                       if(iDfDocument.isVirtualDocument()) {
                           IDfVirtualDocument vdoc = iDfDocument.asVirtualDocument("CURRENT", false);
                           cnode = (IDfCancelCheckoutNode)cco.add(iDfDocument);
                       } else {
                           cnode = (IDfCancelCheckoutNode)cco.add(iDfDocument);
                       }

                       if(cnode == null) {
                           System.out.println("Node is null");
                       }
                       if(!cco.execute()) {
                           System.out.println("Cancel check out operation failed");
                       } else {
                           System.out.println("Cancelled check out for " + r_object_id);
                       }
                   }

                   delo.setVersionDeletionPolicy(IDfDeleteOperation.ALL_VERSIONS);
                   IDfDeleteNode node = (IDfDeleteNode)delo.add(iDfDocument);
                   if(node == null) {
                       System.out.println("Node is null");
                       System.out.println(i);
                       i += 1;
                   }
                   if(delo.execute()) {
                       System.out.println("Delete operation done");
                       System.out.println(i);
                       i += 1;
                   } else {
                       System.out.println("Delete operation failed");
                       System.out.println(i);
                       i += 1;
                   }
               }
           } finally {
               if(collection1 != null) {
                   collection1.close();
               }
           }

       } catch(Exception e) {
           e.printStackTrace();
       } finally {
           sessionManager.release(dfSession);
       }
   }
}

Я не знаю, где я делаю ошибку, каждый раз, когда я пытаюсь, программа останавливается на 50-й итерации. Не могли бы вы помочь мне правильно удалить все документы? Большое спасибо!


person Srivastava    schedule 13.03.2019    source источник


Ответы (3)


Сначала выберите все идентификаторы документов, например, в List<IDfId>, и закройте коллекцию. Не выполняйте другие дорогостоящие операции внутри открытой коллекции, потому что тогда вы излишне ее блокируете.

Это причина, почему он сделал только 50 документов. Потому что у вас была одна основная открытая коллекция, и каждое выполнение операции удаления открывало другую коллекцию, и, вероятно, она достигла некоторого предела. Итак, как я уже сказал, лучше сначала использовать коллекцию, а затем работать с этими данными дальше:

    List<IDfId> ids = new ArrayList<>();
    try {
        query.setDQL("SELECT r_object_id FROM my_report WHERE FOLDER('/Home', DESCEND)");
        collection = query.execute(session, IDfQuery.DF_READ_QUERY);
        while (collection.next()) {
            ids.add(collection.getId("r_object_id"));
        }
    } finally {
        if (collection != null) {
            collection.close();
        }
    }

После этого вы можете пройтись по списку и проделать все действия с нужным вам документом. Но не выполнять операцию удаления в каждой итерации — это неэффективно. Вместо этого добавьте все документы в одну операцию и выполните ее один раз в конце.

    IDfDeleteOperation deleteOperation = clientX.getDeleteOperation();
    deleteOperation.setVersionDeletionPolicy(IDfDeleteOperation.ALL_VERSIONS);
    for (IDfId id : ids) {
        IDfDocument document = (IDfDocument) session.getObject(id);
        ...
        deleteOperation.add(document);
    }
    deleteOperation.execute();

То же самое для IDfCancelCheckoutOperation.

И еще: когда вы используете FileWriter, используйте close() в блоке finally или используйте try-with-resources следующим образом:

    try (BufferedWriter writer = new BufferedWriter(new FileWriter("file.path", true))) {
        writer.write(document.dump());
    } catch (IOException e) {
        throw new UncheckedIOException(e);
    }

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

person cgrim    schedule 13.03.2019
comment
Это идеально. Это работает, большое спасибо! Но я не понял вашего предложения, потому что у вас была одна основная открытая коллекция, и каждое выполнение операции удаления открывало другую коллекцию, и, вероятно, она достигла некоторого предела. Почему операция удаления открывает другую коллекцию? Не могли бы вы объяснить это? - person Srivastava; 13.03.2019
comment
Я рад, что это помогло вам. Операция удаления вызывает метод destroy() или destroyAllVersions() (в зависимости от настроек) объекта, и оба вызывают docbase API, который возвращает результат в виде коллекции. - person cgrim; 13.03.2019

Вы можете просто сделать это из своего кода:

удалить объекты my_report, где папка ('/ Home', спуститься)

не нужно снова извлекать информацию, которую вы выбрасываете ;-)

person Henning Winter    schedule 13.03.2019

Вероятно, вы столкнулись с ограничением набора результатов для клиента DFC. Попробуйте добавить в dfc.properties эти строки и перезапустите свой код, чтобы увидеть, можно ли удалить более 50 строк, а затем настроить его в соответствии с вашими потребностями.

dfc.search.max_results = 100
dfc.search.max_results_per_source = 100
person Miki    schedule 13.03.2019