/*1编写注解
编写Springmvc常用的注解
@controller
@requestmapper
@Serviceim
@autoware
通过编写如上所示的注解,来完成springmvc的基本功能
package xiao.it.annotation;
import java.lang.annotation.Documented;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
@Target(ElementType.FIELD)
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface XiaoAutoware {
String value() default "null";
}
package xiao.it.annotation;
import java.lang.annotation.Documented;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
@Target(ElementType.TYPE)
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface XiaoController {
String value() default "null";
}
package xiao.it.annotation;
import java.lang.annotation.Documented;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
@Target({ElementType.METHOD,ElementType.TYPE})
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface XiaoRequestMapping {
String value() default "null";
}
package xiao.it.annotation;
import java.lang.annotation.Documented;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
@Target(ElementType.TYPE)
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface XiaoService {
String value() default "null";
String param() default "null";
}
/*2 重写httpservlet的get.post方法
写一个自己的httpservelet类来完成springmvc的请求转发操作
package xiao.it.servlet;
import java.io.IOException;
import java.io.PrintWriter;
import java.lang.reflect.InvocationTargetException;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
public class Xiao_wornDispacherServlet extends HttpServlet {
private static final long serialVersionUID = 1L;
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp)
throws ServletException, IOException {
// TODO Auto-generated method stub
this.doPost(req, resp);
}
@Override
protected void doPost(HttpServletRequest req, HttpServletResponse resp)
throws ServletException, IOException {
// TODO Auto-generated method stub
SpringmvxCore core=new SpringmvxCore();
try {
core.doDispacher( req, resp);
} catch(Exception exception){
PrintWriter writer = resp.getWriter();
writer.write("404 请求异常");
}
}
}
/*3、包扫描
包扫描的目的根据basepackage,就是基包(代码中指的是com),扫描下面的子包以及子包下的类
拿到包下的所有类文件后,我们就可以得到文件名
有包名有文件名,我们就可以通过反射new出这些类的实例
目的就是扫描基包下的所有的类文件,根据文件获取类的完整类名:包名+类名
通过文件的方式去扫描
拿到类的Class对象
拿到field对象
拿到field上面的annotation对象
根据annotation对象拿annotation对象的属性
把属性当key拿到map中的实例
然后field。set把实例设置进去
5、建立一个url与类中方法的映射关系
其实是同样的做法
拿到类的Class对象
拿到Method对象
拿到Method上面的annotation对象
把url和method对象存到map中*/
package xiao.it.servlet;
import java.io.File;
import java.io.IOException;
import java.io.InputStream;
import java.lang.annotation.Annotation;
import java.lang.reflect.Field;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.net.URL;
import java.util.ArrayList;
import java.util.Collection;
import java.util.HashMap;
import java.util.Hashtable;
import java.util.Iterator;
import java.util.List;
import java.util.Map;
import java.util.Map.Entry;
import java.util.Properties;
import java.util.Set;
import java.util.regex.Pattern;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.apache.coyote.ActionCode;
import org.apache.tomcat.util.codec.binary.StringUtils;
import worn.it.struct.UrlMapping;
import xiao.it.annotation.XiaoAutoware;
import xiao.it.annotation.XiaoController;
import xiao.it.annotation.XiaoRequestMapping;
import xiao.it.annotation.XiaoService;
public class SpringmvxCore {
//存放类名的文件.class
public HashMap<String,String> nameMap=new HashMap<String, String>();
//存放实例的结构 key=注解小写 value=对象
public HashMap<String,Object> annotation=new HashMap();
//存储URL的映射 [{url,method},{url,method}]
public HashMap<String,UrlMapping> hashmap=new HashMap();
public void doDispacher(HttpServletRequest req, HttpServletResponse resp) throws IOException, ClassNotFoundException, InstantiationException, IllegalAccessException, IllegalArgumentException, InvocationTargetException {
//1读取配置文件
InputStream resourceAsStream = this.getClass().getClassLoader().getResourceAsStream("packege.properties");
Properties properties =new Properties();
properties.load(resourceAsStream);
String string = (String) properties.get("scanpackage");
//所描类文件
Scanner(string);
//加载类文件
loadClassFile();
//进行spring的IoC操作
spring_Ioc();
//组织地址映射
handlerMapping(req,resp);
//最后一部 处理请求
parseURL(req, resp);
}
/**
* 处理路劲映射
* @param req 请求
* @param resp 回应
* @throws ClassNotFoundException
*/
private void handlerMapping(HttpServletRequest req, HttpServletResponse resp) throws ClassNotFoundException {
UrlMapping urlMapping=new UrlMapping();
Collection<String> values = nameMap.values();
for(String str:values){
String classPath=str.replace(".class", "");
Class<?> classd = Class.forName(classPath);
String contextPath = req.getContextPath();
String baseurl=contextPath;
if(!classd.isInterface()){
if(classd.isAnnotationPresent(XiaoController.class)){
if(classd.isAnnotationPresent(XiaoRequestMapping.class)){
XiaoRequestMapping annotation2 = classd.getAnnotation(XiaoRequestMapping.class);
baseurl=baseurl+annotation2.value();
}
Method[] methods = classd.getMethods();
for(Method method:methods){
if(method.isAnnotationPresent(XiaoRequestMapping.class)){
XiaoRequestMapping anno = method.getAnnotation(XiaoRequestMapping.class);
String value = anno.value();
baseurl=baseurl+value;
baseurl=baseurl.replaceAll("//", "/");
urlMapping.setUrl(baseurl);
urlMapping.setMethod(method);
}
}
//控制层
if(classd.isAnnotationPresent(XiaoController.class)){
String simpleName = classd.getSimpleName();
String dealFirst = dealFirst(simpleName);
Object object = annotation.get(dealFirst);
urlMapping.setObj(object);
}
hashmap.put(urlMapping.getUrl(), urlMapping);
}
}
}
}
/**
* 所描包文件封装
* @param file
*/
public void Scanner(String filepath){
String repl= filepath.replaceAll("\\*", "");
String res= repl.replaceAll("\\.\\.", "\\.");
String rep = res.replaceAll("\\.", "/");
URL resource = this.getClass().getClassLoader().getResource("/"+rep);
String path2 = resource.getPath();
File fi=new File(path2);
String[] listFile = fi.list();
//扫描所有的文件
for(String file:listFile){
File fle=new File(path2+file);
if(fle.isDirectory()){
Scanner(filepath+"."+file);
}else{
String name = fle.getName();
String classpath=res+"."+name;
nameMap.put(name,classpath);
}
}
}
/**
* 加载类文件
* @throws ClassNotFoundException
* @throws InstantiationException
* @throws IllegalAccessException
*/
public void loadClassFile() throws ClassNotFoundException, InstantiationException, IllegalAccessException{
if(nameMap.size()<=0){
return ;
}
Collection<String> values = nameMap.values();
for(String path:values){
String claname=path.replaceAll(".class", "");
Class<?> classd = Class.forName(claname);
if(!classd.isInterface()){
Object obj=classd.newInstance();
if(classd.isAnnotationPresent(XiaoService.class)){
XiaoService annotation2 = classd.getAnnotation(XiaoService.class);
String key=null;
String value = annotation2.value();
if(!"null".equals(value)){
key=value;
}else{
key=dealFirst(classd.getSimpleName());
}
annotation.put(key, obj);
}else if(classd.isAnnotationPresent(XiaoController.class)){
XiaoController annotation2 = classd.getAnnotation(XiaoController.class);
String key=null;
String value = annotation2.value();
if(!"null".equals(value)){
key=value;
}else{
key=dealFirst(classd.getSimpleName());
}
annotation.put(key, obj);
}
}
}
}
/**
*
* @param name 原始类名
* @return 首字母小写的类名
*/
public String dealFirst(String name){
String first_word = name.substring(0, 1);
String suString =name.substring(1);
String lowerCase = first_word.toLowerCase();
String finale=lowerCase+suString;
return finale;
}
/**
* 实例化类 并把类关系注入进去
* @throws ClassNotFoundException
*/
public void spring_Ioc() throws ClassNotFoundException{
try{
Collection<Object> values = annotation.values();
for(Object obj:values){
Class<? extends Object> class1 = obj.getClass();
Field[] fields = class1.getDeclaredFields();
for(Field field:fields){
if(field.isAnnotationPresent(XiaoAutoware.class)){
String name = field.getName();
Object object = annotation.get(name);
//字段中如果这个字段是私有的要对这个字段进行设置值
field.setAccessible(true);
//参数一 本对象 参数二 要注入的对象
field.set(obj, object);
}
}
}
}catch(Exception exception){
;
}
}
public void parseURL(HttpServletRequest req, HttpServletResponse resp) throws IllegalAccessException, IllegalArgumentException, InvocationTargetException{
//获取请求参数
StringBuffer requestURL = req.getRequestURL();
String string = requestURL.toString();
String requestURI = req.getRequestURI();
UrlMapping urlMapping = hashmap.get(requestURI);
if(null!=urlMapping){
Object obj = urlMapping.getObj();
Method method = urlMapping.getMethod();
method.invoke(obj, null);
}
}
}
测试框架的使用
package worn.it.controller;
import worn.it.service.UserService;
import xiao.it.annotation.XiaoAutoware;
import xiao.it.annotation.XiaoController;
import xiao.it.annotation.XiaoRequestMapping;
@XiaoController
@XiaoRequestMapping(value="/")
public class UserController {
@XiaoAutoware
private UserService userService;
@XiaoRequestMapping(value="/index")
public String getPage(){
userService.hello();
return "index";
}
}
package worn.it.service;
public interface UserService {
void hello();
}
package worn.it.service;
import xiao.it.annotation.XiaoService;
@XiaoService(value="userService")
public class UserServiceIm implements UserService{
@Override
public void hello() {
// TODO Auto-generated method stub
System.out.println("hello spring mvc");
}
}