1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16 package org.kuali.rice.krad.uif.service.impl;
17
18 import org.apache.commons.lang.StringUtils;
19 import org.kuali.rice.core.api.config.property.ConfigurationService;
20 import org.kuali.rice.krad.service.KRADServiceLocator;
21 import org.kuali.rice.krad.service.KRADServiceLocatorWeb;
22 import org.kuali.rice.krad.service.LookupService;
23 import org.kuali.rice.krad.uif.UifConstants;
24 import org.kuali.rice.krad.uif.view.View;
25 import org.kuali.rice.krad.uif.component.MethodInvokerConfig;
26 import org.kuali.rice.krad.uif.field.InputField;
27 import org.kuali.rice.krad.uif.field.AttributeQuery;
28 import org.kuali.rice.krad.uif.field.AttributeQueryResult;
29 import org.kuali.rice.krad.uif.service.AttributeQueryService;
30 import org.kuali.rice.krad.uif.util.ObjectPropertyUtils;
31 import org.kuali.rice.krad.uif.widget.Suggest;
32 import org.kuali.rice.krad.util.BeanPropertyComparator;
33
34 import java.text.MessageFormat;
35 import java.util.ArrayList;
36 import java.util.Collection;
37 import java.util.Collections;
38 import java.util.HashMap;
39 import java.util.List;
40 import java.util.Map;
41
42
43
44
45
46
47
48 public class AttributeQueryServiceImpl implements AttributeQueryService {
49
50 private LookupService lookupService;
51 private ConfigurationService configurationService;
52
53
54
55
56
57
58 @Override
59 public AttributeQueryResult performFieldSuggestQuery(View view, String fieldId, String fieldTerm,
60 Map<String, String> queryParameters) {
61 AttributeQueryResult queryResult = new AttributeQueryResult();
62
63
64 InputField inputField = (InputField) view.getViewIndex().getComponentById(fieldId);
65 if (inputField == null) {
66 throw new RuntimeException("Unable to find attribute field instance for id: " + fieldId);
67 }
68
69 Suggest fieldSuggest = inputField.getFieldSuggest();
70 AttributeQuery suggestQuery = fieldSuggest.getSuggestQuery();
71
72
73 Map<String, String> additionalCriteria = new HashMap<String, String>();
74 additionalCriteria.put(fieldSuggest.getSourcePropertyName(), fieldTerm + "*");
75
76
77 Collection<?> results = null;
78 if (suggestQuery.hasConfiguredMethod()) {
79 Object queryMethodResult = executeAttributeQueryMethod(view, suggestQuery, queryParameters);
80 if ((queryMethodResult != null) && (queryMethodResult instanceof Collection<?>)) {
81 results = (Collection<?>) queryMethodResult;
82 }
83 } else {
84 results = executeAttributeQueryCriteria(suggestQuery, queryParameters, additionalCriteria);
85 }
86
87
88 if (results != null) {
89 List<String> suggestData = new ArrayList<String>();
90 for (Object result : results) {
91 Object suggestFieldValue =
92 ObjectPropertyUtils.getPropertyValue(result, fieldSuggest.getSourcePropertyName());
93 if (suggestFieldValue != null) {
94
95 suggestData.add(suggestFieldValue.toString());
96 }
97 }
98
99 queryResult.setResultData(suggestData);
100 }
101
102 return queryResult;
103 }
104
105
106
107
108
109 @Override
110 public AttributeQueryResult performFieldQuery(View view, String fieldId, Map<String, String> queryParameters) {
111 AttributeQueryResult queryResult = new AttributeQueryResult();
112
113
114 InputField inputField = (InputField) view.getViewIndex().getComponentById(fieldId);
115 if (inputField == null) {
116 throw new RuntimeException("Unable to find attribute field instance for id: " + fieldId);
117 }
118
119 AttributeQuery fieldQuery = inputField.getFieldAttributeQuery();
120 if (fieldQuery == null) {
121 throw new RuntimeException("Field query not defined for field instance with id: " + fieldId);
122 }
123
124
125 Object resultObject = null;
126 if (fieldQuery.hasConfiguredMethod()) {
127 Object queryMethodResult = executeAttributeQueryMethod(view, fieldQuery, queryParameters);
128 if (queryMethodResult != null) {
129
130 if (queryMethodResult instanceof AttributeQueryResult) {
131 return (AttributeQueryResult) queryMethodResult;
132 }
133
134
135 if (queryMethodResult instanceof Collection<?>) {
136 Collection<?> methodResultCollection = (Collection<?>) queryMethodResult;
137 if (!methodResultCollection.isEmpty()) {
138 resultObject = methodResultCollection.iterator().next();
139 }
140 } else {
141 resultObject = queryMethodResult;
142 }
143 }
144 } else {
145
146 Collection<?> results = executeAttributeQueryCriteria(fieldQuery, queryParameters, null);
147
148 if ((results != null) && !results.isEmpty()) {
149
150 if (results.size() > 1) {
151
152 resultObject = null;
153 }
154 else{
155 resultObject = results.iterator().next();
156 }
157 }
158 }
159
160 if (resultObject != null) {
161
162 Map<String, String> resultFieldData = new HashMap<String, String>();
163 for (String fromField : fieldQuery.getReturnFieldMapping().keySet()) {
164 String returnField = fieldQuery.getReturnFieldMapping().get(fromField);
165
166 String fieldValueStr = "";
167 Object fieldValue = ObjectPropertyUtils.getPropertyValue(resultObject, fromField);
168 if (fieldValue != null) {
169 fieldValueStr = fieldValue.toString();
170 }
171 resultFieldData.put(returnField, fieldValueStr);
172 }
173 queryResult.setResultFieldData(resultFieldData);
174
175 fieldQuery.setReturnMessageText("");
176 } else {
177
178 if (fieldQuery.isRenderNotFoundMessage()) {
179 String messageTemplate =
180 getConfigurationService().getPropertyValueAsString(
181 UifConstants.MessageKeys.QUERY_DATA_NOT_FOUND);
182 String message = MessageFormat.format(messageTemplate, inputField.getLabel());
183 fieldQuery.setReturnMessageText(message.toLowerCase());
184 }
185 }
186
187
188 queryResult.setResultMessage(fieldQuery.getReturnMessageText());
189 queryResult.setResultMessageStyleClasses(fieldQuery.getReturnMessageStyleClasses());
190
191 return queryResult;
192 }
193
194
195
196
197
198
199
200
201
202
203 protected Object executeAttributeQueryMethod(View view, AttributeQuery attributeQuery,
204 Map<String, String> queryParameters) {
205 String queryMethodToCall = attributeQuery.getQueryMethodToCall();
206 MethodInvokerConfig queryMethodInvoker = attributeQuery.getQueryMethodInvokerConfig();
207
208 if (queryMethodInvoker == null) {
209 queryMethodInvoker = new MethodInvokerConfig();
210 }
211
212
213
214 if (StringUtils.isBlank(queryMethodInvoker.getTargetMethod())) {
215 queryMethodInvoker.setTargetMethod(queryMethodToCall);
216 }
217
218
219 if ((queryMethodInvoker.getTargetClass() == null) && (queryMethodInvoker.getTargetObject() == null)) {
220 queryMethodInvoker.setTargetObject(view.getViewHelperService());
221 }
222
223
224 Object[] arguments = null;
225 if ((attributeQuery.getQueryMethodArgumentFieldList() != null) &&
226 (!attributeQuery.getQueryMethodArgumentFieldList().isEmpty())) {
227
228 Class[] argumentTypes = queryMethodInvoker.getArgumentTypes();
229 if ((argumentTypes == null) ||
230 (argumentTypes.length != attributeQuery.getQueryMethodArgumentFieldList().size())) {
231 throw new RuntimeException(
232 "Query method argument field list size does not match found method argument list size");
233 }
234
235 arguments = new Object[attributeQuery.getQueryMethodArgumentFieldList().size()];
236 for (int i = 0; i < attributeQuery.getQueryMethodArgumentFieldList().size(); i++) {
237 String methodArgumentFromField = attributeQuery.getQueryMethodArgumentFieldList().get(i);
238 if (queryParameters.containsKey(methodArgumentFromField)) {
239 arguments[i] = queryParameters.get(methodArgumentFromField);
240 } else {
241 arguments[i] = null;
242 }
243 }
244 }
245 queryMethodInvoker.setArguments(arguments);
246
247 try {
248 queryMethodInvoker.prepare();
249
250 return queryMethodInvoker.invoke();
251 } catch (Exception e) {
252 throw new RuntimeException("Unable to invoke query method: " + queryMethodInvoker.getTargetMethod(), e);
253 }
254 }
255
256
257
258
259
260
261
262
263
264
265 protected Collection<?> executeAttributeQueryCriteria(AttributeQuery attributeQuery,
266 Map<String, String> queryParameters, Map<String, String> additionalCriteria) {
267 Collection<?> results = null;
268
269
270 Map<String, String> queryCriteria = new HashMap<String, String>();
271 for (String fieldName : attributeQuery.getQueryFieldMapping().values()) {
272 if (queryParameters.containsKey(fieldName) && StringUtils.isNotBlank(queryParameters.get(fieldName))) {
273 queryCriteria.put(fieldName, queryParameters.get(fieldName));
274 }
275 }
276
277
278 for (String fieldName : attributeQuery.getAdditionalCriteria().keySet()) {
279 queryCriteria.put(fieldName, attributeQuery.getAdditionalCriteria().get(fieldName));
280 }
281
282
283 if (additionalCriteria != null) {
284 queryCriteria.putAll(additionalCriteria);
285 }
286
287 Class<?> queryClass = null;
288 try {
289 queryClass = Class.forName(attributeQuery.getDataObjectClassName());
290 } catch (ClassNotFoundException e) {
291 throw new RuntimeException(
292 "Invalid data object class given for suggest query: " + attributeQuery.getDataObjectClassName(), e);
293 }
294
295
296 results = getLookupService().findCollectionBySearchUnbounded(queryClass, queryCriteria);
297
298
299 if (!attributeQuery.getSortPropertyNames().isEmpty() && (results != null) && (results.size() > 1)) {
300 Collections.sort((List<?>) results, new BeanPropertyComparator(attributeQuery.getSortPropertyNames()));
301 }
302
303 return results;
304 }
305
306 protected LookupService getLookupService() {
307 if (lookupService == null) {
308 lookupService = KRADServiceLocatorWeb.getLookupService();
309 }
310
311 return lookupService;
312 }
313
314 public void setLookupService(LookupService lookupService) {
315 this.lookupService = lookupService;
316 }
317
318 protected ConfigurationService getConfigurationService() {
319 if (configurationService == null) {
320 configurationService = KRADServiceLocator.getKualiConfigurationService();
321 }
322
323 return configurationService;
324 }
325
326 public void setConfigurationService(ConfigurationService configurationService) {
327 this.configurationService = configurationService;
328 }
329 }