使用反射实现接口引擎

news/2024/5/19 5:19:39 标签: 优化, java, 反射

先介绍一下活动模块的背景

  • 活动主要关系活动表和环节表,每个活动有特定的n个环节
  • 活动主要分为两部分(我总结的):
  • (1)、活动页面交互环节(intercation),由用户主动调用服务
  • (2)、程序主动行为(automation),有用户活动期间投资或者新用户注册触发行为

1、新的活动引擎中,新增一个活动基类接口:
只有一个抽象方法,用于引擎自动执行的行为(例如投资以后送红包,以及新注册用户赠送礼物)

/**
 * user zyu
 * datetime 2017/3/22 13:34
 * description
 */
public interface IBaseActivity {
    void autoMation(Map<String,Object> parmMap);
}

2、活动具体实现类,实现IBaseActivity接口

/**
 * user zyu
 * datetime 2017/3/22 13:41
 * description 活动模板
 */
@Service("simpleActivity")
public class SimpleActivity implements IBaseActivity {

    /**
     * method1
     * @param parmMap
     * @return
     */
    public ReturnResult<Map<String,Object>> method1(Map<String,Object> parmMap){
        /**
         * 逻辑实现
         * 返回数据
         */
        return null;
    }

    /**
     * method2
     * @param parmMap
     * @return
     */
    public ReturnResult<Map<String,Object>> method2(Map<String,Object> parmMap){
        /**
         * 逻辑实现
         * 返回数据
         */
        return null;
    }

    @Override
    public void autoMation(Map<String, Object> parmMap) {
        /**
         * 引擎自动行为逻辑实现
         */
    }
}

3、提供通用的活动接口,用于引擎实例(通过Spring 反射实现),这里还要说一点,主要是踩的坑,开始使用的java原生的反射,但是spring 注入的机制就失效了,只能通过手动装配,这点网上大致是这么解释的:因为通过java原生的反射,没有创建类实例,所以类中的注入就不起作用

装载 baseActivity,这里的baseActivity是IBaseActivity类型

/**
 * load baseActivity
 * 装载 baseActivity
 */
if(activityMap.containsKey(activityCode)){
	baseActivity = activityMap.get(activityCode);
}else {
	ActivityInfo activityInfo = activityInfoService.getActivityInfoByCode(activityCode);
	if(null !=activityInfo && null != activityInfo.getReflexClass()
         && !activityInfo.getReflexClass().equals("")){
		baseActivity = SpringContextHolder.getBean(activityInfo.getReflexClass());
		activityMap.put(activityCode , baseActivity);
	}else {
		resultData.setResultCode(0);
		resultData.setErrorCode(ErrorConstants.PARAM_NOT_RIGHT);
		printJson(resultData);
		return null;
	}
}

装载 method,方法名主要有调用服务方传递

/**
 * load aClass and method
 * 装载 aClass method
 */
if(metMap.containsKey((activityCode+methodName))){
	method = metMap.get((activityCode+methodName));
}else {
	if(classMap.containsKey(activityCode+"class")){
		aClass = classMap.get(activityCode+"class");
	}else {
		aClass = baseActivity.getClass();
		classMap.put((activityCode+"class") ,aClass);
	}
	method =  ReflectionUtils.findMethod(aClass, methodName, Map.class);
	metMap.put((activityCode+methodName) ,method);
}
resultData = (ReturnResult<Map<String, Object>>) ReflectionUtils.invokeMethod(method, baseActivity,parmMap);

出于性能考虑,增加了缓存机制

/**
 * cache class and method
 * 缓存反射类和方法
 */
public static Map<String,Class> classMap = new HashMap<String,Class>();
public static Map<String,IBaseActivity> activityMap = new HashMap<String,IBaseActivity>();
public static Map<String,Method> metMap = new HashMap<String,Method>();

4、修改表结构,在活动表中增加COLUMN1字段,用于存放SimpleActivity活动实现类的@Service注解;
而在环节表中增加COLUMN2字段,用于存放环节类型(主要有intercation和automation,具体解释参照上面)

5、在投资或者注册以后有一个映射类(此类的作用就是用作,活动期间投资送礼物和注册赠送礼品什么的),在此类的映射方法中使用反射,具体实现如下:

/**
 * use new activity engine
 * 使用新的活动引擎
 */
ActivityLink activityLink1 = activityLinkDao.findAutoMationLinkByActivityCode(activityCode);
if (null != activityLink1) {
	try {
		Map<String, Object> parmMap = new HashMap<String, Object>();
		IBaseActivity baseActivity = null;
		if (activityMap.containsKey(activityCode)) {
			baseActivity = activityMap.get(activityCode);
		} else {
			if (null != ai && null != ai.getReflexClass()
				&& !ai.getReflexClass().equals("")) {
				baseActivity = SpringContextHolder.getBean(ai.getReflexClass());
				activityMap.put(activityCode, baseActivity);
			}
		}
		if (null != baseActivity) {
			parmMap.put("parm1", null);
			parmMap.put("parm2", null);
			parmMap.put("parm3", null);
			baseActivity.autoMation(parmMap);
		}
	} catch (Exception e) {
	e.printStackTrace();
	}
}
/** new **/

使用这种模式主要有几点好处:

1、简化接口(活动模块提供一个通用接口)
2、增强可读性的可维护性
3、活动模块化,降低耦合度
4、插拔式


http://www.niftyadmin.cn/n/772897.html

相关文章

总结 90 条写 Python 程序的建议

阅读本文大概需要 3 分钟。 本文于网络整理&#xff0c;版权归原作者所有&#xff0c;如来源信息有误或侵犯权益&#xff0c;请联系我删除。 自己写 Python 也有四五年了&#xff0c;一直是用自己的“强迫症”在维持自己代码的质量。都有去看 Google 的 Python 代码规范&…

基于软件的负载均衡(Nginx与ZooKeeper解析)

什么是负载均衡 负载均衡&#xff08;Load Balance&#xff09;是分布式系统架构设计中必须考虑的因素之一&#xff0c;它通常是指&#xff0c;将请求/数据【均匀】分摊到多个操作单元上执行&#xff0c;负载均衡的关键在于【均匀】。常见互联网分布式架构如上&#xff0c;分为…

Python学习之-进程,详细介绍,轻松理解

01、python之进程 进程是执行中的程序。 每一个进程都有它自己的地址空间&#xff0c;一般情况下&#xff0c;包括: 1、文本区域&#xff08;text region&#xff09;&#xff1a;存储处理器执行的代码&#xff0c; 2、数据区域&#xff08;data region&#xff09;&#x…

【经验分享】转行如何自学Python并且找到工作,分享自己心得

目前信息化产业发展势头很好&#xff0c;互联网就成为了很多普通人想要涉及的行业&#xff0c;因为相比于传统行业&#xff0c;互联网行业涨薪幅度大&#xff0c;机会也多&#xff0c;所以就会大批的人想要转行来学习Python开发。 零基础学习Python必须明确的几点&#xff1a; …

如何将bug扼杀在摇篮里

关于bug&#xff0c;我想大家都不陌生&#xff0c;就像是产品世界里的‘恐怖分子’ 也是最不招人喜欢的家伙&#xff0c;主要是因为bug经常潜藏于无形之中&#xff0c;而一旦发作轻则影响用户体验&#xff0c;重则造成经济损失&#xff0c;我们来看一组兑吧近半年的bug数据。 通…

Python实现翻译小工具

一、背景 利用Requests模块获取有道词典web页面的post信息&#xff0c;BeautifulSoup来获取需要的内容&#xff0c;通过tkinter模块生成gui界面。 二、代码 git源码地址 fanyi.py代码如下&#xff1a; #!/bin/env python # -*- coding:utf-8 -*- # _author:kaliarch import …

python连接mysql详解,轻松使用

Python DB-API使用流程: 引入API模块 获取与数据库的连接 执行SQL语句和存储过程 关闭数据库连接 一、接口包安装 1&#xff09;windows环境 下载地址&#xff1a;https://pypi.python.org/pypi/MySQL-python/1.2.5 比如&#xff1a;MySQL-python-1.2.5.win32-py2.7.exe …