📄 onetomanycrudcontroller.java
字号:
package net.java.workeffort.webapp.action;import java.lang.reflect.InvocationTargetException;import java.lang.reflect.Method;import java.util.Iterator;import java.util.List;import javax.servlet.http.HttpServletRequest;import javax.servlet.http.HttpServletResponse;import net.java.workeffort.infrastructure.exception.IPropertyException;import net.java.workeffort.infrastructure.view.ViewHelper;import net.java.workeffort.service.domain.CollectionElement;import net.java.workeffort.service.support.NoParentRowFkException;import net.java.workeffort.service.support.OptimisticLockingException;import net.java.workeffort.service.support.UniqueConstraintException;import net.java.workeffort.webapp.support.FlowSetValueHelper;import net.java.workeffort.webapp.support.InvalidSynchronizerTokenException;import net.java.workeffort.webapp.support.WebappUtils;import org.apache.commons.beanutils.PropertyUtils;import org.apache.commons.lang.Validate;import org.springframework.validation.BindException;import org.springframework.web.servlet.ModelAndView;/** * A generic CRUD controller for one to many relationship. Also has methods * which allows the user to set a value of a field using page flow. The command * object is stored in session scope. * <p> * <b>Exposed configuration properties: (See BaseFormController also) </b> <br> * <table border="1"> * <tr> * <td><b>Name </b></td> * <td><b>Default </b></td> * <td><b>Description </b></td> * </tr> * <tr> * <td>service</td> * <td>null</td> * <td>The service. Required</td> * </tr> * <tr> * <td>formView</td> * <td>null</td> * <td>The form view. Required</td> * </tr> * <tr> * <td>commandClass</td> * <td>null</td> * <td>The command class. Required</td> * </tr> * <tr> * <td>primaryKeyParameterName</td> * <td>null</td> * <td>Name of the request parameter which will be used as the primary key for * querying the object. Required. Expects to find a property by this name in the * command object</td> * </tr> * <tr> * <td>commandClass</td> * <td>null</td> * <td>The command class. Required</td> * </tr> * <tr> * <td>getObjectMethodName</td> * <td>null</td> * <td>The method name to retrive object in the service. Required</td> * </tr> * <tr> * <td>saveMethodName</td> * <td>null</td> * <td>The save method name in the service. Required</td> * </tr> * <tr> * <td>collectionPropertyName</td> * <td>null</td> * <td>The collection property name in the command class. Required</td> * </tr> * <tr> * <td>collectionElementClass</td> * <td>null</td> * <td>The class of the element stored in the collection. Required</td> * </tr> * </table> * @author Antony Joseph */public class OneToManyCrudController extends BaseFormController { public static final String RESET = "reset"; public static final String IGNORE = "ignore"; public static final String ASSIGN_SELECTED_VALUE = "assignSelectedValue"; public static final String EDIT_ROW = "editRow"; public static final String ADD_ROW = "addRow"; public static final String IGNORE_ROW = "ignoreRow"; public static final String START_FLOW_SET_VALUE = "startFlowSetValue"; public static final String CANCEL_FLOW_SET_VALUE = "cancelFlowSetValue"; // The index into the collection for which the value will be set using a // flow. public static final String COLLECTION_IDX = "collectionIdx"; // The target property name for which the value needs to be set. public static final String TARGET_PROPERTY_NAME_FOR_VALUE = "targetPropertyNameForValue"; public static final String SUB_FLOW = "subFlow"; public static final String SELECTED_VALUE = "selectedValue"; // config parameters protected String primaryKeyParameter; protected String saveMethodName; protected String getObjectMethodName; protected Class collectionElementClass; protected String collectionPropertyName; // instance variables. private Method saveMethod; private Method getObjectMethod; protected Class primaryKeyClass; protected void init() { super.init(); Validate.notNull(service, "Service cannot be null"); Validate.notNull(getFormView(), "'formView' cannot be null"); Validate.notNull(getCommandClass(), "'commandClass' cannot be null"); Validate.notEmpty(primaryKeyParameter, "primaryKeyParameter cannot be null"); Validate.notEmpty(getObjectMethodName, "'getObjectMethodName' cannot be null"); Validate.notEmpty(saveMethodName, "'saveMethodName' cannot be null"); Validate.notNull(collectionPropertyName, "'collectionPropertyName' cannot be null"); Validate.notNull(collectionElementClass, "'collectionElementClass' cannot be null"); // get the primary key class using the configured primaryKeyParameter // and command object Class primaryKeyClass = WebappUtils.getPropertyType(primaryKeyParameter, getCommandClass()); // get the save/getObject methods from the service saveMethod = getServiceMethod(service.getClass(), saveMethodName, new Class[] { getCommandClass() }); getObjectMethod = getServiceMethod(service.getClass(), getObjectMethodName, new Class[] { primaryKeyClass }); // make sure the form is stored in message scope. setSessionForm(true); setValidateOnBinding(false); } public void setPrimaryKeyParameter(String primaryKeyParameter) { this.primaryKeyParameter = primaryKeyParameter; } public void setGetObjectMethodName(String getObjectMethodName) { this.getObjectMethodName = getObjectMethodName; } public void setSaveMethodName(String saveMethodName) { this.saveMethodName = saveMethodName; } public void setCollectionPropertyName(String collectionPropertyName) { this.collectionPropertyName = collectionPropertyName; } public void setCollectionElementClass(Class elementClass) { this.collectionElementClass = elementClass; } protected Object formBackingObject(HttpServletRequest request) throws Exception { if (logger.isInfoEnabled()) logger.info("formBackingObject() invoked."); // Note that a reset is handle like a query. if (QUERY.equals(request.getParameter(DISPATCH_PARAMETER_NAME)) || RESET.equals(request.getParameter(DISPATCH_PARAMETER_NAME))) { Object pk = getParameterValue(request, primaryKeyParameter, primaryKeyClass); return getObject(request, pk); } else if (NEW.equals(request.getParameter(DISPATCH_PARAMETER_NAME))) { saveToken(request); // let the jsp know to display form in insert mode. saveViewHelper(request, ViewHelper.INSERT_MODE); return createCommand(); } else throw new RuntimeException( "formBackingObject(). dispatch is not 'query' or 'insert'. dispatch=" + request.getParameter(DISPATCH_PARAMETER_NAME)); } protected boolean isFormSubmission(HttpServletRequest request) { // reset is a POST. Handle it like a GET. if (RESET.equals(request.getParameter(DISPATCH_PARAMETER_NAME))) { // reset is handled like an initial query return false; } else if (ASSIGN_SELECTED_VALUE.equals(request .getParameter(DISPATCH_PARAMETER_NAME)) || CANCEL_FLOW_SET_VALUE.equals(request .getParameter(DISPATCH_PARAMETER_NAME))) //assignSelectedValue and cancelFlowSetValue are GETs. //Handle them like a form submission. return true; else return super.isFormSubmission(request); } protected ModelAndView processFormSubmission(HttpServletRequest request, HttpServletResponse response, Object command, BindException errors) throws Exception { if (!isTokenValid(request)) { clearToken(request); throw new InvalidSynchronizerTokenException( "Invalid token. dispatch=" + request.getParameter(DISPATCH_PARAMETER_NAME)); } if (ADD_ROW.equals(request.getParameter(DISPATCH_PARAMETER_NAME)) || IGNORE_ROW.equals(request .getParameter(DISPATCH_PARAMETER_NAME)) || EDIT_ROW.equals(request .getParameter(DISPATCH_PARAMETER_NAME)) || START_FLOW_SET_VALUE.equals(request .getParameter(DISPATCH_PARAMETER_NAME)) || CANCEL_FLOW_SET_VALUE.equals(request .getParameter(DISPATCH_PARAMETER_NAME)) || ASSIGN_SELECTED_VALUE.equals(request .getParameter(DISPATCH_PARAMETER_NAME))) { //call onSubmit() even if there are bind errors logger.info(request.getParameter(DISPATCH_PARAMETER_NAME) + " -> processing submit"); return onSubmit(request, response, command, errors); } else { return super.processFormSubmission(request, response, command, errors); } } protected ModelAndView onSubmit(HttpServletRequest request, HttpServletResponse response, Object command, BindException errors) throws Exception { if (logger.isInfoEnabled()) logger.info("onSubmit() invoked."); if (SAVE.equals(request.getParameter(DISPATCH_PARAMETER_NAME))) { return save(request, response, command, errors); } else if (EDIT_ROW.equals(request.getParameter(DISPATCH_PARAMETER_NAME))) { return editRow(request, response, command, errors); } else if (ADD_ROW.equals(request.getParameter(DISPATCH_PARAMETER_NAME))) { return addRow(request, response, command, errors); } else if (IGNORE_ROW.equals(request .getParameter(DISPATCH_PARAMETER_NAME))) { return ignoreRow(request, response, command, errors); } else if (START_FLOW_SET_VALUE.equals(request .getParameter(DISPATCH_PARAMETER_NAME))) { return startFlowSetValue(request, response, command, errors); } else if (ASSIGN_SELECTED_VALUE.equals(request .getParameter(DISPATCH_PARAMETER_NAME))) { return assignSelectedValue(request, response, command, errors); } else if (CANCEL_FLOW_SET_VALUE.equals(request .getParameter(DISPATCH_PARAMETER_NAME))) { return cancelFlowSetValue(request, response, command, errors); } else throw new RuntimeException("onSubmit(). invalid dispatch:" + request.getParameter(DISPATCH_PARAMETER_NAME)); } /** * Just redisplays the view so that the pertinent row is editable.. Note * that no call to the service layer is made. * @param request The request * @param response The response * @param command The command object * @param errors The bind Exception * @return model and view * @throws Exception */ protected ModelAndView editRow(HttpServletRequest request, HttpServletResponse response, Object command, BindException errors) throws Exception { if (logger.isInfoEnabled()) logger.info("editRow() invoked."); // just redisplay the form. The 'update' submitted value for processType // (of the collection element) will be used by the jsp to render the // form appropriately. Also there is no need to display errors. request.setAttribute(SKIP_ERRORS, "skip"); return showForm(request, response, errors); }
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -