1 /** 2 * Copyright 2005-2014 The Kuali Foundation 3 * 4 * Licensed under the Educational Community License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.opensource.org/licenses/ecl2.php 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 package org.kuali.rice.krad.uif.service; 17 18 import java.util.List; 19 import java.util.Map; 20 21 import org.kuali.rice.krad.uif.component.Component; 22 import org.kuali.rice.krad.uif.container.CollectionGroup; 23 import org.kuali.rice.krad.uif.container.Container; 24 import org.kuali.rice.krad.uif.field.DataField; 25 import org.kuali.rice.krad.uif.util.ComponentFactory; 26 import org.kuali.rice.krad.uif.view.ExpressionEvaluatorFactory; 27 import org.kuali.rice.krad.uif.util.LifecycleElement; 28 import org.kuali.rice.krad.uif.view.ViewModel; 29 import org.kuali.rice.krad.uif.widget.Inquiry; 30 31 /** 32 * Provides methods for implementing the various phases of a <code>View</code> 33 * 34 * <ul> 35 * <li>Initialize Phase: Invoked when the view is first requested to setup 36 * necessary state</li> 37 * </ul> 38 * 39 * @author Kuali Rice Team (rice.collab@kuali.org) 40 */ 41 public interface ViewHelperService { 42 43 /** 44 * Hook for service overrides to perform custom initialization prior to view initialization. 45 * 46 * @param model The model. 47 */ 48 void performCustomViewInitialization(Object model); 49 50 /** 51 * Hook for service overrides to perform custom initialization on the component 52 * 53 * @param component component instance to initialize 54 */ 55 void performCustomInitialization(LifecycleElement component); 56 57 /** 58 * Hook for service overrides to perform custom apply model logic on the component 59 * 60 * @param component component instance to apply model to 61 * @param model Top level object containing the data (could be the model or a top level business 62 * object, dto) 63 */ 64 void performCustomApplyModel(LifecycleElement component, Object model); 65 66 /** 67 * Hook for service overrides to perform custom component finalization 68 * 69 * @param component component instance to update 70 * @param model Top level object containing the data 71 * @param parent Parent component for the component being finalized 72 */ 73 void performCustomFinalize(LifecycleElement component, Object model, LifecycleElement parent); 74 75 /** 76 * Hook for service overrides to perform view component finalization 77 * 78 * @param model Top level object containing the data 79 */ 80 void performCustomViewFinalize(Object model); 81 82 /** 83 * Hook for service overrides to process the new collection line before it is added to the 84 * collection 85 * 86 * @param model object instance that contain's the view's data 87 * @param addLine the new line instance to be processed 88 * @param collectionId the id of the collection being added to 89 * @param collectionPath the path to the collection being modified 90 */ 91 void processBeforeAddLine(ViewModel model, Object addLine, String collectionId, String collectionPath); 92 93 /** 94 * Hook for service overrides to process the new collection line after it has been added to the 95 * collection 96 * 97 * @param model object instance that contain's the views data 98 * @param addLine the new line that was added 99 * @param collectionId the id of the collection being added to 100 * @param collectionPath the path to the collection being modified 101 * @param isValidLine indicates if the line is valid 102 */ 103 void processAfterAddLine(ViewModel model, Object addLine, String collectionId, String collectionPath, 104 boolean isValidLine); 105 106 /** 107 * Hook for service overrides to process the save collection line before it is validated 108 * 109 * @param model object instance that contain's the views data 110 * @param lineObject the line instance to be processed 111 * @param collectionId the id of the collection being added to 112 * @param collectionPath the path to the collection being modified 113 */ 114 void processBeforeSaveLine(ViewModel model, Object lineObject, String collectionId, String collectionPath); 115 116 /** 117 * Hook for service overrides to process the save collection line after it has been validated 118 * 119 * @param model object instance that contains the views data 120 * @param lineObject the line instance to be processed 121 * @param collectionId the id of the collection being added to 122 * @param collectionPath the path to the collection being modified 123 */ 124 void processAfterSaveLine(ViewModel model, Object lineObject, String collectionId, String collectionPath); 125 126 /** 127 * Hook for service overrides to process the collection line after it has been deleted 128 * 129 * @param model object instance that contains the views data 130 * @param collectionId the id of the collection being added to 131 * @param collectionPath the path to the collection being modified 132 * @param lineIndex index of the line that was deleted 133 */ 134 void processAfterDeleteLine(ViewModel model, String collectionId, String collectionPath, int lineIndex); 135 136 /** 137 * Hook for creating new components with code and adding them to a container 138 * 139 * <p> 140 * Subclasses can override this method to check for one or more containers by id and then adding 141 * components created in code. This is invoked before the initialize method on the container 142 * component, so the full lifecycle will be run on the components returned. 143 * </p> 144 * 145 * <p> 146 * New components instances can be retrieved using {@link ComponentFactory} 147 * </p> 148 * 149 * @param model object containing the view data 150 * @param container container instance to add components to 151 */ 152 void addCustomContainerComponents(ViewModel model, Container container); 153 154 /** 155 * Invoked when the add line action is chosen for a collection. The 156 * collection path gives the full path to the collection that action was 157 * selected for. Here validation can be performed on the line as well as 158 * further processing on the line such as defaults. If the action is valid 159 * the line should be added to the collection, otherwise errors should be 160 * added to the global <code>MessageMap</code> 161 * 162 * @param model Top level object containing the view data including the 163 * collection and new line 164 * @param collectionId the id of the collection being added to 165 * @param collectionPath the path to the collection being modified 166 */ 167 void processCollectionAddLine(ViewModel model, String collectionId, String collectionPath); 168 169 /** 170 * Adds a blank line to the collection 171 * 172 * <p> 173 * Adds a new collection item to the collection and applies any default values. 174 * </p> 175 * 176 * @param model Top level object containing the view data including the collection and new line 177 * @param collectionId the id of the collection being added to 178 * @param collectionPath the path to the collection being modified 179 */ 180 void processCollectionAddBlankLine(ViewModel model, String collectionId, String collectionPath); 181 182 /** 183 * Invoked when the save line action is chosen for a collection. This method only does server side validation by 184 * default but creates hook for client applications to add additional logic like persisting data. 185 * 186 * @param model Top level object containing the view data including the collection and new line 187 * @param collectionId the id of the collection being added to 188 * @param collectionPath the path to the collection being modified 189 * @param selectedLineIndex The index within the collection of the line to save. 190 */ 191 void processCollectionSaveLine(ViewModel model, String collectionId, String collectionPath, int selectedLineIndex); 192 193 /** 194 * Invoked when the delete line action is chosen for a collection. The 195 * collection path gives the full path to the collection that action was 196 * selected for. Here validation can be performed to make sure the action is 197 * allowed. If the action is valid the line should be deleted from the 198 * collection, otherwise errors should be added to the global 199 * <code>MessageMap</code> 200 * 201 * @param model Top level object containing the view data including the collection 202 * @param collectionId the id of the collection being added to 203 * @param collectionPath the path to the collection being modified 204 * @param lineIndex index of the collection line that was selected for removal 205 */ 206 void processCollectionDeleteLine(ViewModel model, String collectionId, String collectionPath, int lineIndex); 207 208 /** 209 * Process the results returned from a multi-value lookup populating the lines for the collection given 210 * by the path 211 * 212 * @param model object containing the view data 213 * @param collectionId the id of the collection being added to 214 * @param collectionPath the path to the collection being modified 215 * @param multiValueReturnFields String containing the selected line field names 216 * @param lookupResultValues String containing the selected line values 217 */ 218 void processMultipleValueLookupResults(ViewModel model, String collectionId, String collectionPath, 219 String multiValueReturnFields, String lookupResultValues); 220 221 /** 222 * Invoked by the <code>Inquiry</code> widget to build the inquiry link 223 * 224 * <p> 225 * Note this is used primarily for custom <code>Inquirable</code> 226 * implementations to customize the inquiry class or parameters for an 227 * inquiry. Instead of building the full inquiry link, implementations can 228 * make a callback to 229 * org.kuali.rice.krad.uif.widget.Inquiry.buildInquiryLink(Object, String, 230 * Class<?>, Map<String, String>) given an inquiry class and parameters to 231 * build the link field. 232 * </p> 233 * 234 * @param dataObject parent object for the inquiry property 235 * @param propertyName name of the property the inquiry is being built for 236 * @param inquiry instance of the inquiry widget being built for the property 237 */ 238 void buildInquiryLink(Object dataObject, String propertyName, Inquiry inquiry); 239 240 /** 241 * Sets up the view context which will be available to other components through their context 242 * for conditional logic evaluation. 243 */ 244 void setViewContext(); 245 246 /** 247 * Invokes the configured <code>PresentationController</code> and </code>Authorizer</code> for 248 * the view to get the exported action flags and edit modes that can be used in conditional 249 * logic 250 */ 251 void retrieveEditModesAndActionFlags(); 252 253 /** 254 * Perform a database or data dictionary based refresh of a specific property object 255 * 256 * <p> 257 * The object needs to be of type PersistableBusinessObject. 258 * </p> 259 * 260 * @param parentObject parent object that references the object to be refreshed 261 * @param referenceObjectName property name of the parent object to be refreshed 262 */ 263 void refreshReference(Object parentObject, String referenceObjectName); 264 265 /** 266 * Update the reference objects listed in referencesToRefresh of the model 267 * 268 * <p> 269 * The the individual references in the referencesToRefresh string are separated by 270 * KRADConstants.REFERENCES_TO_REFRESH_SEPARATOR). 271 * </p> 272 * 273 * @param referencesToRefresh list of references to refresh ( 274 */ 275 void refreshReferences(String referencesToRefresh); 276 277 /** 278 * Retrieves the default value that is configured for the given data field 279 * 280 * <p> 281 * The field's default value is determined in the following order: 282 * 283 * <ol> 284 * <li>If default value on field is non-blank</li> 285 * <li>If expression is found for default value</li> 286 * <li>If default value finder class is configured for field</li> 287 * <li>If an expression is found for default values</li> 288 * <li>If default values on field is not null</li> 289 * </ol> 290 * </p> 291 * 292 * @param object object that should be populated 293 * @param dataField field to retrieve default value for 294 * @return Object default value for field or null if value was not found 295 */ 296 Object getDefaultValueForField(Object object, DataField dataField); 297 298 /** 299 * Applies the default value configured for the given field (if any) to the line given object 300 * property that is determined by the given binding path 301 * 302 * @param object object that should be populated 303 * @param dataField field to check for configured default value 304 * @param bindingPath path to the property on the object that should be populated 305 */ 306 void populateDefaultValueForField(Object object, DataField dataField, String bindingPath); 307 308 /** 309 * Builds JS script that will invoke the show growl method to display a growl message when the 310 * page is rendered 311 * 312 * <p> 313 * A growl call will be created for any explicit growl messages added to the message map. 314 * </p> 315 * 316 * <p> 317 * Growls are only generated if @{link 318 * org.kuali.rice.krad.uif.view.View#isGrowlMessagingEnabled()} is enabled. If not, the growl 319 * messages are set as info messages for the page 320 * </p> 321 * 322 * @return JS script string for generated growl messages 323 */ 324 String buildGrowlScript(); 325 326 /** 327 * Iterates through the view components picking up data fields and applying an default value 328 * configured 329 * 330 * @param component component that should be checked for default values 331 */ 332 void applyDefaultValues(Component component); 333 334 /** 335 * Populate default values the model backing a line in a collection group. 336 * 337 * @param collectionGroup The collection group. 338 * @param line The model object backing the line. 339 */ 340 void applyDefaultValuesForCollectionLine(CollectionGroup collectionGroup, Object line); 341 342 /** 343 * Uses reflection to find all fields defined on the <code>View</code> instance that have the 344 * <code>RequestParameter</code> annotation (which indicates the field may be populated by the 345 * request). 346 * 347 * <p> 348 * The <code>View</code> instance is inspected for fields that have the 349 * <code>RequestParameter</code> annotation and if corresponding parameters are found in the 350 * request parameter map, the request value is used to set the view property. The Map of 351 * parameter name/values that match are placed in the view so they can be later retrieved to 352 * rebuild the view. Custom <code>ViewServiceHelper</code> implementations can add additional 353 * parameter key/value pairs to the returned map if necessary. 354 * </p> 355 * 356 * <p> 357 * For each field found, if there is a corresponding key/value pair in the request parameters, 358 * the value is used to populate the field. In addition, any conditional properties of 359 * <code>PropertyReplacers</code> configured for the field are cleared so that the request 360 * parameter value does not get overridden by the dictionary conditional logic 361 * </p> 362 * 363 * @param parameters The request parameters that apply to the view. 364 * @see org.kuali.rice.krad.uif.component.RequestParameter 365 */ 366 void populateViewFromRequestParameters(Map<String, String> parameters); 367 368 /** 369 * Gets an expression evaluator factory for use with the current view. 370 * 371 * @return expression evaluator factory 372 */ 373 ExpressionEvaluatorFactory getExpressionEvaluatorFactory(); 374 375 }