1 13 package info.magnolia.cms.taglibs.util; 14 15 import info.magnolia.cms.beans.config.ContentRepository; 16 import info.magnolia.cms.core.Content; 17 import info.magnolia.cms.core.search.Query; 18 import info.magnolia.cms.core.search.QueryResult; 19 import info.magnolia.cms.util.Resource; 20 import info.magnolia.context.MgnlContext; 21 22 import java.text.MessageFormat ; 23 24 import javax.jcr.RepositoryException; 25 import javax.servlet.http.HttpServletRequest ; 26 import javax.servlet.jsp.JspException ; 27 import javax.servlet.jsp.PageContext ; 28 import javax.servlet.jsp.tagext.TagSupport ; 29 30 import org.apache.commons.lang.ArrayUtils; 31 import org.apache.commons.lang.StringUtils; 32 import org.slf4j.Logger; 33 import org.slf4j.LoggerFactory; 34 35 36 59 public class SimpleSearchTag extends TagSupport { 60 61 64 private static final long serialVersionUID = 222L; 65 66 69 private static final String RESERVED_CHARS = "()[]{}<>:/\\@*?=\"'&"; 71 74 static final String [] KEYWORDS = new String []{"and", "or"}; 76 79 private static Logger log = LoggerFactory.getLogger(SimpleSearchTag.class); 80 81 84 private int startLevel; 85 86 89 private String query; 90 91 94 private String var; 95 96 100 private int scope = PageContext.PAGE_SCOPE; 101 102 106 public void setQuery(String query) { 107 this.query = query; 108 } 109 110 114 public void setVar(String var) { 115 this.var = var; 116 } 117 118 122 public void setScope(String scope) { 123 if ("request".equalsIgnoreCase(scope)) { this.scope = PageContext.REQUEST_SCOPE; 125 } 126 else if ("session".equalsIgnoreCase(scope)) { this.scope = PageContext.SESSION_SCOPE; 128 } 129 else if ("application".equalsIgnoreCase(scope)) { this.scope = PageContext.APPLICATION_SCOPE; 131 } 132 else { 133 this.scope = PageContext.PAGE_SCOPE; 135 } 136 } 137 138 142 public void setStartLevel(int startLevel) { 143 this.startLevel = startLevel; 144 } 145 146 149 public int doStartTag() throws JspException { 150 151 String queryString = generateXPathQuery(); 152 153 if (queryString == null) { 154 if (log.isDebugEnabled()) { 155 log.debug("A valid query could not be built, skipping"); } 157 return EVAL_PAGE; 158 } 159 160 if (log.isDebugEnabled()) { 161 log.debug("Executing xpath query " + queryString); } 163 164 Query q; 165 try { 166 q = MgnlContext.getQueryManager(ContentRepository.WEBSITE).createQuery(queryString, "xpath"); 168 QueryResult result = q.execute(); 169 170 pageContext.setAttribute(var, result.getContent(), scope); 171 } 172 catch (Exception e) { 173 log.error(MessageFormat.format( 174 "{0} caught while parsing query for search term [{1}] - query is [{2}]: {3}", new Object []{e.getClass().getName(), this.query, queryString, e.getMessage()}), e); 176 } 177 178 return EVAL_PAGE; 179 } 180 181 186 protected String generateXPathQuery() { 187 188 String startPath = null; 189 190 if (this.startLevel != 0) { 192 try { 193 Content activePage = Resource.getActivePage((HttpServletRequest ) this.pageContext.getRequest()); 194 if (activePage != null) { 195 startPath = StringUtils.strip(activePage.getAncestor(this.startLevel).getHandle(), "/"); } 197 } 198 catch (RepositoryException e) { 199 log.error(e.getMessage(), e); 200 } 201 } 202 203 String [] tokens = StringUtils.split(StringUtils.lowerCase(StringUtils.replaceChars( 205 this.query, 206 RESERVED_CHARS, 207 null))); 208 209 if (tokens == null) { 211 return null; 212 } 213 214 StringBuffer xpath = new StringBuffer (tokens.length * 20); 215 if (StringUtils.isNotEmpty(startPath)) { 216 xpath.append(startPath); 217 } 218 xpath.append("//*[@jcr:primaryType=\'mgnl:content\']/*/*["); 220 String joinOperator = "and"; boolean emptyQuery = true; 222 223 for (int j = 0; j < tokens.length; j++) { 224 String tkn = tokens[j]; 225 if (ArrayUtils.contains(KEYWORDS, tkn)) { 226 joinOperator = tkn; 227 } 228 else { 229 if (!emptyQuery) { 230 xpath.append(" "); xpath.append(joinOperator); 232 xpath.append(" "); } 234 xpath.append("jcr:contains(., '"); xpath.append(tkn); 236 xpath.append("')"); emptyQuery = false; 238 } 239 240 } 241 242 xpath.append("]"); 244 if (emptyQuery) { 246 return null; 247 } 248 249 return xpath.toString(); 250 } 251 252 255 public void release() { 256 this.query = null; 257 this.var = null; 258 this.scope = PageContext.PAGE_SCOPE; 259 this.startLevel = 0; 260 super.release(); 261 } 262 263 } 264 | Popular Tags |