Adds methods handling 'filter' and 'limit' expressions
[mkjsf-moved-to-github.git] / src / main / java / com / indexdata / mkjsf / pazpar2 / commands / SearchCommand.java
1 package com.indexdata.mkjsf.pazpar2.commands;\r
2 \r
3 import java.util.List;\r
4 \r
5 import javax.enterprise.context.SessionScoped;\r
6 import javax.inject.Named;\r
7 \r
8 import org.apache.log4j.Logger;\r
9 \r
10 import com.indexdata.mkjsf.pazpar2.Pz2Service;\r
11 import com.indexdata.mkjsf.pazpar2.commands.sp.ServiceProxyCommand;\r
12 import com.indexdata.mkjsf.pazpar2.data.ResponseDataObject;\r
13 \r
14 @SessionScoped @Named\r
15 public class SearchCommand extends Pazpar2Command implements ServiceProxyCommand {\r
16   \r
17   private static final long serialVersionUID = -1888520867838597236L;\r
18   private static Logger logger = Logger.getLogger(SearchCommand.class);\r
19   private SingleTargetFilter singleTargetFilter = null;\r
20     \r
21   public SearchCommand() {\r
22     super("search");\r
23   }\r
24   \r
25   public ResponseDataObject run() {\r
26     logger.info("Running " + getCommandName());\r
27     Pz2Service.get().getStateMgr().hasPendingStateChange("search",false);\r
28     Pz2Service.get().getPzresp().resetSearchAndBeyond();\r
29     Pz2Service.get().getPzreq().getRecord().removeParametersInState();        \r
30     Pz2Service.get().getPzreq().getShow().setParameterInState(new CommandParameter("start","=",0));    \r
31     Pz2Service.get().getSearchClient().setSearchCommand(this);\r
32     return super.run();\r
33   }\r
34     \r
35   public void setQuery(String query) {    \r
36     setParameter(new CommandParameter("query","=",query));\r
37   }\r
38   \r
39   public String getQuery () {    \r
40     return getParameter("query") == null ? null  : getParameter("query").getValueWithExpressions();\r
41   }\r
42   \r
43   public void setFilter(String filterExpression) {\r
44     if (filterExpression != null && filterExpression.length()>0) {\r
45       setParameter(new FilterParameter(new Expression(filterExpression)));\r
46     }\r
47   }\r
48   \r
49   public void setFilter(String field, String operator, String value, String label) {\r
50     setParameter(new FilterParameter(new Expression(field,operator,value,label)));\r
51   }\r
52   \r
53   public String getFilter() {\r
54     return getParameter("filter") == null ? null : ((FilterParameter)getParameter("filter")).getValueWithExpressions();\r
55   }\r
56   \r
57   public List<Expression> getFilters() {\r
58     return getParameter("filter").getExpressions();\r
59   }\r
60   \r
61   public void addFilter(String field, String operator, String value, String label) {\r
62     if (getParameter("filter") == null) {\r
63       setFilter(field + operator + value);\r
64     } else {\r
65       getParameter("filter").addExpression(new Expression(field,operator,value,(label != null ? label : value)));\r
66     }\r
67   }\r
68   \r
69   public void removeFilters () {\r
70     removeParameter("filter");\r
71   }\r
72   \r
73   public void removeFilter(String field, String operator, String value) {\r
74     removeExpression("filter",new Expression(field, operator, value, null));\r
75   }\r
76   \r
77   public void removeFiltersAfter(String field, String operator, String value) {\r
78     removeExpressionsAfter("filter",new Expression(field,operator,value,null));\r
79   }\r
80   \r
81   public boolean hasFilter () {\r
82     return getFilter().length()>0;\r
83   }\r
84   \r
85   public void setLimit (String limitExpression) {   \r
86     if (limitExpression != null && limitExpression.length()>0) {\r
87       setParameter(new LimitParameter(new Expression(limitExpression)));\r
88     }\r
89   }\r
90   \r
91   public void setLimit(String field, String operator, String value, String label) {\r
92     setParameter(new LimitParameter(new Expression(field,operator,value,label)));\r
93   }\r
94       \r
95   public String getLimit () {\r
96     return getParameter("limit") == null ? null : ((FilterParameter)getParameter("limit")).getValueWithExpressions();    \r
97   }\r
98   \r
99   public List<Expression> getLimitExpressions() {\r
100     return getParameter("limit").getExpressions();\r
101   }\r
102   \r
103   public boolean hasLimitExpression(String... expressionFields) {\r
104     logger.trace("Checking for limit expression for " + expressionFields);\r
105     for (String field : expressionFields) {\r
106       if (getLimitExpressions(field) != null && getLimitExpressions(field).size()>0) {\r
107         logger.trace("Limit expression found (" + field + ")");\r
108         return true;\r
109       }  \r
110     }\r
111     logger.trace("No limit expressions found");\r
112     return false;\r
113   }\r
114   \r
115   public Expression getOneLimitExpression(String expressionField) {\r
116     List<Expression> exprs = getLimitExpressions(expressionField);\r
117     if (exprs != null && exprs.size()>0) {\r
118       if (exprs.size()>1) {\r
119         logger.warn("More that one limit expression found for [" + expressionField + "] but only asked to return the first one");\r
120       }\r
121       return exprs.get(0);\r
122     } else {\r
123       return null;\r
124     }\r
125     \r
126   }\r
127   \r
128   public List<Expression> getLimitExpressions(String... expressionFields) {\r
129     logger.trace("Checking for limit parameter");\r
130     if (parameters.get("limit")!=null) {\r
131       logger.trace("Found");\r
132       return getParameter("limit").getExpressions(expressionFields);\r
133     } else {\r
134       logger.trace("Not found");\r
135       return null;\r
136     }\r
137   }\r
138   \r
139   public void addLimit(String field, String operator, String value, String label) {\r
140     if (getParameter("limit") == null) {\r
141       setLimit(field, operator, value, label);\r
142     } else {\r
143       addExpression("limit",new Expression(field,operator,value,label));\r
144       \r
145     }\r
146   }\r
147   \r
148   public void removeLimits() {\r
149     removeParameter("limit");\r
150   }\r
151   \r
152   public void removeLimits(String... fields) {    \r
153     removeExpressions("limit",fields);    \r
154   }\r
155   \r
156   public void removeLimit(String field, String operator, String value) {\r
157     removeExpression("limit",new Expression(field, operator, value, null));    \r
158   }\r
159   \r
160   public void removeLimitsAfter(String field, String operator, String value, String... fields) {     \r
161     removeExpressionsAfter("limit",new Expression(field,operator,value,null),fields);    \r
162   }\r
163 \r
164         \r
165   public void setStartrecs (String startrecs) {\r
166     setParameter(new CommandParameter("startrecs","=",startrecs));\r
167   }\r
168   \r
169   public String getStartrecs () {\r
170     return getParameterValue("startrecs");\r
171   }\r
172   \r
173   public void setMaxrecs (String maxrecs) {\r
174     setParameter(new CommandParameter("maxrecs","=",maxrecs));\r
175   }\r
176   \r
177   public String getMaxrecs () {\r
178     return getParameterValue("maxrecs");\r
179   }\r
180   \r
181   public void setSort (String sort) {\r
182     setParameter(new CommandParameter("sort","=",sort));\r
183   }\r
184   \r
185   public String getSort () {\r
186     return getParameterValue("sort");\r
187   }\r
188   \r
189   public void setRank (String rank) {\r
190     setParameter(new CommandParameter("rank","=",rank));\r
191   }\r
192   \r
193   public String getRank () {\r
194     return getParameterValue("rank");\r
195   }\r
196   \r
197   public void setMergekey (String mergekey) {\r
198     setParameter(new CommandParameter("mergekey","=",mergekey));\r
199   }\r
200   \r
201   public String getMergekey () {\r
202     return getParameterValue("mergekey");\r
203   }\r
204   \r
205   \r
206   /**\r
207    * Sets a facet, in CQL, to restrict the current results\r
208    * \r
209    * @param facetKey  i.e.  'au' for author\r
210    * @param term  i.e. 'Dickens, Charles'\r
211    */\r
212   public void setFacet(String facetKey, String term) {\r
213     if (term != null && term.length()>0) {         \r
214       getParameter("query").addExpression(new Expression(facetKey,"=",term,null));            \r
215     }            \r
216   }\r
217   \r
218   /**\r
219    * Sets a facet to limit the current query by. The \r
220    * facet is appended to the query string itself (rather\r
221    * as a separately managed entity. It will thus appear\r
222    * in a query field as retrieved by getQuery(). It will\r
223    * not be removed by removeFacet(...)\r
224    * \r
225    * @param facetKey  i.e. 'au' for author\r
226    * @param term i.e. 'Dickens, Charles'\r
227    */\r
228   public void setFacetOnQuery (String facetKey, String term) {\r
229     String facetExpression = facetKey + "=" + term;    \r
230     if (term != null && term.length()>0) {\r
231       String currentQuery= getParameterValue("query");\r
232       setParameter(new CommandParameter("query","=", currentQuery + " and " + facetExpression));      \r
233     }            \r
234   }\r
235       \r
236   /**\r
237    * Removes a facet set by setFacet(...)\r
238    * \r
239    * Will not remove facets set by setFacetOnQuery(...)\r
240    *  \r
241    * @param facetKey i.e. 'au' for author\r
242    * @param term i.e. 'Dickens, Charles'\r
243    */\r
244   public void removeFacet(String facetKey, String term) {\r
245     if (getParameter("query") != null) {\r
246       getParameter("query").removeExpression(new Expression(facetKey,"=",term,null));\r
247     }\r
248   }\r
249   \r
250   \r
251   /**\r
252    * Adds a single target filter to restrict the current query by, \r
253    * then executes the current search.\r
254    * \r
255    * This is a special case of the general setFilter function, \r
256    * allowing to associate a descriptive target name with the \r
257    * filter expression for display in UI. \r
258    * \r
259    * @param targetId pazpar2's ID for the target to limit by\r
260    * @param targetName a descriptive name for the target\r
261    */\r
262   public void setSingleTargetFilter (String targetId, String targetName) {    \r
263     if (hasSingleTargetFilter(new SingleTargetFilter(targetId,targetName))) {\r
264       logger.debug("Already using target filter " + this.singleTargetFilter.getFilterExpression());\r
265     } else {      \r
266       logger.debug("Setting new single target filter for [" + targetName + "]");\r
267       this.singleTargetFilter = new SingleTargetFilter(targetId,targetName);\r
268       setParameter(new CommandParameter("filter","=",this.singleTargetFilter.getFilterExpression()));            \r
269     }    \r
270   }\r
271 \r
272   public SingleTargetFilter getSingleTargetFilter () {\r
273     logger.debug("request to get the current single target filter " + singleTargetFilter);\r
274     return singleTargetFilter;\r
275   }\r
276    \r
277   /**\r
278    * Removes the current target filter from the search\r
279    * \r
280    */\r
281   public String removeSingleTargetFilter () {\r
282     logger.debug("Removing target filter " + singleTargetFilter.getFilterExpression());\r
283     this.singleTargetFilter = null;\r
284     removeParameter("filter");\r
285     return null;\r
286   }\r
287   \r
288   /**\r
289    * \r
290    * @return The target filter set on the current search command\r
291    */\r
292   public boolean hasSingleTargetFilter() {\r
293     logger.debug("Checking if a single target filter is set: " + (singleTargetFilter != null));\r
294     return singleTargetFilter != null;    \r
295   }\r
296   \r
297   /**\r
298    * Resolves if the current search command has a target filter - to\r
299    * be used by the UI for conditional rendering of target filter info.\r
300    * \r
301    * @return true if the current search command is limited by a target \r
302    * filter\r
303    */\r
304   protected boolean hasSingleTargetFilter(SingleTargetFilter targetFilter) {\r
305     logger.debug("Checking if target filter for [" + targetFilter.getTargetName() + "] is set.");\r
306     return hasSingleTargetFilter() && targetFilter.equals(this.singleTargetFilter);\r
307   }\r
308     \r
309   public SearchCommand copy () {\r
310     SearchCommand newCommand = new SearchCommand();\r
311     for (String parameterName : parameters.keySet()) {\r
312       newCommand.setParameterInState(parameters.get(parameterName).copy());      \r
313     }\r
314     newCommand.singleTargetFilter = this.singleTargetFilter;\r
315     return newCommand;\r
316   }\r
317 \r
318   @Override\r
319   public ServiceProxyCommand getSp() {\r
320     return this;\r
321   }\r
322 \r
323   @Override\r
324   public boolean spOnly() {\r
325     return false;\r
326   }\r
327 \r
328 }\r