论坛首页 Java企业应用论坛

工具:任务重发器 OR 异步执行任务

浏览 1735 次
精华帖 (0) :: 良好帖 (0) :: 新手帖 (0) :: 隐藏帖 (0)
作者 正文
   发表时间:2008-11-26   最后修改:2008-11-26
记录一下项目中产生出来的东西。好不好另当别论,大家可以指点一二。东西没什么含量,主要是解决一个问题时产生的一些想法。希望能有更好的意见。


项目有一个小模块是用RCP来完成的。其中有一个要求就是当网络断开的时候RCP客户端提交的请求能保存下来,等网络连通之后再次发送出去。

因为我们的RCP项目都是通过webservice的方式去推他的数据的,数据的提交方式相对类似,所以打算做一个任务的重发容器。

思路是这样的,使用一个任务类Task用于记录提交失败的方法,把任务存放在一个单例TaskContainer中。然后通过手动或是定时任务去调用TaskExecutor执行未完成的任务。

Task.java记录要执行任务的信息。其中taskType是用于判断任务的类型,是webserivce还是普通service。

	private Class taskClass;
	private String methodName;
	private Object[] args;
	private Class[] params;
	private String taskType = TASK_TYPE_WEBSERVICE;


然后是TaskExecutor中执行Task的方法。很简单~~就是invoke。

	private void invokeTaskWebService(Task task) throws Exception {
		try {

			Object obj = WebServiceUtil.getService(task.getTaskClass());
			buildTaskMethod(task).invoke(obj, task.getArgs());
		} catch (TaskBuildMethodException e) {
			logger.error("创建method时出错!");
			throw e;
		} catch (Exception ex) {
			logger.error("TaskContainer执行异常");
			throw new RuntimeException();
		}
	}



主要的buildTaskMethod方法。有些特殊点的类型不能用obj.getClass()得到。

	/**
	 * 通过task得到method
	 * 
	 * @param task
	 * @return
	 */
	private Method buildTaskMethod(Task task) throws TaskBuildMethodException {
		try {
			Class[] params = new Class[task.getArgs().length];
			if (task.getParams() == null) {
				int i = 0;
				for (Object obj : task.getArgs()) {
					if (obj instanceof List) {
						params[i] = List.class;
					} else if (obj instanceof Map) {
						params[i] = Map.class;
					} else if (obj instanceof Set) {
						params[i] = Set.class;
					} else if (obj instanceof Boolean) {
						params[i] = boolean.class;
					} else {
						params[i] = obj.getClass();
					}
					i++;
				}
			}else{
				params = task.getParams();
			}
			Method method = task.getTaskClass().getMethod(task.getMethodName(),
					params);
			if (method == null) {
				throw new TaskBuildMethodException();
			}
			return method;
		} catch (Exception e) {
			throw new TaskBuildMethodException();
		}
	}


其它的一些代码就不帖了。

任务的执行可以手动也可以是定时器去跑。在RCP本地程序中我是写了一个单例的TaskTimer去跑。在服务端要用到这样的功能话就起上Quartz比较合适。

[size=medium;]其它功能:异步执行任务[/size]
这个东西做完在RCP上运行蛮不错的。在异常出现之后创建一个Task放入容器内,然后找个网络通的时候执行。
其实上面那个功能都用的不太多,后面在项目的过程中发现一个更加实用的功能。


我们的一些功能流程在走到一定的时候会要去执行一些比较耗时的任务。往往这些耗时的任务让我们的流程卡在那边不能动弹,只有执行结束之后才能继续下面的流程。(耗时任务具体为什么要消耗大量的时候就不讲了。)这些耗时任务都有一个特点。他们只是拿到当前流程的一些数据与状态,然后去跑一下。最开始有一个想法是说做一个定时器,对这个流程进行定时查看,查看有没有需要跑的状态记录。但这个是行不通的,因为我们有很多个流程需要这样的功能。就算不需要去定义多个定时器那也是需要去写多个检查方法。

所以就使用了上面所说的那个Task小工具。把过去需要调用的方法写成Task装入TaskExecutor中,然后起一个定时任务去跑容器内的Task,效果蛮不错的,解决了我们之前的问题,达到了异步执行任务的功能,而不影响当前的流程。

论坛首页 Java企业应用版

跳转论坛:
Global site tag (gtag.js) - Google Analytics