All Downloads are FREE. Search and download functionalities are using the official Maven repository.

cn.tom.mvc.core.ControllerInvoke Maven / Gradle / Ivy

There is a newer version: 1.0.3
Show newest version
package cn.tom.mvc.core;

import java.io.IOException;
import java.io.InputStream;
import java.lang.annotation.Annotation;
import java.lang.reflect.*;
import java.util.Map;

import cn.tom.mvc.annotation.Handler.Resource;
import cn.tom.mvc.annotation.ContentType;
import cn.tom.mvc.annotation.Response.Html;
import cn.tom.mvc.annotation.Response.Json;
import cn.tom.mvc.annotation.Response.Stream;
import cn.tom.mvc.ext.BeanFactory;
import cn.tom.mvc.ext.HTTPConverter;
import cn.tom.mvc.ext.JavassistUtil;
import cn.tom.mvc.interceptor.ActionInvocation;
import cn.tom.kit.clazz.Converter;
import cn.tom.kit.clazz.ReflectUtil;
import cn.tom.kit.io.FileUtil;

/**
 * 一条URL 请求 的 处理过程  field,annotation,action,method
 */
public class ControllerInvoke {
	private ActionInvocation actionInvocation;
	private ControllerModel control;
	
	public ControllerInvoke(ActionInvocation _actionInvocation) {
		actionInvocation = _actionInvocation;
		control = _actionInvocation.getAppControl();
	}

	/* action通用处理,是继承,非拦截 */
	public boolean beforeControl() throws Exception {
		Method m = control.getClass().getMethod("before", RequestContext.class, Map.class);
		return (Boolean) m.invoke(control, actionInvocation.getRequestContext(), actionInvocation.getParaMap());
	}

	/* 得到所有的属性 */
	private Field[] loadField(Class c) {
		return c.getDeclaredFields();
	}

	/*
	 * 解析属性, 根据annation 赋值 
	 */
	public void paserFieldAnotation() throws IllegalArgumentException, IllegalAccessException {
		if(control.isPaserField()) return;
		Field[] fields = loadField(control.getClass());
		for (Field field : fields) {
			//if(field.get(control) != null) continue; // 如果已经初始化
			Annotation[] anos = loadAnnotation(field);
			if (anos.length > 0) {
				Resource resource = field.getAnnotation(Resource.class);
				if(resource != null){
					try{
						field.setAccessible(true);  //无视 修饰符, 设置可见
						/* 设置属性的值 参数1-设置的实例化对象,参数2-设置的值 */
						field.set(control, BeanFactory.getInstance(resource.value()));
					}catch(Exception e){
						throw new CocookException(e);
					}
				}
			}
		}
		control.setPaserField(true);
	}

	/* 得到指定的annotation数组 */
	private  Annotation[] loadAnnotation(T obj) {
		return ((AnnotatedElement) obj).getAnnotations();
	}

	public Object parserControllerMethod() throws Exception {
		/* 得到对应methodName的方法 */
		String methodUrl=  actionInvocation.getMapping().getPath();
		Method me = actionInvocation.getMethod();
		Object obj = null;
		if(me==null) {
			actionInvocation.getRequestContext().error(404, 
				methodUrl+" not found on action["+actionInvocation.getAppControl().getClass().getSimpleName()+"]");
			return null;
		}
		
		if (beforeControl()) { // 预先处理
			Annotation[] anos = loadAnnotation(me);
			if (anos.length == 0) {
				obj = invoke(me);
			} else {
				obj = paserMethodAnnotation(me);
			}
		}
		
		return obj;
	}

	/**
	 * 对方法annotation进行解析
	 * 
	 * @param me
	 * @param control
	 * @param map
	 * @return
	 * @throws Exception
	 */
	private Object paserMethodAnnotation(Method _me) throws IOException{

		/* passer HttpMethod annotation */
		Object obj = invoke(_me);

		/* passer ex annotation */
		obj = control.extAnnnotation(obj, _me, actionInvocation.getParaMap());

		if (obj == null) {
			return null;
		}
		
		/* passer Json annotation */
		if (_me.isAnnotationPresent(Json.class)) {
			actionInvocation.getRequestContext().printJSON(obj);
			return null;
		}
		
		/* passer Html annotation */
		if (_me.isAnnotationPresent(Html.class)) {
			actionInvocation.getRequestContext().printHTML(obj);
			return null;
		}

		/* passer Stream annotation */
		if (_me.isAnnotationPresent(Stream.class)) {
			paserStream(_me, obj);
			return null;
		}

		return obj;
	}

	private void paserStream(Method _me, Object _obj) throws IOException {
		if (_obj instanceof InputStream) {
			Stream in = _me.getAnnotation(Stream.class);
			if(in.value()==ContentType.Image){
				actionInvocation.getResponse().setContentType("image/jpeg");;
				
				FileUtil.copy((InputStream)_obj, actionInvocation.getResponse().getOutputStream());
				return;
			}
			
			FileUtil.copy((InputStream) _obj, actionInvocation.getResponse().getOutputStream());
		} else {
			throw new IllegalArgumentException("Reflect.paserMethodAnnotation: error return type,no inputStream found");
		}
	}

	/**
	 * 返回方法执行后的返回值
	 * 
	 * @param me
	 * @param control
	 * @param map
	 * @return
	 * @throws Exception
	 */
	private Object invoke(Method _me) {
		String paramNames[] = null;
		Class[] _class = _me.getParameterTypes();
		Object[] params = new Object[_class.length];
		for (int i = 0; i < _class.length; i++) {
			Class clazz = _class[i];
			if (HTTPConverter.canConvertRequestContext(clazz)) {
				params[i] = HTTPConverter.coverterclass2RequestContext(clazz, actionInvocation);
			} else if (Converter.canConvertValue(clazz)) {
				if (paramNames == null) {
					paramNames = JavassistUtil.getMethodParamNames(control.getClass(), _me);
				}
				params[i] = Converter.coverterClass2Value(clazz, null, actionInvocation.getParaMap().get(paramNames[i]));

			} else {
				params[i] = ReflectUtil.mapToBean(actionInvocation.getParaMap(), clazz);
			}
		}

		return ReflectUtil.invokeMethod(control, _me, params);
	}

}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy