公司采用的是spring的mvc架构,但是做了很多改动。spring mvc架构本身提供了几种从url映射contrller的方法。常用的如:SimpleUrlHandlerMapping等。公司的mvc架构在SimpleUrlHandlerMapping基础上做了一层封装。前台不论什么url都会映射到同一个contrller上,然后通过java反射机制来调用具体的处理方法,然后返回相应的ModelAndView。
genericController中的关键代码如下:
protected ModelAndView _handleRequest(HttpServletRequest request, HttpServletResponse response) throws Exception {
request.setCharacterEncoding("UTF-8");
String methodName = this.methodNameResolver.getHandlerMethodName(request);
String moduleName = (String) request.getAttribute(BaseUtils.PARAMNAME + "0");
ModelAndView mav = controllerProcess.invoke(moduleName, methodName, request, response);
return mav;
}
其中methodName为函数名,modelName为模块类名。例如一个请求是以/console.login.do结尾,methodName就为login,moduleName为console,这样根据Java反射机制就会去调用ConsoleController.java里面的login方法来处理这个请求。这个处理过程很复杂,公司的代码写的很乱,很多函数现在都已不使用。
首先有一个properties文件保存modelName到具体controller的映射关系。
appservice=com.wiscom.ccs.web.controller.AppserviceController
reader=com.wiscom.ccs.web.controller.ReaderController
vote=com.wiscom.ccs.web.controller.VoteController
csh=com.wiscom.ccs.web.controller.CSHDateController
程序中得到这样的关系放到map中。然后
private void loadBeanHandlersFromProperties() {
//从propertyies文件得到映射关系
Map map = getPropertiesFromConfigs(this.controllerConfigFiles);
//得到key的迭代器
Iterator it = map.keySet().iterator();
while (it.hasNext()) {
String key = (String) it.next();
String cname = (String) map.get(key);
log.info("load web handler:" + key + "=" + cname);
try {
Class clazz = Class.forName(cname);
BeanHandler bh = new BeanHandler();
bh.setClassz(clazz);
try {
// 实例化
Object obj = BeanUtils.instantiateClass(clazz);
bh.setValue(obj);
this.beanHandlerMap.put(key, obj);
} catch (Throwable e) {
log.error("create '" + clazz.getName() + "' error!");
log.error(e.getMessage(), e);
continue;
}
//结果保存在map中
beanHandlers.add(bh);
} catch (ClassNotFoundException e) {
log.error(e.getMessage(), e);
}
}
}
然后根据得到的modelName从map中得到相应的object。然后来查找methodName:
...
Method[] methods = obj.getClass().getMethods();
for (int i = 0; i < methods.length; i++) {
Method _method = methods[i];
// log.debug("methods:" + _method.getName());
Class returnType = _method.getReturnType();
// log.debug("return class:" + returnType);
if (ModelAndView.class.equals(returnType) || Map.class.equals(returnType)
|| ModelAndMethod.class.equals(returnType)) {
// 找到方法
if (_method.getName().equals(methodName)) {
method = _method;
break;
}
}
}
...
然后得到params并执行,拿参数这段很长:
List params = new ArrayList();
Class[] classes = method.getParameterTypes();
int paramLen = classes.length;
BindException be = null;
for (int i = 0; i < paramLen; i++) {
// 一般参数类型都是下面几种主要的
if (classes[i].equals(HttpServletRequest.class)) {
params.add(request);
} else if (classes[i].equals(HttpServletResponse.class)) {
params.add(response);
} else if (classes[i].equals(HttpSession.class)) {
params.add(getHttpSession(request, response));
} else if (classes[i].equals(WebInput.class)) {
params.add(new WebInput(request));
} else if (classes[i].equals(FileWebInput.class)) {
params.add(new FileWebInput(request));
} else if (classes[i].equals(WebOutput.class)) {
params.add(new WebOutput(request, response));
} else if (classes[i].equals(ApplicationContext.class)) {
params.add(this.getApplicationContext());
} else {
// 其他类型去spring context里拿
Object resultObject = null;
if (beanParameterHandlers != null && beanParameterHandlers.size() > 0) {
Iterator it = beanParameterHandlers.iterator();
while (it.hasNext()) {
BeanHandler bh = (BeanHandler) it.next();
if (classes[i].equals(bh.getClassz())) {
if (bh.getName() != null) {
String bname = bh.getName();
resultObject = this.getApplicationContext().getBean(bname);
} else {
resultObject = bh.getValue();
}
if (resultObject instanceof BeanHandlerFactory) {
try {
resultObject = ((BeanHandlerFactory) resultObject).getValue(request, response);
} catch (ModelAndViewDefiningException e) {
return e.getModelAndView();
} catch (Throwable ex) {
log.error(ex.getMessage(), ex);
return handleException(request, response, ex);
}
}
break;
}
}
}
if (resultObject != null) {
params.add(resultObject);
} else {
// 还没有就直接实例化生成, 这里的是需要绑定的command类
Object command = newCommandObject(classes[i]);
try {
bind(request, command);
params.add(command);
} catch (BindException _be) {
be = _be;
params.add(null);
}
}
}
}
if (be != null) {
if (classes[paramLen - 1].equals(BindException.class)) {
params.add(be);
} else {
throw new ServletRequestBindingException("Errors binding onto object '" + be.getObjectName() + "'",
be);
}
}
// 执行
Object returnValue = method.invoke(obj, params.toArray(new Object[params.size()]));
分享到:
相关推荐
2. **Verilog语言**:Verilog是硬件描述语言(HDL)之一,用于设计和验证数字电子系统的逻辑行为。它允许工程师用代码表示电路,支持模块化设计,便于复用和测试。 3. **Controller设计**:NAND Flash Controller的...
在分析这些原理图时,我们还需要关注电源管理部分,控制器需要稳定的工作电压,因此会有相应的电源稳压和滤波电路。此外,可能还会有LED指示灯或其他辅助功能的电路设计。 总的来说,Atari Jaguar控制器的电路原理...
从压缩包子文件的文件名"Vimeo_Speed_Contoller.crx"来看,这是插件的安装包文件,CRX是Chrome扩展的文件格式,表明这款插件是为Chrome浏览器设计的。用户可以通过将此CRX文件拖放到浏览器的扩展管理页面来安装,...
MATLAB是一种强大的计算环境,特别适合于数值分析、算法开发、数据可视化以及模型构建。 首先,AC to AC控制器的核心是晶闸管(Silicon-Controlled Rectifier,简称SCR),这是一种半导体器件,能够通过控制其触发...
通过用户-角色表(如表4所示)进行连接,实现一个用户可拥有多个角色,一个角色可以分配--------<项目介绍>该资源内项目源码是个人的毕设,代码都测试ok,都是运行成功后才上传资源,答辩评审平均分达到96分,放心...
后台控制器,通常用Java的Spring MVC、Python的Django、Node.js的Express等框架实现,负责接收前端发送的文件数据。当收到前端POST请求时,后台控制器会解析接收到的FormData,从中提取出文件数据。对于图片,可能...
WiFi温度计一个简单的物联网设备来控制吸烟者的体温。 我使用的是Wemos D1 Mini,因为使用ESP-8266可以使用W-LAN连接来发布数据。 就我个人而言,我使用DS18B20温度传感器测量Smoker内部的温度,并通过WiFi和MQTT将...
此web工程实现了连接oracle数据库完成基本功能:查询,插入,删除,更新。连接的数据库为员工信息管理系统,采用Contrller,Service,Dao三层结构,controller层为servlet,下层均有一个接口和一个实现类。...
terraform-RPi为愚蠢的控制器配置使用Terraform为FollyEngine设置RPi控制器将导致: 愚蠢的用户设置 pi用户的密码已更改 .folly.site DNS和* .. folly.site DNS设置以指向尾标IP Docker已安装并正在运行 尾标安装和...
《Arm CoreLink GIC-600 Generic Interrupt Controller 技术参考手册》是关于ARMv8架构下中断控制器GIC-600的详细指南,由ARM Limited或其关联公司版权所有。该手册覆盖了从r1p6版本的多个发布迭代,提供了控制器的...
在这个特定的案例中,"Contoller_Scripting_Examples" 是一个开源存储库,它提供了多种Bitwig控制器脚本的示例,旨在帮助用户理解和应用这一技术。 标题提到的"Bitwig Controller Scripting Examples",意味着这个...
一个简单的用户界面,可使用Adfruit PWM contoller控制基于Arduino的机械臂。 这是一个非常简单的项目,它提供了一个基于Java的(摇摆)应用程序,可以直接控制连接到Adafruit PWM伺服驱动器的电机。 该应用程序使...
Realtek PCLe GBE Family Controllor(win10)安装包,版本号为10.003.0728.2015,支持32位和64位Windows10系统。该驱动除了支持相应的硬件设备功能外,还包括了稳定性和性能提升。Realtek网卡用户可下载安装。
中文版LOGIX5000仿真快速讲解中.
adc inteface through c8051 contoller
STC89S51+双路DS18B20+4为数码管显示PROTEL硬件原理图+PCB工程+软件源码,可以作为你的学习设计参考。 void main() { // uchar i,j; // uart_init(); search_romid_ds18b20();//上电自动搜索两路DS18B20的ROM值,并...
在IT行业中,逆向工程通常是指通过对软件的二进制代码或者数据进行分析,来推导出其设计原理、算法和实现方式的过程。在Java Web开发领域,MyBatis逆向工程(MyBatis Generator,简称MBG)是这样一个工具,它能够...
此轮播图片是由CSS+JavaScript制作完成的,功能还算完整默认每一秒自动切换可更改,鼠标停靠在图片上自动停止自动滑动移出恢复,作者菜鸟一枚如果说有Bug请大家指出,发这东西也为了锻炼锻炼自己提升自己的代码编写...
Blacktip Reef Controller(BRC)是一个综合项目,它结合了硬件和软件的元素,用于管理和控制礁石水族箱的环境参数。这个项目的核心在于利用Arduino微控制器来收集和处理传感器数据,以及通过Servlet和JavaScript...