我知道如何通过JCR在 JCR SQL2 queries 中搜索某些内容。
但是,我想在某些情况下使用Java,使用JCR API:javax.jcr.Node
,javax.jcr.NodeIterator
等。
我担心我会通过自己的编码来重新发明轮子。
是否有任何可用的内容(Gist
,Github
或else
)?
答案 0 :(得分:2)
您可以使用SlingQuery。它受jQuery的启发并遵循它的语法。您应该仅使用它来搜索少量节点(最好在100以下),因为遍历查询很慢。
修改强>
您的示例可能会转换为以下SlingQueries(未经测试):
SlingQuery.$(startResource).find("[name=teasers][title=awesome-teaser]")
SlingQuery.$(startResource).find("[name][controlName]")
SlingQuery是Apache Sling的一部分,因为有一段时间,这就是github存储库似乎被放弃的原因。
注意:您可以静态导入Dollar符号并使用语法删除SlingQuery上的静态访问,例如$(resource).find(" ...");
答案 1 :(得分:1)
我最终编写了自己的实现。
随意改进或添加评论以获得潜在的改进。
Java可能不是搜索JCR的最有效方式,因此请注意性能损失(使用JCR SQL2
)。
但是,有些情况下使用JCR SQL2会比较烦人。例如:JCR SQL2 - result query order as in JCR browser
我建议您在树中尽可能低地启动搜索。
阅读上述每种方法的评论以找到更多信息。
package com.nameoforganization.jcr;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.Map;
import javax.jcr.Node;
import javax.jcr.NodeIterator;
import javax.jcr.RepositoryException;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
public class JcrSearchUtils {
private static final Logger log = LoggerFactory.getLogger(JcrUtil.class);
/*
* Recursive search in JCR tree: properties matching values
* Parameters:
* - node: node to start the search from
* - propertyValueConditions: properties searched along with the value expected for it
* - searchResults: set this to null when launching the search
*/
public static ArrayList<Node> searchRecursivelyPropMatchVal(Node node, HashMap<String, String> propertyValueConditions, ArrayList<Node> searchResults) {
if(searchResults == null){
searchResults = new ArrayList<Node>();
}
try{
NodeIterator list = node.getNodes();
while(list.hasNext()) {
Node currentSubNode = list.nextNode();
Boolean hasAllRequiredPropsAndVals = true;
for (Map.Entry<String, String> entry : propertyValueConditions.entrySet()) {
String propertyName = entry.getKey();
Object searchedValue = entry.getValue();
if ( !currentSubNode.hasProperty(propertyName) || !currentSubNode.getProperty(propertyName).getString().equals(searchedValue) ){
hasAllRequiredPropsAndVals = false;
}
}
if ( hasAllRequiredPropsAndVals ){
searchResults.add(currentSubNode);
}
searchRecursivelyPropMatchVal(currentSubNode, propertyValueConditions, searchResults);
}
return searchResults;
} catch (RepositoryException rpe){
log.info("Recursive search in JCR tree (properties matching values) via JCR API failed");
}
return null;
}
/*
* Recursive search in JCR tree: required properties present
* Parameters:
* - node: node to start the search from
* - propertyValueConditions: properties searched along with the value expected for it
* - searchResults: set this to null when launching the search
*/
public static ArrayList<Node> searchRecursivelyPropPres(Node node, ArrayList<String> propertyPresConditions, ArrayList<Node> searchResults) {
if(searchResults == null){
searchResults = new ArrayList<Node>();
}
try{
NodeIterator list = node.getNodes();
while(list.hasNext()) {
Node currentSubNode = list.nextNode();
Boolean hasAllRequiredProperties = true;
for (String propertyName : propertyPresConditions) {
if ( !currentSubNode.hasProperty(propertyName) ){
hasAllRequiredProperties = false;
}
}
if( hasAllRequiredProperties ){
searchResults.add(currentSubNode);
}
searchRecursivelyPropPres(currentSubNode, propertyPresConditions, searchResults);
}
return searchResults;
} catch (RepositoryException rpe){
log.info("Recursive search in JCR tree (required properties present) via JCR API failed");
}
return null;
}
}
/*
* Search nodes with properties:
* "name" having value "teasers"
* "title" having value "awesome-teaser"
*/
// Node startingNode = set this yourself :)
HashMap<String, String> propertyValueConditions = new HashMap<String, String>();
propertyValueConditions.put("name", "teasers");
propertyValueConditions.put("title", "awesome-teaser");
ArrayList<Node> nodesFound = JcrUtil.searchRecursivelyPropMatchVal(startingNode, propertyValueConditions, null);
/*
* Search nodes having properties "name" and "controlName"
*/
// Node startingNode = set this yourself :)
ArrayList<String> propertyPresConditions = new ArrayList<String>();
propertyPresConditions.add("name");
propertyPresConditions.add("controlName");
ArrayList<Node> nodesFound = JcrUtil.searchRecursivelyPropPres(startingNode, propertyPresConditions, null);
答案 2 :(得分:1)
您可以使用ItemVisitor递归遍历存储库,收集符合您标准的所有项目。
E.g。打印出class UserMailer < ApplicationMailer
def try_notif(notification, post, user)
@notification = notification
@post = post
@user = user
mail(to: @post.user.email, subject: 'New Notification')
end
end
类型的所有属性:
Long