├── .gitignore ├── README.md ├── pom.xml └── src └── main ├── java └── org │ └── aisframework │ └── web │ ├── annotation │ ├── Controller.java │ ├── MapURL.java │ └── ResponseBody.java │ ├── asm │ ├── ReadMethodArgNameClassVisitor.java │ └── ReadMethodArgNameMethodVisitor.java │ ├── classcollection │ └── ClassCollection.java │ ├── param │ ├── HandlerMapping.java │ └── MethodResolver.java │ ├── servlet │ └── AisDispatcherServlet.java │ ├── structure │ ├── MethodPro.java │ ├── ModelMap.java │ └── RequestMethod.java │ ├── test │ └── test.java │ └── utils │ ├── AjaxUtils.java │ ├── AsmUtils.java │ ├── CollectionUtils.java │ ├── Config.java │ ├── FileUtils.java │ ├── ReflectProcessor.java │ ├── ReflectUtils.java │ └── StringUtils.java ├── resources └── config.ini └── webapp ├── WEB-INF ├── page │ ├── 404.html │ └── succ.html └── web.xml ├── ajaxtest.html └── index.html /.gitignore: -------------------------------------------------------------------------------- 1 | 2 | # Maven # 3 | target/ 4 | # IDEA # 5 | .idea/ 6 | *.iml 7 | # Eclipse # 8 | .settings/ 9 | .metadata/ 10 | .classpath 11 | .project 12 | Servers 13 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | ## AisMVC,一款仿SpringMVC框架的轻便快捷的Java MVC开发框架 2 | 3 | #### 前言 4 | * 写这个框架的意义在于过去使用springmvc框架作为项目中的Controller层,springmvc的简洁配置和使用让我们选择了它,但这个框架我用着也发现了它也有很多冗余功能的地方。我们团队开发web项目一般采用前后端分离,所以后端的的Controller层的功能仅仅只有提供ajax接口,页面集成后的跳转,过滤器和拦截器,所以我就想着自己写一款仿springmvc的mvc框架作为自己和团队以后的开发中小型项目的框架,舍掉冗余的部分,只要项目中实际需要的功能 5 | 6 | #### 这个框架暂时还没有经过严密的测试,所以想使用的同学我在这里说声抱歉,虽然我自己通过maven打成jar包测试过,但暂时没有用于实际开发的打算,第一是自己一个人的实力有限还是怕真实运用中出现自己不能解决的问题,其实我目前内心的真实想法是告诉大家一个mvc框架到底是怎么实现的,springmvc框架想一下吃透也不现实,如果通过我的这个框架大家也有写框架的动力和思路我也是我想看到的,也想告诉大家只要动起手来自己也能写框架,有些东西不是说说而已。很多人或许会说现在mvc框架这么多,你的这个算什么啊?但我想说现在很多时候我们百度搜索的资料来自前人,很多都是5,6年前的老资料了,我也不想以后我们的后辈通过搜索引擎搜出来的还是我们这个时候搜出来的前人总结,开发的资料。我想我也应该留点东西了。 7 | #### 框架流程图 8 | 9 | ![me](http://o9beglkd1.bkt.clouddn.com/B21B9E90-F3A9-4C2D-8BEA-A0375CE87CD8.jpg) 10 | 11 | #### 功能代码演示 12 | 13 | ```Java 14 | 15 | /** 16 | * Created by gaorui on 16/6/14. 17 | */ 18 | @Controller 19 | public class test { 20 | 21 | 22 | /** 23 | * @author gaorui 24 | * @param s1 25 | * @param s2 26 | * @param request 27 | * @param response 28 | * @param session 29 | * 普通url处理 30 | */ 31 | @MapURL(value = "get",RequestMethod = RequestMethod.GET) 32 | public void get(String s1,String s2,HttpServletRequest request, HttpServletResponse response, HttpSession session){ 33 | 34 | return; 35 | } 36 | 37 | 38 | /** 39 | * @author gaorui 40 | * @return String 41 | * 服务端跳转页面处理,默认 web-inf下所有 .html文件 42 | */ 43 | @MapURL(value="foward") 44 | public String foward(){ 45 | 46 | return "page/succ"; 47 | 48 | } 49 | 50 | /** 51 | * @author gaorui 52 | * @param userid 53 | * @return Object 54 | * 服务端处理前端ajax请求,返回json数据 55 | */ 56 | @MapURL(value = "getUser", RequestMethod = RequestMethod.GET) 57 | @ResponseBody 58 | public JSONObject getUser(int userid){ 59 | 60 | JSONObject jsonObject = new JSONObject(); 61 | jsonObject.put("userid",userid); 62 | return jsonObject; 63 | 64 | } 65 | } 66 | 67 | ``` 68 | #### mvc框架功能介绍 69 | * 注解实现 70 | * @MapURL注解实现http请求路由 71 | * 反射实现方法参数注入 72 | * String返回类型方法转发请求 73 | * @ResponseBody注解实现ajax接口 74 | * 增加config.ini配置文件,实现定向动态扫描项目中的@Controller 类 75 | * 增加注解参数RequestMethod 默认http请求类型,请求类型不合法返回405状态码 76 | 77 | #### commit log 78 | * 1.0 初始化项目 79 | * 1.1 dhy join 80 | * 1.2 mvc框架功能雏形 81 | * 1.3 增加handlerMapping处理器映射,控制器卸耦 82 | * 1.4 增加config.ini配置文件,实现定向动态扫描项目中的@Controller 类 83 | * 1.5 增加注解参数RequestMethod 默认http请求类型,请求类型不合法返回405状态码 84 | * 1.6 下一步准备做项目的容错处理,过滤器准备用原生的不准备加入框架 85 | * 1.7 修改部分目录结构,画框架整体流程图,后面继续做容错处理和性能优化 86 | -------------------------------------------------------------------------------- /pom.xml: -------------------------------------------------------------------------------- 1 | 3 | 4.0.0 4 | com.AisMVC 5 | AisMVC 6 | war 7 | 0.0.1-SNAPSHOT 8 | AisMVC Maven Webapp 9 | http://maven.apache.org 10 | 11 | 1.6 12 | 1.6 13 | UTF-8 14 | 3.0.1 15 | 16 | 17 | 18 | 19 | javax.servlet 20 | javax.servlet-api 21 | 3.1.0 22 | provided 23 | 24 | 25 | 26 | org.ow2.asm 27 | asm-all 28 | 5.0.3 29 | 30 | 31 | com.alibaba 32 | fastjson 33 | 1.1.42 34 | 35 | 36 | 37 | 38 | 39 | 40 | org.apache.maven.plugins 41 | maven-compiler-plugin 42 | 3.1 43 | 44 | 1.6 45 | 1.6 46 | UTF-8 47 | 48 | 49 | maven-assembly-plugin 50 | 51 | 52 | 53 | com.allen.capturewebdata.Main 54 | 55 | 56 | 57 | jar-with-dependencies 58 | 59 | 60 | 61 | 62 | 63 | 64 | 65 | -------------------------------------------------------------------------------- /src/main/java/org/aisframework/web/annotation/Controller.java: -------------------------------------------------------------------------------- 1 | package org.aisframework.web.annotation; 2 | 3 | import java.lang.annotation.ElementType; 4 | import java.lang.annotation.Retention; 5 | import java.lang.annotation.RetentionPolicy; 6 | import java.lang.annotation.Target; 7 | 8 | /** 9 | * Created by gaorui on 2016/6/14. 10 | */ 11 | @Target(ElementType.TYPE) 12 | @Retention(RetentionPolicy.RUNTIME) 13 | public @interface Controller {} 14 | -------------------------------------------------------------------------------- /src/main/java/org/aisframework/web/annotation/MapURL.java: -------------------------------------------------------------------------------- 1 | package org.aisframework.web.annotation; 2 | 3 | import org.aisframework.web.structure.RequestMethod; 4 | 5 | import java.lang.annotation.ElementType; 6 | import java.lang.annotation.Retention; 7 | import java.lang.annotation.RetentionPolicy; 8 | import java.lang.annotation.Target; 9 | 10 | /** 11 | * Created by gaorui on 2016/6/14. 12 | */ 13 | @Target({ElementType.TYPE,ElementType.METHOD,ElementType.FIELD,ElementType.CONSTRUCTOR}) 14 | @Retention(RetentionPolicy.RUNTIME) 15 | public @interface MapURL { 16 | String value(); 17 | String RequestMethod() default "GET"; 18 | 19 | } 20 | -------------------------------------------------------------------------------- /src/main/java/org/aisframework/web/annotation/ResponseBody.java: -------------------------------------------------------------------------------- 1 | package org.aisframework.web.annotation; 2 | 3 | import java.lang.annotation.ElementType; 4 | import java.lang.annotation.Retention; 5 | import java.lang.annotation.RetentionPolicy; 6 | import java.lang.annotation.Target; 7 | 8 | /** 9 | * Created by gaorui on 16/6/18. 10 | */ 11 | @Target(ElementType.METHOD) 12 | @Retention(RetentionPolicy.RUNTIME) 13 | public @interface ResponseBody { 14 | 15 | 16 | } -------------------------------------------------------------------------------- /src/main/java/org/aisframework/web/asm/ReadMethodArgNameClassVisitor.java: -------------------------------------------------------------------------------- 1 | package org.aisframework.web.asm; 2 | 3 | import java.util.ArrayList; 4 | import java.util.HashMap; 5 | import java.util.List; 6 | import java.util.Map; 7 | 8 | import org.objectweb.asm.ClassVisitor; 9 | import org.objectweb.asm.MethodVisitor; 10 | import org.objectweb.asm.Opcodes; 11 | import org.objectweb.asm.Type; 12 | 13 | public class ReadMethodArgNameClassVisitor extends ClassVisitor { 14 | 15 | public Map> nameArgMap = new HashMap>(); 16 | 17 | public ReadMethodArgNameClassVisitor() { 18 | super(Opcodes.ASM5); 19 | } 20 | 21 | @Override 22 | public MethodVisitor visitMethod(int access, String name, String desc, 23 | String signature, String[] exceptions) { 24 | Type methodType = Type.getMethodType(desc); 25 | int len = methodType.getArgumentTypes().length; 26 | List argumentNames = new ArrayList(); 27 | nameArgMap.put(name, argumentNames); 28 | ReadMethodArgNameMethodVisitor visitor = new ReadMethodArgNameMethodVisitor(Opcodes.ASM5); 29 | visitor.argumentNames = argumentNames; 30 | visitor.argLen = len; 31 | return visitor; 32 | } 33 | } 34 | -------------------------------------------------------------------------------- /src/main/java/org/aisframework/web/asm/ReadMethodArgNameMethodVisitor.java: -------------------------------------------------------------------------------- 1 | package org.aisframework.web.asm; 2 | 3 | /** 4 | * Created by lenovo on 2016/5/19. 5 | */ 6 | 7 | import org.objectweb.asm.Label; 8 | import org.objectweb.asm.MethodVisitor; 9 | 10 | import java.util.List; 11 | 12 | public class ReadMethodArgNameMethodVisitor extends MethodVisitor { 13 | 14 | public List argumentNames; 15 | 16 | public int argLen; 17 | 18 | public ReadMethodArgNameMethodVisitor(int api) { 19 | super(api); 20 | } 21 | 22 | @Override 23 | public void visitLocalVariable(String name, String desc, String signature, 24 | Label start, Label end, int index) { 25 | if("this".equals(name)) { 26 | return; 27 | } 28 | if(argLen-- > 0) { 29 | argumentNames.add(name); 30 | } 31 | } 32 | 33 | } 34 | -------------------------------------------------------------------------------- /src/main/java/org/aisframework/web/classcollection/ClassCollection.java: -------------------------------------------------------------------------------- 1 | package org.aisframework.web.classcollection; 2 | 3 | 4 | 5 | import org.aisframework.web.annotation.Controller; 6 | import org.aisframework.web.annotation.MapURL; 7 | import org.aisframework.web.annotation.ResponseBody; 8 | import org.aisframework.web.structure.MethodPro; 9 | import org.aisframework.web.utils.Config; 10 | import org.aisframework.web.utils.FileUtils; 11 | import org.aisframework.web.utils.StringUtils; 12 | 13 | import java.lang.reflect.Method; 14 | import java.util.HashMap; 15 | import java.util.HashSet; 16 | import java.util.Map; 17 | import java.util.Set; 18 | 19 | /** 20 | * Created by gaorui on 2016/6/14. 21 | */ 22 | public class ClassCollection { 23 | public static Map methodMap; 24 | public static Set> classSet; 25 | public static Map> classMap; 26 | public static void scanClassSetByPackage(String packageName) 27 | { 28 | methodMap=new HashMap(); 29 | classMap=new HashMap>(); 30 | classSet=new HashSet>(); 31 | String filePath= Config.getProPath()+ StringUtils.modifyPackagePath(packageName); 32 | FileUtils.getClassSet(filePath,classSet,packageName); 33 | for(Class clazz:classSet) 34 | { 35 | if(clazz.isAnnotationPresent(Controller.class)) 36 | { 37 | Method[] methods=clazz.getDeclaredMethods(); 38 | for(Method method:methods) 39 | { 40 | if(method.isAnnotationPresent(MapURL.class)) 41 | { 42 | MapURL mapURL=method.getAnnotation(MapURL.class); 43 | boolean b = false; 44 | if(method.isAnnotationPresent(ResponseBody.class)){ 45 | b = true; 46 | } 47 | MethodPro mp=new MethodPro(method,mapURL.value(),mapURL.RequestMethod(),b); 48 | 49 | methodMap.put(mapURL.value(),mp); 50 | classMap.put(mapURL.value(),clazz); 51 | 52 | } 53 | 54 | } 55 | } 56 | } 57 | } 58 | 59 | public static Set> getClassSet() { 60 | return classSet; 61 | } 62 | 63 | 64 | 65 | public static Map getMethodMap() { 66 | return methodMap; 67 | } 68 | 69 | public static Map> getClassMap() { 70 | return classMap; 71 | } 72 | 73 | 74 | } 75 | -------------------------------------------------------------------------------- /src/main/java/org/aisframework/web/param/HandlerMapping.java: -------------------------------------------------------------------------------- 1 | package org.aisframework.web.param; 2 | 3 | import org.aisframework.web.structure.MethodPro; 4 | import org.aisframework.web.test.test; 5 | import org.aisframework.web.utils.CollectionUtils; 6 | import org.aisframework.web.utils.ReflectProcessor; 7 | 8 | import javax.servlet.http.HttpServletRequest; 9 | import javax.servlet.http.HttpServletResponse; 10 | import java.lang.reflect.Method; 11 | import java.util.List; 12 | import java.util.Map; 13 | 14 | /** 15 | * Created by gaorui on 16/6/19. 16 | */ 17 | public class HandlerMapping { 18 | 19 | public static void HandlerMapping(HttpServletRequest req,HttpServletResponse resp, Map methodProMap, String key) { 20 | 21 | try { 22 | 23 | List paramlist = MethodResolver.getMethodNames(methodProMap.get(key).getMethod().getDeclaringClass().getName(), key); 24 | Map params = req.getParameterMap(); 25 | MethodPro methodPro = methodProMap.get(key); 26 | Method method = methodPro.getMethod(); 27 | List classNames = CollectionUtils.classArrToStringList(method.getParameterTypes()); 28 | Object[] invokeParamVulue = MethodResolver.paramarray(paramlist, classNames, req, resp, params);; 29 | Method urlmethod = methodProMap.get(key).getMethod(); 30 | 31 | String reqtype = req.getMethod().toUpperCase(); 32 | 33 | //http请求处理 34 | if(methodPro.getUrlStyle().equals("POST")){ 35 | if(!reqtype.equals("POST")) { 36 | 37 | resp.sendError(405); 38 | //resp.getWriter().print("405 not allowed"); 39 | return; 40 | } 41 | } 42 | 43 | //String返回方法参数类型处理 44 | if (urlmethod.getReturnType().getName().equals("java.lang.String")) { 45 | 46 | String uri = ReflectProcessor.parseMethod(method,test.class, key, invokeParamVulue).toString(); 47 | req.getRequestDispatcher("WEB-INF/" + uri + ".html").forward(req, resp); 48 | return; 49 | 50 | //ajax接口处理 51 | } else if (methodProMap.get(key).getAjax()) { 52 | 53 | Object o = ReflectProcessor.parseMethod(method,test.class, key, invokeParamVulue); 54 | resp.getWriter().print(o); 55 | return; 56 | } 57 | 58 | ReflectProcessor.parseMethod(method,test.class, key, invokeParamVulue); 59 | return; 60 | } catch (Exception e) { 61 | e.printStackTrace(); 62 | } 63 | } 64 | } 65 | -------------------------------------------------------------------------------- /src/main/java/org/aisframework/web/param/MethodResolver.java: -------------------------------------------------------------------------------- 1 | package org.aisframework.web.param; 2 | 3 | 4 | import org.aisframework.web.asm.ReadMethodArgNameClassVisitor; 5 | import org.aisframework.web.structure.ModelMap; 6 | import org.aisframework.web.utils.Config; 7 | import org.objectweb.asm.ClassReader; 8 | 9 | import javax.servlet.http.HttpServletRequest; 10 | import javax.servlet.http.HttpServletResponse; 11 | import java.io.File; 12 | import java.io.FileInputStream; 13 | import java.io.IOException; 14 | import java.io.InputStream; 15 | import java.util.*; 16 | import java.util.Map.Entry; 17 | 18 | public class MethodResolver { 19 | 20 | 21 | 22 | public static List getMethodNames(String className,String methodName) throws IOException { 23 | List list=new ArrayList(); 24 | String cn= Config.getProPath()+className.replace(".", "/")+".class"; 25 | InputStream is=new FileInputStream(new File(cn)); 26 | ClassReader cr = new ClassReader(is); 27 | ReadMethodArgNameClassVisitor classVisitor = new ReadMethodArgNameClassVisitor(); 28 | cr.accept(classVisitor, 0); 29 | for(Entry> entry : classVisitor.nameArgMap.entrySet()) { 30 | if(entry.getKey().equals(methodName)) { 31 | for (String s : entry.getValue()) { 32 | list.add(s); 33 | } 34 | } 35 | } 36 | return list; 37 | } 38 | 39 | 40 | 41 | public static Object[] paramarray(List paraNames, List classNames, HttpServletRequest req, HttpServletResponse resp, Map params) { 42 | List list=new ArrayList(); 43 | 44 | String paramValue = ""; 45 | 46 | for(int i=0,length=paraNames.size();i methodProMap =null; 25 | @Override 26 | public void init(ServletConfig servletConfig) throws ServletException { 27 | ClassCollection.scanClassSetByPackage(Config.getAnnoClassConfig("base-package"));//初始化配置下的 @Controller类 28 | methodProMap = ClassCollection.getMethodMap();//拿到封装的每个类方法的属性 29 | } 30 | 31 | @Override 32 | protected void service(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { 33 | 34 | String pathInfo=req.getServletPath(); 35 | String key = pathInfo.replaceAll("/", "").split("\\.")[0]; 36 | if (methodProMap.containsKey(key)) { 37 | HandlerMapping.HandlerMapping(req,resp,methodProMap,key);//转发到映射器进行映射处理 38 | 39 | return ; 40 | 41 | } 42 | 43 | //用户请求url没有映射404处理 44 | resp.sendError(404); 45 | } 46 | } 47 | 48 | -------------------------------------------------------------------------------- /src/main/java/org/aisframework/web/structure/MethodPro.java: -------------------------------------------------------------------------------- 1 | package org.aisframework.web.structure; 2 | 3 | import java.lang.reflect.Method; 4 | 5 | /** 6 | * Created by lenovo on 2016/5/16. 7 | */ 8 | public class MethodPro { 9 | private String name; 10 | private String url; 11 | private String urlStyle; 12 | private Method method; 13 | private Boolean isAjax; 14 | 15 | public MethodPro(Method method, String url, String urlStyle,boolean isAjax) { 16 | this.method = method; 17 | this.url = url; 18 | this.urlStyle = urlStyle; 19 | this.isAjax = isAjax; 20 | 21 | this.name=method.getName(); 22 | } 23 | 24 | 25 | 26 | public Method getMethod() { 27 | return method; 28 | } 29 | 30 | public void setMethod(Method method) { 31 | this.method = method; 32 | } 33 | 34 | public String getName() { 35 | return name; 36 | } 37 | 38 | public void setName(String name) { 39 | this.name = name; 40 | } 41 | 42 | public String getUrl() { 43 | return url; 44 | } 45 | 46 | public void setUrl(String url) { 47 | this.url = url; 48 | } 49 | 50 | public String getUrlStyle() { 51 | return urlStyle; 52 | } 53 | 54 | public void setUrlStyle(String urlStyle) { 55 | this.urlStyle = urlStyle; 56 | } 57 | 58 | 59 | public Boolean getAjax() { 60 | return isAjax; 61 | } 62 | 63 | public void setAjax(Boolean ajax) { 64 | isAjax = ajax; 65 | } 66 | } 67 | -------------------------------------------------------------------------------- /src/main/java/org/aisframework/web/structure/ModelMap.java: -------------------------------------------------------------------------------- 1 | package org.aisframework.web.structure; 2 | 3 | import java.util.HashMap; 4 | import java.util.Map; 5 | 6 | /** 7 | * Created by lenovo on 2016/5/22. 8 | */ 9 | public class ModelMap { 10 | public Map map; 11 | 12 | public ModelMap(Map map) 13 | { 14 | this.map=map; 15 | } 16 | public ModelMap() 17 | { 18 | map=new HashMap(); 19 | } 20 | 21 | public void put(String s,Object o) 22 | { 23 | map.put(s,o); 24 | } 25 | 26 | public void get(String s) 27 | { 28 | map.get(s); 29 | } 30 | 31 | public Map getMap() { 32 | return map; 33 | } 34 | } 35 | -------------------------------------------------------------------------------- /src/main/java/org/aisframework/web/structure/RequestMethod.java: -------------------------------------------------------------------------------- 1 | package org.aisframework.web.structure; 2 | 3 | /** 4 | * Created by gaorui on 16/6/25. 5 | */ 6 | public class RequestMethod { 7 | public final static String GET = "GET"; 8 | public final static String POST = "POST"; 9 | 10 | } 11 | -------------------------------------------------------------------------------- /src/main/java/org/aisframework/web/test/test.java: -------------------------------------------------------------------------------- 1 | package org.aisframework.web.test; 2 | 3 | import com.alibaba.fastjson.JSON; 4 | import com.alibaba.fastjson.JSONObject; 5 | import org.aisframework.web.annotation.Controller; 6 | import org.aisframework.web.annotation.MapURL; 7 | import org.aisframework.web.annotation.ResponseBody; 8 | import org.aisframework.web.structure.RequestMethod; 9 | 10 | import javax.servlet.http.HttpServletRequest; 11 | import javax.servlet.http.HttpServletResponse; 12 | import javax.servlet.http.HttpSession; 13 | import java.io.IOException; 14 | import java.io.PrintWriter; 15 | import java.util.HashMap; 16 | import java.util.Map; 17 | 18 | /** 19 | * Created by gaorui on 16/6/14. 20 | */ 21 | @Controller 22 | public class test { 23 | 24 | 25 | /** 26 | * @author gaorui 27 | * @param s1 28 | * @param s2 29 | * @param request 30 | * @param response 31 | * @param session 32 | * 普通url处理 33 | */ 34 | @MapURL(value = "get",RequestMethod = RequestMethod.GET) 35 | public void get(String s1,String s2,HttpServletRequest request, HttpServletResponse response, HttpSession session){ 36 | 37 | System.out.print(s1+""+s2); 38 | return; 39 | } 40 | 41 | 42 | /** 43 | * @author gaorui 44 | * @return String 45 | * 服务端跳转页面处理,默认 web-inf下所有 .html文件 46 | */ 47 | @MapURL(value="foward") 48 | public String foward(){ 49 | 50 | return "page/succ"; 51 | 52 | } 53 | 54 | /** 55 | * @author gaorui 56 | * @param userid 57 | * @return Object 58 | * 服务端处理前端ajax请求,返回json数据 59 | */ 60 | @MapURL(value = "getUser", RequestMethod = RequestMethod.GET) 61 | @ResponseBody 62 | public JSONObject getUser(Integer userid,Integer me){ 63 | 64 | JSONObject jsonObject = new JSONObject(); 65 | jsonObject.put("userid",userid); 66 | return jsonObject; 67 | 68 | } 69 | } 70 | -------------------------------------------------------------------------------- /src/main/java/org/aisframework/web/utils/AjaxUtils.java: -------------------------------------------------------------------------------- 1 | package org.aisframework.web.utils; 2 | 3 | import javax.servlet.http.HttpServletRequest; 4 | 5 | /** 6 | * Created by gaorui on 16/7/1. 7 | */ 8 | public class AjaxUtils { 9 | public static boolean isAjaxRequest(HttpServletRequest request){ 10 | 11 | String requestedWith = request.getHeader("X-Requested-With"); 12 | Boolean isAjax = requestedWith != null ? requestedWith.equals("XMLHttpRequest"):false; 13 | 14 | return isAjax; 15 | } 16 | } 17 | -------------------------------------------------------------------------------- /src/main/java/org/aisframework/web/utils/AsmUtils.java: -------------------------------------------------------------------------------- 1 | package org.aisframework.web.utils; 2 | 3 | import org.objectweb.asm.*; 4 | 5 | import java.io.IOException; 6 | import java.lang.reflect.Method; 7 | import java.lang.reflect.Modifier; 8 | 9 | 10 | /** 11 | * Created by gaorui on 16/6/15. 12 | */ 13 | public class AsmUtils { 14 | /** 15 | * 16 | *

17 | * 比较参数类型是否一致 18 | *

19 | * 20 | * @param types 21 | * asm的类型({@link Type}) 22 | * @param clazzes 23 | * java 类型({@link Class}) 24 | * @return 25 | */ 26 | private static boolean sameType(Type[] types, Class[] clazzes) { 27 | // 个数不同 28 | if (types.length != clazzes.length) { 29 | return false; 30 | } 31 | 32 | for (int i = 0; i < types.length; i++) { 33 | if (!Type.getType(clazzes[i]).equals(types[i])) { 34 | return false; 35 | } 36 | } 37 | return true; 38 | } 39 | 40 | /** 41 | * 42 | *

43 | * 获取方法的参数名 44 | *

45 | * 46 | * @param m 47 | * @return 48 | */ 49 | public static String[] getMethodParamNames(final Method m) { 50 | final String[] paramNames = new String[m.getParameterTypes().length]; 51 | final String n = m.getDeclaringClass().getName(); 52 | ClassReader cr = null; 53 | try { 54 | cr = new ClassReader(n); 55 | } catch (IOException e) { 56 | throw new RuntimeException(e); 57 | } 58 | cr.accept(new ClassVisitor(Opcodes.ASM4) { 59 | @Override 60 | public MethodVisitor visitMethod(final int access, 61 | final String name, final String desc, 62 | final String signature, final String[] exceptions) { 63 | final Type[] args = Type.getArgumentTypes(desc); 64 | // 方法名相同并且参数个数相同 65 | if (!name.equals(m.getName()) 66 | || !sameType(args, m.getParameterTypes())) { 67 | return super.visitMethod(access, name, desc, signature, 68 | exceptions); 69 | } 70 | MethodVisitor v = super.visitMethod(access, name, desc, 71 | signature, exceptions); 72 | return new MethodVisitor(Opcodes.ASM4, v) { 73 | @Override 74 | public void visitLocalVariable(String name, String desc, 75 | String signature, Label start, Label end, int index) { 76 | int i = index - 1; 77 | // 如果是静态方法,则第一就是参数 78 | // 如果不是静态方法,则第一个是"this",然后才是方法的参数 79 | if (Modifier.isStatic(m.getModifiers())) { 80 | i = index; 81 | } 82 | if (i >= 0 && i < paramNames.length) { 83 | paramNames[i] = name; 84 | } 85 | super.visitLocalVariable(name, desc, signature, start, 86 | end, index); 87 | } 88 | 89 | }; 90 | } 91 | }, 0); 92 | return paramNames; 93 | } 94 | 95 | 96 | } 97 | -------------------------------------------------------------------------------- /src/main/java/org/aisframework/web/utils/CollectionUtils.java: -------------------------------------------------------------------------------- 1 | package org.aisframework.web.utils; 2 | 3 | import java.util.ArrayList; 4 | import java.util.List; 5 | 6 | /** 7 | * Created by gaorui on 2016/5/20. 8 | */ 9 | public class CollectionUtils { 10 | public static List arrayToList(T[] arr) 11 | { 12 | List list=new ArrayList(); 13 | for(T t:arr) 14 | { 15 | list.add(t); 16 | } 17 | return list; 18 | } 19 | 20 | public static List classArrToStringList(Class[] classArr) 21 | { 22 | List list=new ArrayList(); 23 | for(Class clazz:classArr) 24 | { 25 | list.add(clazz.getName()); 26 | } 27 | return list; 28 | } 29 | } 30 | -------------------------------------------------------------------------------- /src/main/java/org/aisframework/web/utils/Config.java: -------------------------------------------------------------------------------- 1 | package org.aisframework.web.utils; 2 | 3 | import java.io.BufferedInputStream; 4 | import java.io.File; 5 | import java.io.FileInputStream; 6 | import java.io.FileNotFoundException; 7 | import java.util.HashMap; 8 | import java.util.Map; 9 | import java.util.Scanner; 10 | 11 | /** 12 | * Created by gaorui on 2016/5/16. 13 | */ 14 | public class Config { 15 | 16 | 17 | public static String getProPath() { 18 | String path = getPath(); 19 | path = path.replace("file:", ""); 20 | return path; 21 | } 22 | 23 | 24 | 25 | public static String getPath() { 26 | // String path = Thread.currentThread().getContextClassLoader().getResource("").toString(); 27 | String path=Config.class.getClassLoader().getResource("").toString(); 28 | return path; 29 | } 30 | 31 | 32 | 33 | public static String getAnnoClassConfig(String source) { 34 | String path = getProPath(); 35 | File file = new File(path + File.separator + "config.ini"); 36 | if (!file.exists()) { 37 | //System.out.println("没有找到config.ini文件,默认扫描所有类"); 38 | return ""; 39 | } 40 | Scanner sc = null; 41 | 42 | try { 43 | sc = new Scanner(new BufferedInputStream(new FileInputStream(file))); 44 | } catch (FileNotFoundException e) { 45 | e.printStackTrace(); 46 | } 47 | 48 | Map config = new HashMap(); 49 | String configkey = ""; 50 | while (sc.hasNextLine()) { 51 | String line = sc.nextLine(); 52 | if (!line.startsWith("#") && line != null && !"".equals(line)) { 53 | line = line + "="; 54 | String[] con = line.split("="); 55 | configkey = con[0].trim(); 56 | config.put(con[0].trim(), con[1].trim()); 57 | } 58 | } 59 | 60 | return config.get(configkey); 61 | 62 | } 63 | } 64 | -------------------------------------------------------------------------------- /src/main/java/org/aisframework/web/utils/FileUtils.java: -------------------------------------------------------------------------------- 1 | package org.aisframework.web.utils; 2 | 3 | import java.io.File; 4 | import java.util.Set; 5 | 6 | /** 7 | * Created by gaorui on 2016/5/16. 8 | */ 9 | public class FileUtils { 10 | public static void getClassSet(String path,Set> classSet,String packageName) 11 | { 12 | File file=new File(path); 13 | for(String fileName:file.list()) 14 | { 15 | String newPath=path+File.separator+fileName; 16 | if(new File(newPath).isDirectory()) { 17 | getClassSet(newPath, classSet,packageName); 18 | }else{ 19 | if(newPath.endsWith(".class")) 20 | { 21 | try { 22 | String className=newPath.substring(newPath.lastIndexOf(StringUtils.modifyPackagePath(packageName))).replace(File.separator,".").replace(".class",""); 23 | 24 | Class cls=Class.forName(className);//,false,Thread.currentThread().getContextClassLoader()); 25 | classSet.add(cls); 26 | } catch (ClassNotFoundException e) { 27 | continue; 28 | } 29 | 30 | } 31 | } 32 | } 33 | } 34 | } 35 | -------------------------------------------------------------------------------- /src/main/java/org/aisframework/web/utils/ReflectProcessor.java: -------------------------------------------------------------------------------- 1 | package org.aisframework.web.utils; 2 | 3 | /** 4 | * Created by gaorui on 16/6/5. 5 | */ 6 | 7 | 8 | import org.aisframework.web.annotation.MapURL; 9 | 10 | import java.lang.reflect.Method; 11 | 12 | 13 | 14 | public class ReflectProcessor { 15 | 16 | public static Object parseMethod(final Method method,final Class clazz, String methodname, Object[] value) throws Exception { 17 | 18 | 19 | if(value == null){ 20 | value = new Object[]{}; 21 | } 22 | Object o =null; 23 | final Object obj = clazz.getConstructor(new Class[] {}).newInstance(new Object[] {}); 24 | 25 | 26 | o = method.invoke(obj,value); 27 | 28 | 29 | 30 | return o; 31 | } 32 | 33 | 34 | } 35 | -------------------------------------------------------------------------------- /src/main/java/org/aisframework/web/utils/ReflectUtils.java: -------------------------------------------------------------------------------- 1 | package org.aisframework.web.utils; 2 | 3 | import java.lang.reflect.Field; 4 | import java.util.Map; 5 | 6 | /** 7 | * Created by gaorui on 2016/5/21. 8 | */ 9 | public class ReflectUtils { 10 | public static boolean classLoaded(String source) 11 | { 12 | try { 13 | Class clazz=Class.forName(source); 14 | } catch (ClassNotFoundException e) { 15 | return false; 16 | } 17 | return true; 18 | } 19 | 20 | public static boolean hasField(String className,Map reqParaMap) 21 | { 22 | Class clazz=ReflectUtils.loadClass(className); 23 | Field[] fields=clazz.getDeclaredFields(); 24 | Object o=null; 25 | try { 26 | o= clazz.newInstance(); 27 | for (Field field : fields) { 28 | String filedName=field.getName(); 29 | if (reqParaMap.containsKey(filedName)) { 30 | return true; 31 | } 32 | } 33 | }catch (IllegalAccessException e){ 34 | e.printStackTrace(); 35 | }catch (InstantiationException e){ 36 | e.printStackTrace(); 37 | } 38 | return false; 39 | } 40 | 41 | public static Class loadClass(String source) 42 | { 43 | Class clazz; 44 | try { 45 | clazz=Class.forName(source); 46 | } catch (ClassNotFoundException e) { 47 | return null; 48 | } 49 | return clazz; 50 | } 51 | 52 | public static Object getObjectByClassAndReq(String className, Map reqParaMap) { 53 | Class clazz=ReflectUtils.loadClass(className); 54 | Field[] fields=clazz.getDeclaredFields(); 55 | Object o=null; 56 | try { 57 | o= clazz.newInstance(); 58 | for (Field field : fields) { 59 | String filedName=field.getName(); 60 | if (reqParaMap.containsKey(filedName)) { 61 | field.setAccessible(true); 62 | field.set(o, reqParaMap.get(filedName)); 63 | } 64 | } 65 | }catch (IllegalAccessException e){ 66 | e.printStackTrace(); 67 | }catch (InstantiationException e){ 68 | e.printStackTrace(); 69 | } 70 | return o; 71 | } 72 | } 73 | -------------------------------------------------------------------------------- /src/main/java/org/aisframework/web/utils/StringUtils.java: -------------------------------------------------------------------------------- 1 | package org.aisframework.web.utils; 2 | 3 | import java.io.File; 4 | 5 | /** 6 | * Created by gaorui on 2016/5/16. 7 | */ 8 | public class StringUtils { 9 | public static String modifyPackagePath(String packageName) 10 | { 11 | if(packageName.indexOf(".")>-1) 12 | return packageName.replace(".", File.separator); 13 | else 14 | return packageName; 15 | } 16 | 17 | 18 | } 19 | -------------------------------------------------------------------------------- /src/main/resources/config.ini: -------------------------------------------------------------------------------- 1 | base-package=org.aisframework.web.test -------------------------------------------------------------------------------- /src/main/webapp/WEB-INF/page/404.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 404 6 | 7 | 8 |

404,hello world

9 | 10 | -------------------------------------------------------------------------------- /src/main/webapp/WEB-INF/page/succ.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | succ 6 | 7 | 8 |

路由方法成功

9 | 10 | -------------------------------------------------------------------------------- /src/main/webapp/WEB-INF/web.xml: -------------------------------------------------------------------------------- 1 | 4 | 5 | 6 | Archetype Created Web Application 7 | 8 | 9 | AisDispatcherServlet 10 | org.aisframework.web.servlet.AisDispatcherServlet 11 | 1 12 | 13 | 14 | AisDispatcherServlet 15 | *.do 16 | 17 | 18 | -------------------------------------------------------------------------------- /src/main/webapp/ajaxtest.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | ajaxtest 6 | 7 | 39 | 40 | 41 | 42 | 43 | -------------------------------------------------------------------------------- /src/main/webapp/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | Title 6 | 7 | 8 | 9 | 10 | --------------------------------------------------------------------------------