回想起過往的漫漫編程人生路,不禁讓人唏噓感慨,或許這是我人生中第一次比較正規地使用反射了(/ω╲),不廢話,碼上見:
import java.lang.reflect.InvocationTargetException;import java.lang.reflect.Method;import java.util.ArrayList;import java.util.Enumeration;import java.util.HashMap;import java.util.List;import java.util.Map;import javax.servlet.http.HttpServletRequest;import org.nutz.lang.Strings;/*** @author 艾小天 * 需要把返回的 Object 強轉成一開始傳進來 model 就行了*/public class FormUtil { private static final String STRING = "java.lang.String";//用於反射中的類型判斷 private static final String INTEGER = "java.lang.Integer";//用於反射中的類型判斷 private static final String BOOLEAN = "java.lang.Boolean";//用於反射中的類型判斷 private static final String DOMAIN = "domain.";//表單中各欄位統一的首碼,ps:domain.id private static final String SET = "set";//用於擷取 model 的 set 方法,給屬性賦值 /** * * @param request * @param target:需要映射的 model 類 * @return */ public static Object getDomainMap(HttpServletRequest request, Object target) { Map<String, Object> dr = new HashMap<>(); //擷取表單中所有以 domain. 開頭的欄位值並放到 dr 中 Enumeration<String> e = request.getParameterNames(); while (e.hasMoreElements()) { String paramName = e.nextElement(); if(!Strings.isBlank(paramName) && paramName.startsWith(DOMAIN)) { dr.put(paramName.substring(7).toUpperCase(), request.getParameter(paramName)); } } //擷取 model 中所有 set** 方法 List<Method> methodArr = getSetMethod(target.getClass().getName()); for (Method method : methodArr) { String propertName = method.getName().substring(3).toUpperCase(); //通過遍曆調用所有 set 方法把值傳到對應的屬性中 setParam(method, dr.get(propertName), target); } return target; } /** * 擷取 model 中所有帶 set** 的方法; * @param pkgName:類的全路徑名 * @return */ @SuppressWarnings({ "rawtypes", "unchecked" }) private static List<Method> getSetMethod(String pkgName) { List<Method> methodArr = new ArrayList(); try { Class clazz = Class.forName(pkgName); Method[] methods = clazz.getMethods(); for (Method method : methods) { String methodName = method.getName(); if (methodName.indexOf(SET) == 0) { methodArr.add(method); } } } catch (ClassNotFoundException e) { e.printStackTrace(); } return methodArr; } /** * 調用 model 中的方法把值傳到對應的屬性上去 * @param method:model 的方法 * @param value:對應的set * @param target:需要映射的 model 類 */ private static void setParam(Method method, Object value, Object target) { Class<?>[] parameterTypes = method.getParameterTypes(); //一般只有一個參數,直接取 [0] 了 String paramType = parameterTypes[0].getName(); if (!Strings.isBlank(paramType) && value != null && !"".equals(value)) { try { //model 對應表單中就只有這三種類型的資料,有需要再添加 switch (paramType) { case STRING: method.invoke(target, value.toString()); break; case INTEGER: method.invoke(target, new Integer(value.toString())); break; case BOOLEAN: method.invoke(target, new Boolean(value.toString())); break; default: method.invoke(target, value.toString()); break; } } catch (IllegalAccessException | IllegalArgumentException | InvocationTargetException e) { e.printStackTrace();; } } }}