001/** 002 * Copyright 2005-2017 The Kuali Foundation 003 * 004 * Licensed under the Educational Community License, Version 2.0 (the "License"); 005 * you may not use this file except in compliance with the License. 006 * You may obtain a copy of the License at 007 * 008 * http://www.opensource.org/licenses/ecl2.php 009 * 010 * Unless required by applicable law or agreed to in writing, software 011 * distributed under the License is distributed on an "AS IS" BASIS, 012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 013 * See the License for the specific language governing permissions and 014 * limitations under the License. 015 */ 016package org.kuali.rice.kim.lookup; 017 018import org.apache.commons.collections.CollectionUtils; 019import org.apache.commons.lang.StringUtils; 020import org.kuali.rice.core.api.criteria.Predicate; 021import org.kuali.rice.core.api.criteria.PredicateUtils; 022import org.kuali.rice.core.api.criteria.QueryByCriteria; 023import org.kuali.rice.core.api.util.ConcreteKeyValue; 024import org.kuali.rice.core.api.util.KeyValue; 025import org.kuali.rice.core.web.format.BooleanFormatter; 026import org.kuali.rice.core.web.format.CollectionFormatter; 027import org.kuali.rice.core.web.format.DateFormatter; 028import org.kuali.rice.core.web.format.Formatter; 029import org.kuali.rice.kew.api.KewApiConstants; 030import org.kuali.rice.kim.api.KimConstants; 031import org.kuali.rice.kim.api.group.Group; 032import org.kuali.rice.kim.api.group.GroupQueryResults; 033import org.kuali.rice.kim.api.identity.Person; 034import org.kuali.rice.kim.api.identity.principal.Principal; 035import org.kuali.rice.kim.api.identity.principal.PrincipalQueryResults; 036import org.kuali.rice.kim.api.services.KimApiServiceLocator; 037import org.kuali.rice.kim.api.type.KimAttributeField; 038import org.kuali.rice.kim.api.type.KimType; 039import org.kuali.rice.kim.framework.services.KimFrameworkServiceLocator; 040import org.kuali.rice.kim.framework.type.KimTypeService; 041import org.kuali.rice.kim.impl.KIMPropertyConstants; 042import org.kuali.rice.kim.impl.group.GroupBo; 043import org.kuali.rice.kim.impl.type.KimTypeLookupableHelperServiceImpl; 044import org.kuali.rice.kim.util.KimCommonUtilsInternal; 045import org.kuali.rice.kns.document.authorization.BusinessObjectRestrictions; 046import org.kuali.rice.kns.kim.type.DataDictionaryTypeServiceHelper; 047import org.kuali.rice.kns.lookup.HtmlData; 048import org.kuali.rice.kns.web.comparator.CellComparatorHelper; 049import org.kuali.rice.kns.web.struts.form.LookupForm; 050import org.kuali.rice.kns.web.ui.Column; 051import org.kuali.rice.kns.web.ui.Field; 052import org.kuali.rice.kns.web.ui.ResultRow; 053import org.kuali.rice.kns.web.ui.Row; 054import org.kuali.rice.krad.bo.BusinessObject; 055import org.kuali.rice.krad.bo.PersistableBusinessObject; 056import org.kuali.rice.krad.data.KradDataServiceLocator; 057import org.kuali.rice.krad.datadictionary.AttributeDefinition; 058import org.kuali.rice.krad.keyvalues.IndicatorValuesFinder; 059import org.kuali.rice.krad.keyvalues.KeyValuesFinder; 060import org.kuali.rice.krad.service.KRADServiceLocatorWeb; 061import org.kuali.rice.krad.util.GlobalVariables; 062import org.kuali.rice.krad.util.KRADConstants; 063import org.kuali.rice.krad.util.UrlFactory; 064 065import java.sql.Date; 066import java.sql.Timestamp; 067import java.util.ArrayList; 068import java.util.Calendar; 069import java.util.Collection; 070import java.util.Collections; 071import java.util.Comparator; 072import java.util.HashMap; 073import java.util.Iterator; 074import java.util.List; 075import java.util.Map; 076import java.util.Properties; 077 078import static org.kuali.rice.core.api.criteria.PredicateFactory.*; 079 080public class GroupLookupableHelperServiceImpl extends KimLookupableHelperServiceImpl { 081 082 // need this so kimtypeId value can be retained in 'rows' 083 // 1st pass populate the grprows 084 // 2nd pass for jsp, no populate, so return the existing one. 085 private static final String KIM_TYPE_ID_PROPERTY_NAME = "kimTypeId"; 086 private List<Row> grpRows = new ArrayList<Row>(); 087 private List<Row> attrRows = new ArrayList<Row>(); 088 private String typeId = ""; 089 private List<KimAttributeField> attrDefinitions; 090 private final Map<String, String> groupTypeValuesCache = new HashMap<String, String>(); 091 092 @Override 093 public List<HtmlData> getCustomActionUrls(BusinessObject bo, List pkNames) { 094 GroupBo groupImpl = (GroupBo) bo; 095 List<HtmlData> anchorHtmlDataList = new ArrayList<HtmlData>(); 096 if(allowsNewOrCopyAction(KimConstants.KimUIConstants.KIM_GROUP_DOCUMENT_TYPE_NAME)){ 097 anchorHtmlDataList.add(getEditGroupUrl(groupImpl)); 098 } 099 return anchorHtmlDataList; 100 } 101 102 protected HtmlData getEditGroupUrl(GroupBo groupBo) { 103 String href = ""; 104 105 Properties parameters = new Properties(); 106 parameters.put(KRADConstants.DISPATCH_REQUEST_PARAMETER, KRADConstants.DOC_HANDLER_METHOD); 107 parameters.put(KRADConstants.PARAMETER_COMMAND, KewApiConstants.INITIATE_COMMAND); 108 parameters.put(KRADConstants.DOCUMENT_TYPE_NAME, KimConstants.KimUIConstants.KIM_GROUP_DOCUMENT_TYPE_NAME); 109 parameters.put(KimConstants.PrimaryKeyConstants.GROUP_ID, groupBo.getId()); 110 if (StringUtils.isNotBlank(getReturnLocation())) { 111 parameters.put(KRADConstants.RETURN_LOCATION_PARAMETER, getReturnLocation()); 112 } 113 href = UrlFactory.parameterizeUrl(KimCommonUtilsInternal.getKimBasePath()+KimConstants.KimUIConstants.KIM_GROUP_DOCUMENT_ACTION, parameters); 114 115 HtmlData.AnchorHtmlData anchorHtmlData = new HtmlData.AnchorHtmlData(href, 116 KRADConstants.DOC_HANDLER_METHOD, KRADConstants.MAINTENANCE_EDIT_METHOD_TO_CALL); 117 return anchorHtmlData; 118 } 119 120 /** 121 * Converts GroupInfo objects to GroupBo objects. 122 * 123 * @param fieldValues names and values returned by the Group Lookup screen 124 * @return groupImplList a list of GroupImpl objects 125 */ 126 @Override 127 public List<GroupBo> getSearchResults(java.util.Map<String,String> fieldValues) { 128 Map<String, String> criteriaMap = new HashMap<String, String>(fieldValues); 129 QueryByCriteria.Builder criteria = QueryByCriteria.Builder.create(); 130 criteriaMap.remove(KRADConstants.DOC_FORM_KEY); 131 criteriaMap.remove(KRADConstants.BACK_LOCATION); 132 criteriaMap.remove(KRADConstants.DOC_NUM); 133 String refToRef = criteriaMap.get(KRADConstants.REFERENCES_TO_REFRESH); 134 if (StringUtils.isNotBlank(refToRef) && refToRef.equalsIgnoreCase("GroupBo")) { 135 criteriaMap.remove(KRADConstants.REFERENCES_TO_REFRESH); 136 } 137 boolean validPrncplFoundIfPrncplCritPresent = true; 138 Map<String, String> attribsMap = new HashMap<String, String>(); 139 if (!criteriaMap.isEmpty()) { 140 List<Predicate> predicates = new ArrayList<Predicate>(); 141 //principalId doesn't exist on 'Group'. Lets do this predicate conversion separately 142 if (StringUtils.isNotBlank(criteriaMap.get(KimConstants.UniqueKeyConstants.PRINCIPAL_NAME))) { 143 QueryByCriteria.Builder principalCriteria = QueryByCriteria.Builder.create(); 144 Predicate principalPred = like("principalName", criteriaMap.get(KimConstants.UniqueKeyConstants.PRINCIPAL_NAME)); 145 principalCriteria.setPredicates(principalPred); 146 //String principalId = KimApiServiceLocator.getIdentityService() 147 // .getPrincipalByPrincipalName(criteriaMap.get(KimConstants.UniqueKeyConstants.PRINCIPAL_NAME)).getPrincipalId(); 148 PrincipalQueryResults principals = KimApiServiceLocator.getIdentityService() 149 .findPrincipals(principalCriteria.build()); 150 List<String> principalIds = new ArrayList<String>(); 151 for (Principal principal : principals.getResults()) { 152 principalIds.add(principal.getPrincipalId()); 153 } 154 if (CollectionUtils.isNotEmpty(principalIds)) { 155 Timestamp currentTime = new Timestamp(Calendar.getInstance().getTimeInMillis()); 156 predicates.add( and( 157 in("members.memberId", principalIds.toArray( 158 new String[principalIds.size()])), 159 equal("members.typeCode", KimConstants.KimGroupMemberTypes.PRINCIPAL_MEMBER_TYPE.getCode()), 160 and( 161 or(isNull("members.activeFromDateValue"), lessThanOrEqual("members.activeFromDateValue", currentTime)), 162 or(isNull("members.activeToDateValue"), greaterThan("members.activeToDateValue", currentTime)) 163 ) 164 )); 165 }else { 166 validPrncplFoundIfPrncplCritPresent = false; 167 } 168 169 } 170 criteriaMap.remove(KimConstants.UniqueKeyConstants.PRINCIPAL_NAME); 171 Map<String, String> criteriaCopy = new HashMap<String, String>(); 172 // copy the criteria map so we can modify it 173 criteriaCopy.putAll(criteriaMap); 174 // check the attribute definitions for attribute names 175 for(String key : criteriaCopy.keySet()) { 176 if (isParamAttribute(key)) { 177 if (StringUtils.isNotBlank(criteriaMap.get(key))) { 178 String attributeName = StringUtils.substringBetween(key, "attributes(", ")"); 179 attribsMap.put(attributeName, criteriaMap.get(key)); 180 } 181 182 // valid attribute name so remove from criteria map 183 criteriaMap.remove(key); 184 } 185 } 186 predicates.add(PredicateUtils.convertMapToPredicate(criteriaMap)); 187 criteria.setPredicates(and(predicates.toArray(new Predicate[predicates.size()]))); 188 } 189 List<Group> groups = new ArrayList<Group>(); 190 if (validPrncplFoundIfPrncplCritPresent) { 191 GroupQueryResults groupResults = KimApiServiceLocator.getGroupService().findGroups(criteria.build()); 192 groups = groupResults.getResults(); 193 } 194 195 //have to convert back to Bos 196 Map<String, GroupBo> groupBos = new HashMap<String, GroupBo>(groups.size()); 197 for (Group group : groups) { 198 // filter by any attributes 199 if (attribsMap.isEmpty()) { 200 if (groupBos.get(group.getId()) == null) { 201 groupBos.put(group.getId(), GroupBo.from(group)); 202 } 203 } else { 204 boolean containsAllAttribs = true; 205 for (String attribute : attribsMap.keySet()) { 206 containsAllAttribs &= group.getAttributes().containsKey(attribute) && 207 group.getAttributes().get(attribute).equalsIgnoreCase(attribsMap.get(attribute)); 208 } 209 if (containsAllAttribs) { 210 if (groupBos.get(group.getId()) == null) { 211 groupBos.put(group.getId(), GroupBo.from(group)); 212 } 213 } 214 } 215 } 216 217 return new ArrayList<GroupBo>(groupBos.values()); 218 } 219 220 /** 221 * Determines if the given parameter is wrapped with attributes() and the wrapped value is a non-empty 222 * <code>String</code>. 223 * @param param The string to test. 224 * @return <code>TRUE</code> if the parameter passed in is wrapped with attributes() and the wrapped value is 225 * non-empty, <code>FALSE</code> otherwise. 226 */ 227 private boolean isParamAttribute(String param) { 228 return param.matches("attributes\\((.*?)\\)") && 229 StringUtils.isNotBlank(StringUtils.substringBetween(param, "attributes(",")")) && 230 StringUtils.substringBetween(param, "attributes(",")") != "null"; 231 } 232 233 @Override 234 public boolean checkForAdditionalFields(Map<String, String> fieldValues) { 235 List<Row> attributeRows = setupAttributeRows(fieldValues); 236 if (attributeRows.isEmpty()) { 237 setAttrRows(attributeRows); 238 } else if (CollectionUtils.isEmpty(getAttrRows())) { 239 setAttrRows(attributeRows); 240 } 241 if (getAttrRows().size() > 0) { 242 return true; 243 } 244 return false; 245 } 246 247 248 @Override 249 public List<Row> getRows() { 250 if (getGrpRows().isEmpty()) { 251 List<Row> rows = super.getRows(); 252 List<Row> returnRows = new ArrayList<Row>(); 253 for (Row row : rows) { 254 for (int i = row.getFields().size() - 1; i >= 0; i--) { 255 Field field = row.getFields().get(i); 256 if (field.getPropertyName().equals(KIM_TYPE_ID_PROPERTY_NAME)) { 257 Field typeField = new Field(); 258 typeField.setFieldLabel("Type"); 259 typeField.setPropertyName(KIM_TYPE_ID_PROPERTY_NAME); 260 typeField.setFieldValidValues(getGroupTypeOptions()); 261 typeField.setFieldType(Field.DROPDOWN); 262 row.getFields().set(i, typeField); 263 } 264 } 265 returnRows.add(row); 266 } 267 // principalName 268 Field typeField = new Field(); 269 typeField.setFieldLabel("Principal Name"); 270 typeField.setPropertyName(KIMPropertyConstants.Person.PRINCIPAL_NAME); 271 typeField.setFieldType(Field.TEXT); 272 typeField.setMaxLength(40); 273 typeField.setSize(20); 274 typeField.setQuickFinderClassNameImpl("org.kuali.rice.kim.api.identity.Person"); 275 typeField.setFieldConversions( "principalName:principalName" ); 276 typeField.setLookupParameters( "principalName:principalName" ); 277 // Identify the best spot to insert the "Principal Name" search field. Note that the code below assumes that the final row of the 278 // group search fields is not a row with hidden fields; if this ever becomes the case in the future, this fix may need to 279 // be modified accordingly. 280 List<Field> fields = (returnRows.isEmpty()) ? new ArrayList<Field>() : returnRows.get(returnRows.size() - 1).getFields(); 281 if (!fields.isEmpty() && fields.get(fields.size() - 1).getFieldType().equals(Field.BLANK_SPACE)) { 282 // If the last row in the list has a BLANK_SPACE field coming after any non-BLANK_SPACE fields, add the new field to that row. 283 int insertLoc = fields.size() - 1; 284 while (insertLoc >= 0 && fields.get(insertLoc).getFieldType().equals(Field.BLANK_SPACE)) { 285 insertLoc--; 286 } 287 fields.set(insertLoc + 1, typeField); 288 returnRows.get(returnRows.size() - 1).setFields(fields); 289 } else { 290 // Otherwise, add a new row containing that field. 291 int fieldLen = fields.size(); 292 fields = new ArrayList<Field>(); 293 fields.add(typeField); 294 for (int i = 1; i < fieldLen; i++) { 295 Field blankSpace = new Field(); 296 blankSpace.setFieldType(Field.BLANK_SPACE); 297 blankSpace.setPropertyName(Field.BLANK_SPACE); 298 fields.add(blankSpace); 299 } 300 returnRows.add(new Row(fields)); 301 } 302 303 setGrpRows(returnRows); 304 } 305 if (getAttrRows().isEmpty()) { 306 setAttrDefinitions(Collections.<KimAttributeField>emptyList()); 307 return getGrpRows(); 308 } 309 List<Row> fullRows = new ArrayList<Row>(); 310 fullRows.addAll(getGrpRows()); 311 fullRows.addAll(getAttrRows()); 312 return fullRows; 313 } 314 315 316 @Override 317 public List<Column> getColumns() { 318 List<Column> columns = super.getColumns(); 319 for (Row row : attrRows) { 320 for (Field field : row.getFields()) { 321 Column newColumn = new Column(); 322 newColumn.setColumnTitle(field.getFieldLabel()); 323 newColumn.setMaxLength(getColumnMaxLength(field.getPropertyName())); 324 newColumn.setPropertyName(field.getPropertyName()); 325 newColumn.setFormatter(field.getFormatter()); 326 columns.add(newColumn); 327 } 328 } 329 return columns; 330 } 331 332 @Override 333 public Collection<GroupBo> performLookup(LookupForm lookupForm, Collection resultTable, boolean bounded) { 334 setBackLocation((String) lookupForm.getFieldsForLookup().get(KRADConstants.BACK_LOCATION)); 335 setDocFormKey((String) lookupForm.getFieldsForLookup().get(KRADConstants.DOC_FORM_KEY)); 336 List<GroupBo> displayList; 337 338 // call search method to get results 339 if (bounded) { 340 displayList = getSearchResults(lookupForm.getFieldsForLookup()); 341 } 342 else { 343 displayList = (List<GroupBo>)getSearchResultsUnbounded(lookupForm.getFieldsForLookup()); 344 } 345 346 HashMap<String,Class> propertyTypes = new HashMap<String, Class>(); 347 348 boolean hasReturnableRow = false; 349 350 List returnKeys = getReturnKeys(); 351 List pkNames = KRADServiceLocatorWeb.getLegacyDataAdapter().listPrimaryKeyFieldNames(getBusinessObjectClass()); 352 Person user = GlobalVariables.getUserSession().getPerson(); 353 354 // iterate through result list and wrap rows with return url and action urls 355 for (Iterator iter = displayList.iterator(); iter.hasNext();) { 356 BusinessObject element = (BusinessObject) iter.next(); 357 if(element instanceof PersistableBusinessObject){ 358 lookupForm.setLookupObjectId(((PersistableBusinessObject)element).getObjectId()); 359 } 360 361 BusinessObjectRestrictions businessObjectRestrictions = getBusinessObjectAuthorizationService().getLookupResultRestrictions(element, user); 362 363 HtmlData returnUrl = getReturnUrl(element, lookupForm, returnKeys, businessObjectRestrictions); 364 365 String actionUrls = getActionUrls(element, pkNames, businessObjectRestrictions); 366 //Fix for JIRA - KFSMI-2417 367 if("".equals(actionUrls)){ 368 actionUrls = ACTION_URLS_EMPTY; 369 } 370 371 List<Column> columns = getColumns(); 372 for (Object element2 : columns) { 373 374 Column col = (Column) element2; 375 Formatter formatter = col.getFormatter(); 376 377 // pick off result column from result list, do formatting 378 String propValue = KRADConstants.EMPTY_STRING; 379 Object prop = null; 380 if (col.getPropertyName().matches("\\w+\\.\\d+$")) { 381 String id = col.getPropertyName().substring(col.getPropertyName().lastIndexOf('.') + 1); //.split("\\d+$"))[1]; 382 prop = ((GroupBo)element).getGroupAttributeValueById(id); 383 } 384 if (prop == null) { 385 prop = (String) KradDataServiceLocator.getDataObjectService().wrap(element) 386 .getPropertyValueNullSafe(findAndConvertAttributeNamesToMappableProperty(col.getPropertyName())); 387 } else { 388 } 389 390 // set comparator and formatter based on property type 391 Class propClass = propertyTypes.get(col.getPropertyName()); 392 if ( propClass == null /*&& !skipPropTypeCheck*/) { 393 try { 394 propClass = KRADServiceLocatorWeb.getLegacyDataAdapter().getPropertyType(element, 395 col.getPropertyName()); 396 propertyTypes.put( col.getPropertyName(), propClass ); 397 } catch (Exception e) { 398 throw new RuntimeException("Cannot access PropertyType for property " + "'" + col.getPropertyName() + "' " + " on an instance of '" + element.getClass().getName() + "'.", e); 399 } 400 } 401 402 // formatters 403 if (prop != null) { 404 // for Booleans, always use BooleanFormatter 405 if (prop instanceof Boolean) { 406 formatter = new BooleanFormatter(); 407 } 408 409 // for Dates, always use DateFormatter 410 if (prop instanceof Date) { 411 formatter = new DateFormatter(); 412 } 413 414 // for collection, use the list formatter if a formatter hasn't been defined yet 415 if (prop instanceof Collection && formatter == null) { 416 formatter = new CollectionFormatter(); 417 } 418 419 if (formatter != null) { 420 propValue = (String) formatter.format(prop); 421 } 422 else { 423 propValue = prop.toString(); 424 if (col.getPropertyName().equals(KIM_TYPE_ID_PROPERTY_NAME)) { 425 propValue = groupTypeValuesCache.get(prop.toString()); 426 } 427 } 428 } 429 430 // comparator 431 col.setComparator(CellComparatorHelper.getAppropriateComparatorForPropertyClass(propClass)); 432 col.setValueComparator(CellComparatorHelper.getAppropriateValueComparatorForPropertyClass(propClass)); 433 434 propValue = maskValueIfNecessary(element.getClass(), col.getPropertyName(), propValue, businessObjectRestrictions); 435 436 col.setPropertyValue(propValue); 437 438 if (StringUtils.isNotBlank(propValue)) { 439 col.setColumnAnchor(getInquiryUrl(element, col.getPropertyName())); 440 441 } 442 } 443 444 ResultRow row = new ResultRow(columns, returnUrl.constructCompleteHtmlTag(), actionUrls); 445 row.setRowId(returnUrl.getName()); 446 row.setReturnUrlHtmlData(returnUrl); 447 // because of concerns of the BO being cached in session on the ResultRow, 448 // let's only attach it when needed (currently in the case of export) 449 if (getBusinessObjectDictionaryService().isExportable(getBusinessObjectClass())) { 450 row.setBusinessObject(element); 451 } 452 if(element instanceof PersistableBusinessObject){ 453 row.setObjectId((((PersistableBusinessObject)element).getObjectId())); 454 } 455 456 457 boolean rowReturnable = isResultReturnable(element); 458 row.setRowReturnable(rowReturnable); 459 if (rowReturnable) { 460 hasReturnableRow = true; 461 } 462 resultTable.add(row); 463 } 464 465 lookupForm.setHasReturnableRow(hasReturnableRow); 466 467 return displayList; 468 } 469 470 471 private List<KeyValue> getGroupTypeOptions() { 472 List<KeyValue> options = new ArrayList<KeyValue>(); 473 options.add(new ConcreteKeyValue("", "")); 474 475 Collection<KimType> kimGroupTypes = KimApiServiceLocator.getKimTypeInfoService().findAllKimTypes(); 476 // get the distinct list of type IDs from all groups in the system 477 for (KimType kimType : kimGroupTypes) { 478 if (KimTypeLookupableHelperServiceImpl.hasGroupTypeService(kimType) && groupTypeValuesCache.get(kimType.getId()) == null) { 479 String value = kimType.getNamespaceCode().trim() + KRADConstants.FIELD_CONVERSION_PAIR_SEPARATOR + kimType.getName().trim(); 480 options.add(new ConcreteKeyValue(kimType.getId(), value)); 481 } 482 } 483 Collections.sort(options, new Comparator<KeyValue>() { 484 @Override 485 public int compare(KeyValue k1, KeyValue k2) { 486 return k1.getValue().compareTo(k2.getValue()); 487 } 488 }); 489 return options; 490 } 491 492 private List<Row> setupAttributeRows(Map fieldValues) { 493 List<Row> returnRows = new ArrayList<Row>(); 494 for (Row row : getGrpRows()) { 495 Field field = row.getFields().get(0); 496 if (field.getPropertyName().equals(KIM_TYPE_ID_PROPERTY_NAME) && StringUtils.isNotBlank(field.getPropertyValue())) { 497 if (!StringUtils.isBlank(getTypeId()) || !getTypeId().equals(field.getPropertyValue())) { 498 setTypeId(field.getPropertyValue()); 499 setAttrRows(new ArrayList<Row>()); 500 KimType kimType = getTypeInfoService().getKimType( field.getPropertyValue() ); 501 KimTypeService kimTypeService = KimFrameworkServiceLocator.getKimTypeService(kimType); 502 List<KimAttributeField> definitions = kimTypeService.getAttributeDefinitions(kimType.getId()); 503 setAttrDefinitions(definitions); 504 for (KimAttributeField d : definitions) { 505 final AttributeDefinition definition = DataDictionaryTypeServiceHelper 506 .toKimAttributeDefinition(d); 507 List<Field> fields = new ArrayList<Field>(); 508 Field typeField = new Field(); 509 510 String attrDefnId = d.getId(); 511 typeField.setFieldLabel(definition.getLabel()); 512 typeField.setPropertyName("attributes(" + definition.getName()+")"); 513 typeField.setPropertyValue(fieldValues.get(typeField.getPropertyName())); 514 if (definition.getControl().isSelect()) { 515 typeField.setFieldValidValues(definition.getOptionsFinder().getKeyValues()); 516 typeField.setFieldType(Field.DROPDOWN); 517 } else if (definition.getControl().isText()){ 518 typeField.setMaxLength(definition.getMaxLength()); 519 if (definition.getControl().getSize() != null) { 520 typeField.setSize(definition.getControl().getSize()); 521 } 522 typeField.setFieldType(Field.TEXT); 523 } else if (definition.getControl().isRadio()) { 524 typeField.setFieldValidValues(definition.getOptionsFinder().getKeyValues()); 525 typeField.setFieldType(Field.RADIO); 526 } else if (definition.getControl().isCheckbox()) { 527 KeyValuesFinder finder = new IndicatorValuesFinder(); 528 typeField.setFieldValidValues(finder.getKeyValues()); 529 typeField.setFieldType(Field.RADIO); 530 //typeField.setFieldType(Field.CHECKBOX); 531 } else if (definition.getControl().isHidden()) { 532 typeField.setFieldType(Field.HIDDEN); 533 } else if (definition.getControl().isLookupReadonly()) { 534 typeField.setFieldType(Field.LOOKUP_READONLY); 535 } else if (definition.getControl().isTextarea()) { 536 typeField.setMaxLength(definition.getMaxLength()); 537 if (definition.getControl().getSize() != null) { 538 typeField.setSize(definition.getControl().getSize()); 539 } 540 typeField.setFieldType(Field.TEXT_AREA); 541 } 542 fields.add(typeField); 543 returnRows.add(new Row(fields)); 544 } 545 } else { 546 return getAttrRows(); 547 } 548 } else if (field.getPropertyName().equals(KIM_TYPE_ID_PROPERTY_NAME) && StringUtils.isBlank(field.getPropertyValue())) { 549 setTypeId(""); 550 } 551 } 552 return returnRows; 553 } 554 555 public List<Row> getGrpRows() { 556 return this.grpRows; 557 } 558 559 public void setGrpRows(List<Row> grpRows) { 560 this.grpRows = grpRows; 561 } 562 563 public List<KimAttributeField> getAttrDefinitions() { 564 return this.attrDefinitions; 565 } 566 567 public void setAttrDefinitions(List<KimAttributeField> attrDefinitions) { 568 this.attrDefinitions = attrDefinitions; 569 } 570 571 public List<Row> getAttrRows() { 572 return this.attrRows; 573 } 574 575 public void setAttrRows(List<Row> attrRows) { 576 this.attrRows = attrRows; 577 } 578 579 public String getTypeId() { 580 return this.typeId; 581 } 582 583 public void setTypeId(String typeId) { 584 this.typeId = typeId; 585 } 586 587 /** 588 * This method determines if a property name refers to an attribute. If so, we have to adjust the formatting so the 589 * wrapper recognizes it as being mappable. 590 * @param propertyName is any property name that will be wrapped as part of a lookup result 591 * @return either the unaltered property name or a modified version of the property name if it is an attribute 592 */ 593 private String findAndConvertAttributeNamesToMappableProperty(String propertyName) { 594 if (isParamAttribute(propertyName)) { 595 return propertyName.replaceAll("attributes\\((.*?)\\)", "attributes\\[$1\\]"); 596 } else { 597 return propertyName; 598 } 599 } 600 601 @Override 602 public void performClear(LookupForm lookupForm) { 603 super.performClear(lookupForm); 604 this.attrRows = new ArrayList<Row>(); 605 } 606 607}