Expand my Community achievements bar.

Guidelines for the Responsible Use of Generative AI in the Experience Cloud Community.
SOLVED

Querybuilder returns incorrect results occasionally

Avatar

Level 4

I'm having an issue where the querybuilder will occasionally return incorrect results. I have a requirement to add a label to collections containing assets with a restricted tag. It works most of the time, but occasionally the querybuilder will return collections that don't contain any restricted assets.I have a clientlib that grabs all the collection paths in the viewport and sends it to the servlet that runs the query. Based on my logging, it appears that the error is occuring in the servlet when it receives incorrect results showing a collection has an asset with the restricted tag, but doesn't. There doesn't seem to be any consistency with which collections/assets this happens to.  I have tried running the queries through the debugger repeatedly to see if it would return incorrect results, but I haven't been able to reproduce the error there. Any idea why this would happen? I'm running aem 6.5.

 

 

@Component(service= Servlet.class,
property={
Constants.SERVICE_DESCRIPTION + "=Check collection restrictions.",
"sling.servlet.methods=" + HttpConstants.METHOD_POST,
"sling.servlet.paths="+"/bin/my/check-restrictions"
})
public class CollectionRestrictionServlet extends SlingAllMethodsServlet {

private transient Logger logger = LoggerFactory.getLogger(CollectionRestrictionServlet.class);
transient Map<String, String> querymap = new HashMap<>();

@Reference
transient QueryBuilder queryBuilder;

@Override
protected void doPost(SlingHttpServletRequest request, SlingHttpServletResponse response)
throws IOException {
try {
Session session = request.getResourceResolver().adaptTo(Session.class);
RequestParameter[] param = request.getRequestParameters("item");
List<String> collections = new ArrayList<>();
List<String> resCollections = new ArrayList<>();
for(RequestParameter par : param){
collections.add(URLDecoder.decode(par.getString(), "UTF-8"));
}
Writer writer = response.getWriter();
logger.info("Collections checked for asset restrictions: " + collections);
for(String col : collections){
querymap.put("path", "/content");
querymap.put("type", "dam:Asset");
querymap.put("memberOf", col);
querymap.put("property", "jcr:content/metadata/restricted");
querymap.put("property.1_value", "my-asset-info:restricted/do-not-modify");
querymap.put("property.2_value", "my-asset-info:restricted/credit-to-photographer");
querymap.put("property.3_value", "my-asset-info:restricted/credit-to-designer");
querymap.put("property.4_value", "my-asset-info:restricted/digital-use-only");
querymap.put("property.5_value", "my-asset-info:restricted/social-media-use-only");
querymap.put("p.limit", "1");
Query query = queryBuilder.createQuery(PredicateGroup.create(querymap), session);
SearchResult result = query.getResult();
long resNum = result.getTotalMatches();
logger.info("Collection: " + col + " returned " + resNum);
if (resNum > 0){
resCollections.add(col);
}
}
if (resCollections.size() > 0){
String out = resCollections.toString();
logger.info("Collections with restrictions sent to clientlib: " + out);
writer.write(out);
}
else {
writer.write("");
}
}
catch(Exception e){
logger.error("Unable to obtain asset restrictions for collection " + e);
}
}
}
1 Accepted Solution

Avatar

Correct answer by
Level 4

After some more testing and reading through the documentation I have added in a line 

queryBuilder.clearFacetCache();

at the end of each for loop. This has fixed the issue. 

View solution in original post

7 Replies

Avatar

Community Advisor

What is the below line do ? 

querymap.put("memberOf", col);

 and you are returning 1 , if you want all the result set p.limit=-1

 querymap.put("p.limit", "1");

 

Avatar

Level 4
querymap.put("memberOf", col);

this finds assets that are a member of the collection I am checking.

 

And as far as the p.limit goes, I only need the one result. If the collection has a single asset with a restriction tag it gets the restricted label.

Avatar

Community Advisor

It looks like you are NOT using a service user, which can be a problem with querying nodes in the JCR, might be a permissions issue. I suggest you exchange 

                        Session session = request.getResourceResolver().adaptTo(Session.class);

with a service user, and then ensure that all the right permissions are assigned to this service user. 

Are you always using admin user when performing your actions?

Avatar

Level 4

Wouldn't the admin have the permissions required? I tried using a service user, but for some reason i'm getting "session has been closed" errors on some of the queries now. Previously, I wasn't receiving any access control errors or anything. 

 

here's the code I added to try your suggestion:

 

Map<String, Object> params = new HashMap<String, Object>();
params.put(ResourceResolverFactory.USER, MyConstants.MY_SYSTEM_USER);
resolver = resourceResolverFactory.getServiceResourceResolver(params);
Session session = resolver.adaptTo(Session.class);

 

Avatar

Community Advisor

If you are looking for single result then use p.limit=1 and order by clause to get consistent result.



Arun Patidar

Avatar

Level 4

I'm not sure how this would affect the error I'm experiencing? The query should be returning 0 results in the instances I am referring to, but instead it is saying that assets are members of collections that they aren't in at all. 

Avatar

Correct answer by
Level 4

After some more testing and reading through the documentation I have added in a line 

queryBuilder.clearFacetCache();

at the end of each for loop. This has fixed the issue.