您现在的位置是:首页 > 正文

Java反射调用ashx

2024-02-01 02:35:05阅读 3

这篇文章卡了大概一周,一个是没时间,只能带娃加锻炼间隙挤点时间,一个是碰到了问题卡住了。本篇实现反射调用ashx实现类的基础结构。

首先申明ashx的接口,所有的ashx实现类继承实现该接口的基类

package appcode;
import java.io.*;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
//http执行请求接口
public interface IBaseHttpHandler {
    /// <summary>
    /// 执行请求
    /// </summary>
    /// <param name="request">请求对象</param>
    /// <param name="response">响应对象</param>
    public void ProcessRequest(HttpServletRequest request, HttpServletResponse response);
}

然后实现第一个不需要会话的基类

package appcode;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.File;
import java.io.PrintWriter;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.net.MalformedURLException;
import java.net.URL;
import java.net.URLClassLoader;
import java.lang.Class;
import java.util.ArrayList;
import java.util.Enumeration;
import java.util.jar.JarFile;
import java.util.jar.JarEntry;
import LIS.Core.MultiPlatform.LISContext;
import appcode.IBaseHttpHandler;
//实现不带会话的请求基类
public class BaseHttpHandlerNoSession implements IBaseHttpHandler {
    ///请求对象
    public HttpServletRequest Request=null;

    ///响应对象
    HttpServletResponse Response=null;


    ///输出数据到前台
    private void Write(PrintWriter writer,String str)
    {
        writer.println(str);
        writer.flush();
        writer.close();
    }


    /// <summary>
    /// 执行请求
    /// </summary>
    /// <param name="request">请求对象</param>
    /// <param name="response">响应对象</param>
    public void ProcessRequest(HttpServletRequest request, HttpServletResponse response)
    {
        try {
            Request = request;
            Response = response;
            //前台传入的要调用的方法
            String method = LISContext.GetRequest(request, "Method");
            if (method != "") {
                //得到方法
                Method m = this.getClass().getMethod(method);
                if (m != null) {
                    //执行
                    Object ret = m.invoke(this);
                    PrintWriter writer = response.getWriter();
                    if (ret == null) {
                        Write(writer, "");
                    } else {
                        Write(writer, (String) ret);
                    }
                } else {
                    //没有指定名称的方法
                }
            } else {
                //没按要求传调用方法
            }
        }
        catch (Exception ex)
        {
            ex.printStackTrace();
        }
    }
}

然后实现主中间件中转调用实现的ashx

import appcode.IBaseHttpHandler;

import java.io.*;
import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
import java.util.concurrent.ConcurrentHashMap;
import java.net.URL;
import java.net.URLClassLoader;

import java.util.*;


@javax.servlet.annotation.WebServlet(name = "MianMiddleware")
public class MianMiddleware extends javax.servlet.http.HttpServlet {

    /// <summary>
    /// 缓存路径和类型,允许多线程读一个线程写
    /// </summary>
    private static ConcurrentHashMap<String, Class> hsType = new ConcurrentHashMap<>();

    ///执行post请求
    @Override
    protected void doPost(HttpServletRequest request, HttpServletResponse response)
            throws ServletException, IOException {
        response.setContentType("text/html");
        request.setCharacterEncoding("UTF-8");
        response.setCharacterEncoding("UTF-8");
        String url=request.getRequestURI();
        //解析得到类名
        String className = url.split("\\.")[0];
        PrintWriter writer = response.getWriter();
        //反射得到类型
        Object objDeal = GetObjectByConfString(className,writer);
        //转换处理接口
        if(objDeal!=null)
        {
            //转换成接口
            appcode.IBaseHttpHandler baseDeal=(appcode.IBaseHttpHandler)objDeal;
            baseDeal.ProcessRequest(request,response);
        }
        else
        {
            Write(writer,"为找到名称为:"+className+"的处理类");
        }
    }

    /// <summary>
    /// 通过配置得当对象
    /// </summary>
    /// <param name="confStr">配置/UI/sys/ashx/ashCommonNoSession</param>
    /// <returns></returns>
    public static Object GetObjectByConfString(String confStr,PrintWriter writer) {
        try {
            //取第一部分
            if (confStr.charAt(0) == '/') {
                confStr = confStr.substring(1);
            }
            if (!hsType.containsKey(confStr)) {
                URL urlBase = new File("D:\\Java业余\\jbase\\Lib\\appcode.jar").toURI().toURL();
                //自己生成jar包路径
                URL url = new File("D:\\Java业余\\jbase\\Lib\\AshDemo.jar").toURI().toURL();
                URL[] urls = new URL[]{urlBase,url};
                //加载程序集,这里很重要,一定要指定父加载器,否则加载的类和父加载器的类不认为是一个类
                URLClassLoader loader = new URLClassLoader(urls, MianMiddleware.class.getClassLoader());
                ClassLoader  loader1=Thread.currentThread().getContextClassLoader();
                //加载类
                Class c = loader.loadClass("AshDemo.ashDemo");
                //先写死,后面执行编译和从jar包反射
                hsType.put(confStr, c);
            }
            Class c = hsType.get(confStr);
            //创建对象
            Object o = c.newInstance();
            return o;
        }
        catch (Exception ex) {
            ex.printStackTrace();
        }
        return null;
    }

    //get直接走post的逻辑
    @Override
    protected void doGet(HttpServletRequest request, HttpServletResponse response)
            throws ServletException, IOException {
        doPost(request,response);
    }

    ///输出数据到前台
    private static void Write(PrintWriter writer,String str)
    {
        writer.println(str);
        writer.flush();
        writer.close();
    }

}

在这里插入图片描述

然后实现一个ashx的demo
在这里插入图片描述

测试
在这里插入图片描述

在这里插入图片描述

本次碰到的卡壳问题就是通过URLClassLoader加载的类和创建的对象无法转换成接口类型。明明是一个类型,运行总是报错无法转换。各方资料查看加上自己尝试,发现要指定URLClassLoader类加载器的父加载器,这样父加载器加载的类就不会被重复加载导致类型不匹配了。

下个阶段就是实现文件变化监控和比对ashx实现类代码和jar包时间自动编译jar包供反射调用了。为下图的每个ashx的Java类生成jar包供反射使用而达到脚本化的目的,这样就可以实现业务脚本化和虚拟M层,用虚拟M来兼容打印和仪器接口等。

在这里插入图片描述

卡壳问题没人询问是真痛苦,卡过去了收获不少,有些事看着简单,动手做多多少少还是有些意外的

网站文章

  • mysql事务机制

    mysql事务机制

    一、事务的基本要素(ACID) 1、原子性(Atomicity) 2、一致性(Consistency) 3、隔离性(Isolation) 4、持久性(Durability) 二、事务的并发问题   1...

    2024-02-01 02:34:58
  • 字符串加空格

    题目描述给定一个字符串,在字符串的每个字符之间都加一个空格。输出修改后的新字符串。输入共一行,包含一个字符串。注意字符串中可能包含空格。数据范围1≤字符串长度≤100输出输出增加空格后的字符串。样例输...

    2024-02-01 02:34:52
  • 将训练好的 mmdetection 模型转为 tensorrt 模型

    mmdetection 是商汤科技(2018 COCO 目标检测挑战赛冠军)和香港中文大学开源的基于Pytorch实现的深度学习目标检测工具箱,性能强大,运算效率高,配置化编程,比较容易训练、测试。但...

    2024-02-01 02:34:23
  • 多样性数据源报表如何做?几行代码就能解决。

    多样性数据源报表如何做?几行代码就能解决。

    ​现代应用已经进入多数据源阶段了,不再是一个单一的数据库包打天下,一个应用中会涉及除关系数据库外各种数据源,如文本文件类数据、NOSQL、多维数据库、HTML Webservice等等,即使是关系数据...

    2024-02-01 02:34:17
  • C#读取CSV文件 热门推荐

    C#读取CSV文件功能属性标签反射部分Csv读取的class读取文件读取title(字段名!)读取数据(values)将读取的字段名(title)和数据集合(二维数组)序列化结束语 功能 读取CSV文...

    2024-02-01 02:34:10
  • SpringBoot整合缓存(Caffeine、Redis)

    SpringBoot整合缓存(Caffeine、Redis)

    Bean如果不添加其他信息直接注入一个也行。

    2024-02-01 02:34:02
  • Java将JSON字符串与自定义对象之间的转化

    Java将自定义对象转化为JSON字符串JsonUtil.toJson(A);Java将JSON字符串转化为自定义对象InputStream in = req.getInputStream();String json = Streams.asString(in);A a = JsonUtil.of(json, A.class);

    2024-02-01 02:33:33
  • 算法设计与分析 第三章 动态规划

    算法设计与分析 第三章 动态规划

    一、思维导图 二、经典例题 1.矩阵链乘问题 (1)最优子结构证明: 假设有一个连续相乘的矩阵,要使相乘的次数最少。现在假设,x{i…j}是一个最优加括号方案。那么x{i…j} = x{i,k}+x{k+1,j},若x{i…k}是不是其子问题的最优解,那么一定存在一个y{i…k}为其子问题的最优解,那么一定有y{i…k}+x{k+1}

    2024-02-01 02:33:27
  • Qt QStandardItemModel用法(超级详细)

    Qt QStandardItemModel用法(超级详细)

    QStandardItemModel 是标准的以项数据(item data)为基础的标准数据模型类,通常与 QTableView 组合成 Model/View 结构,实现通用的二维数据的管理功能。本节介绍 QStandardltemModel 的使用,主要用到以下 3 个类:QStandardItemModel:基于项数据的标准数据模型,可以处理二维数据。维护一个二维的项数据数组,每个项是一...

    2024-02-01 02:33:20
  • post发送后加号丢失

    +为post特殊字符,所以传递后会丢失,要解诀这个问题,首先要加传递的内容进行加密。然后再解密。C#编码:Server.UrlEncode(ur)C#解码:Server.UrlDecodeJquery解码:decodeURIComponent(url);Jquery编码:encodeURIComponent(url);...

    2024-02-01 02:32:52