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

cq.web.servlet.BaseServlet Maven / Gradle / Ivy

The newest version!
package cq.web.servlet;

import cq.web.servlet.annotation.*;
import cq.web.servlet.bean.WebNode;
import cq.web.servlet.constant.RequestType;
import cq.web.servlet.exception.WebException;
import cq.web.utils.ClassUtils;
import cq.web.utils.StringUtils;

import javax.servlet.ServletConfig;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.Part;
import java.io.*;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.lang.reflect.Parameter;
import java.util.*;

@SuppressWarnings("serial")
public abstract class BaseServlet extends HttpServlet implements cq.web.servlet.ServletConfig {
    private static Map handleMap = new HashMap<>(); //存储所有请求节点

    @Override
    public void init(ServletConfig config) throws ServletException {
        initRoots();
        onStart();
        super.init(config);
    }

    /**
     * 加载处理请求方法
     */
    private void initRoots() {
        Set classNames = new HashSet<>();
        for (String pack : initPackage()) {
            classNames.addAll(ClassUtils.getClassName(pack, isScanerChildPack()));
        }
        try {
            for (String className : classNames) {
                String handlePath = "";
                boolean allowOrigin = false;
                Class clazz = Class.forName(className);
                if (clazz.isAnnotationPresent(ANNOTATION_WEB)) {
                    if (clazz.isAnnotationPresent(ANNOTATION_HANDLE)) {
                        Handle clazzHandle = clazz.getAnnotation(ANNOTATION_HANDLE);
                        handlePath = StringUtils.addFirstOblihne(clazzHandle.value());
                    }
                    if (clazz.isAnnotationPresent(ANNOTATION_ALLOW_ORIGIN)) {
                        allowOrigin = true;
                    }
                    Method[] methods = clazz.getDeclaredMethods();
                    for (Method method : methods) {
                        if (method.isAnnotationPresent(ANNOTATION_HANDLE)) {
                            boolean isUpload = false;
                            if (method.isAnnotationPresent(ANNOTATION_UPLOAD)) {
                                isUpload = true;
                            }
                            if (method.isAnnotationPresent(ANNOTATION_ALLOW_ORIGIN)) {
                                allowOrigin = true;
                            }
                            if (method.isAnnotationPresent(ANNOTATION_NOT_ORIGIN)) {
                                allowOrigin = false;
                            }
                            boolean isResponse = false;
                            if (method.isAnnotationPresent(ANNOTATION_RESPONSE)) {
                                isResponse = true;
                            }
                            Handle methodHandle = method.getAnnotation(ANNOTATION_HANDLE);
                            WebNode webNode = new WebNode(clazz.newInstance(), method, methodHandle.method(), isUpload, isResponse, allowOrigin);
                            handleMap.put(handlePath + StringUtils.addFirstOblihne(methodHandle.value()) + urlPattern(), webNode);
                        }
                    }
                }
            }
        } catch (Exception e) {
            throw new WebException(e);
        }
    }

    /**
     * 分发请求
     */
    private void doResponse(HttpServletRequest req, HttpServletResponse resp) throws IOException {
        setEncoding(req, resp);
        PrintWriter writer = resp.getWriter();
        String path = req.getRequestURI().replaceFirst(req.getContextPath(), "");
        WebNode webNode = handleMap.get(path);
        if (webNode != null) {
            if (webNode.isAllowOrigin()) {
                resp.setHeader("Access-Control-Allow-Origin", "*");
                resp.setHeader("Access-Control-Allow-Methods", "*");
                resp.setHeader("Access-Control-Allow-Headers", "*");
            }
            if (webNode.getType().type.equals(req.getMethod())) {
                Method method = webNode.getMethod();
                try {
                    Object result;
                    if (webNode.isUpload()) {
                        if (webNode.getType() == RequestType.POST) {
                            result = doUploadFile(req, webNode.getObject(), method);
                        } else {
                            result = method.invoke(webNode.getObject(), false, null);
                        }
                    } else {
                        result = method.invoke(webNode.getObject(), getParams(req, method));
                    }
                    if (webNode.isResponse()) {
                        writer.append((String) result);
                    }
                } catch (Exception e) {
                    throw new WebException(e);
                }
            } else {
                writer.append(requestMethodErrorMsg());
            }
        } else {
            writer.append(handleNotFondMsg());
        }
    }

    /**
     * 文件上传
     *
     * @param req
     * @param obj
     * @param method
     * @return
     */
    private Object doUploadFile(HttpServletRequest req, Object obj, Method method) throws IOException, ServletException, InvocationTargetException, IllegalAccessException {
        Boolean isSuccess = true;
        Upload upload = method.getAnnotation(ANNOTATION_UPLOAD);
        String savePath = upload.value();
        List fileNameList = new ArrayList<>();
        Collection parts = req.getParts();
        if (parts != null && parts.size() > 0) {
            for (Part part : parts) {
                String fileType = getFileType(part);
                String fileName = UUID.randomUUID().toString().replaceAll("-", "");
                try {
                    String realName = fileName + fileType;
                    saveFile(savePath, realName, part);
                    fileNameList.add(realName);
                } catch (Exception e) {
                    isSuccess = false;
                }
            }
        } else {
            isSuccess = false;
        }
        return method.invoke(obj, isSuccess, fileNameList);
    }

    /**
     * 获取上传文件后缀名
     *
     * @param part
     * @return
     */
    private String getFileType(Part part) {
        String header = part.getHeader("Content-Disposition");
        String fileName = header.substring(header.indexOf("filename=\"") + 10, header.lastIndexOf("\""));
        int index = fileName.lastIndexOf(".");
        String fileType = "";
        if (index > 0) {
            fileType = fileName.substring(fileName.lastIndexOf("."));
        }
        return fileType;
    }

    /**
     * 存储文件
     *
     * @param savePath 存储路径
     * @param fileName 文件名
     * @param part
     */
    private void saveFile(String savePath, String fileName, Part part) throws IOException, FileNotFoundException {
        InputStream in = part.getInputStream();
        File file = new File(savePath);
        if (!file.exists()) {
            file.mkdir();
        }
        FileOutputStream out = new FileOutputStream(new File(savePath + fileName));
        byte[] buffer = new byte[1024];
        while (in.read(buffer) != -1) {
            out.write(buffer);
        }
        out.flush();
        out.close();
        in.close();
    }

    /**
     * 设置字符编码
     */
    private void setEncoding(HttpServletRequest req, HttpServletResponse resp) throws IOException {
        req.setCharacterEncoding(charset());
        resp.setContentType("text/html;charset=" + charset());
        resp.setCharacterEncoding(charset());
    }

    /**
     * 获取参数
     */
    private Object[] getParams(HttpServletRequest req, Method m) {
        Parameter[] parameters = m.getParameters();
        Object[] obj = new Object[parameters.length];
        for (int i = 0; i < parameters.length; i++) {
            Object value = null;
            if (parameters[i].isAnnotationPresent(ANNOTATION_PARAM)) {
                value = StringUtils.str2obj(
                        req.getParameter(parameters[i].getDeclaredAnnotation(ANNOTATION_PARAM).value()),
                        parameters[i].getType());
            } else if (parameters[i].isAnnotationPresent(ANNOTATION_REQUEST_BODY)) {
                value = getParams(req);
            }
            obj[i] = value;
        }
        if (isPrintRequestInfo2Console()) {
            System.err.println("[INFO]" + req.getRequestURI() + "(" + req.getMethod() + "):" + getParams(req));
        }
        return obj;
    }

    private String getParams(HttpServletRequest req) {
        Map parameterMap = req.getParameterMap();
        StringBuilder sb = new StringBuilder();
        sb.append("{");
        for (Map.Entry entry : parameterMap.entrySet()) {
            sb.append("\"").append(entry.getKey()).append("\":\"");
            for (String s : entry.getValue()) {
                sb.append(s).append(",");
            }
            sb.deleteCharAt(sb.length() - 1);
            sb.append("\",");
        }
        if (sb.length() > 1) {
            sb.deleteCharAt(sb.length() - 1);
        }
        sb.append("}");
        return sb.toString();
    }

    @Override
    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws IOException {
        doResponse(req, resp);
    }

    @Override
    protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws IOException {
        doResponse(req, resp);
    }

    @Override
    protected void doDelete(HttpServletRequest req, HttpServletResponse resp) throws IOException {
        doResponse(req, resp);
    }

    @Override
    protected void doPut(HttpServletRequest req, HttpServletResponse resp) throws IOException {
        doResponse(req, resp);
    }

    @Override
    public void destroy() {
        onDestroy();
        super.destroy();
    }
}




© 2015 - 2025 Weber Informatics LLC | Privacy Policy