This is an automated email from the ASF dual-hosted git repository.

mridulpathak pushed a commit to branch trunk
in repository https://gitbox.apache.org/repos/asf/ofbiz-plugins.git


The following commit(s) were added to refs/heads/trunk by this push:
     new 7fa3b821c Fixed: A database error while indexing adds an incomplete 
product or content document to the Lucene index (OFBIZ-13700)
7fa3b821c is described below

commit 7fa3b821c1698155f54545abe6f06ff1e634253c
Author: Mridul Pathak <[email protected]>
AuthorDate: Tue Oct 20 13:40:50 2026 +0530

    Fixed: A database error while indexing adds an incomplete product or 
content document to the Lucene index (OFBIZ-13700)
    
    - ContentDocument looks up the content ancestors itself instead of calling 
ContentWorker.getContentAncestryAll(), which logged database errors, so a 
database error is thrown and the content is no longer indexed without its site.
    - ProductDocument rethrows a GenericEntityException raised while rendering 
a product content as text, instead of indexing the product without that text. 
Other rendering errors are still logged, so that a broken content does not 
block the re-indexing of the product.
---
 .../ofbiz/content/search/ContentDocument.java      | 31 +++++++++++++++++++++-
 .../ofbiz/content/search/ProductDocument.java      |  3 +++
 2 files changed, 33 insertions(+), 1 deletion(-)

diff --git 
a/lucene/src/main/java/org/apache/ofbiz/content/search/ContentDocument.java 
b/lucene/src/main/java/org/apache/ofbiz/content/search/ContentDocument.java
index 5f78028a0..07ac5f293 100644
--- a/lucene/src/main/java/org/apache/ofbiz/content/search/ContentDocument.java
+++ b/lucene/src/main/java/org/apache/ofbiz/content/search/ContentDocument.java
@@ -21,8 +21,10 @@ package org.apache.ofbiz.content.search;
 import java.io.IOException;
 import java.sql.Timestamp;
 import java.util.ArrayList;
+import java.util.HashSet;
 import java.util.List;
 import java.util.Locale;
+import java.util.Set;
 
 import org.apache.lucene.document.Document;
 import org.apache.lucene.document.Field;
@@ -36,7 +38,9 @@ import org.apache.ofbiz.base.util.UtilMisc;
 import org.apache.ofbiz.base.util.UtilValidate;
 import org.apache.ofbiz.content.content.ContentWorker;
 import org.apache.ofbiz.entity.Delegator;
+import org.apache.ofbiz.entity.GenericEntityException;
 import org.apache.ofbiz.entity.GenericValue;
+import org.apache.ofbiz.entity.util.EntityQuery;
 import org.apache.ofbiz.service.LocalDispatcher;
 
 /**
@@ -91,7 +95,7 @@ public class ContentDocument implements LuceneDocument {
             doc.add(new TextField("description", description, Store.YES));
         }
         List<String> ancestorList = new ArrayList<>();
-        ContentWorker.getContentAncestryAll(content.getDelegator(), contentId, 
"WEB_SITE_PUB_PT", "TO", ancestorList);
+        getContentAncestry(content.getDelegator(), contentId, 
"WEB_SITE_PUB_PT", ancestorList, new HashSet<>());
         String ancestorString = StringUtil.join(ancestorList, " ");
         if (UtilValidate.isNotEmpty(ancestorString)) {
             Field field = new StringField("site", ancestorString, Store.NO);
@@ -104,6 +108,31 @@ public class ContentDocument implements LuceneDocument {
         return doc;
     }
 
+    /**
+     * Adds the ancestors of a content having the given content type to the 
list, following the content associations from
+     * contentId to contentIdTo. Unlike ContentWorker.getContentAncestryAll(), 
a database error is thrown instead of being
+     * logged, so that the content is not indexed without its ancestors.
+     */
+    private static void getContentAncestry(Delegator delegator, String 
contentId, String contentTypeId, List<String> ancestorList,
+            Set<String> visitedContentIds) throws GenericEntityException {
+        if (!visitedContentIds.add(contentId)) {
+            return;
+        }
+        List<GenericValue> contentAssocs = 
EntityQuery.use(delegator).from("ContentAssoc")
+                .where("contentId", contentId)
+                .cache().filterByDate().queryList();
+        for (GenericValue contentAssoc : contentAssocs) {
+            String contentIdTo = contentAssoc.getString("contentIdTo");
+            getContentAncestry(delegator, contentIdTo, contentTypeId, 
ancestorList, visitedContentIds);
+            if (!ancestorList.contains(contentIdTo)) {
+                GenericValue contentTo = 
EntityQuery.use(delegator).from("Content").where("contentId", 
contentIdTo).cache().queryOne();
+                if (contentTo != null && 
contentTypeId.equals(contentTo.getString("contentTypeId"))) {
+                    ancestorList.add(contentIdTo);
+                }
+            }
+        }
+    }
+
     private boolean indexDataResource(Document doc) throws GeneralException {
         String contentId = content.getString("contentId");
         GenericValue dataResource = content.getRelatedOne("DataResource", 
true);
diff --git 
a/lucene/src/main/java/org/apache/ofbiz/content/search/ProductDocument.java 
b/lucene/src/main/java/org/apache/ofbiz/content/search/ProductDocument.java
index 032452803..c0a407941 100644
--- a/lucene/src/main/java/org/apache/ofbiz/content/search/ProductDocument.java
+++ b/lucene/src/main/java/org/apache/ofbiz/content/search/ProductDocument.java
@@ -296,6 +296,9 @@ public class ProductDocument implements LuceneDocument {
                             String contentText = 
DataResourceWorker.renderDataResourceAsText(null, delegator, 
productContentAndInfo.getString(
                                     "dataResourceId"), drContext, null, null, 
false);
                             addTextField(doc, "content", contentText, false, 
"fullText", delegator);
+                        } catch (GenericEntityException e) {
+                            // a database error: keep the indexed document 
rather than index the product without this text
+                            throw e;
                         } catch (IOException | GeneralException e1) {
                             Debug.logError(e1, "Error getting content text to 
index", MODULE);
                         }

Reply via email to