取消@Asynchronous EJB调用

mal*_*loc 7 java asynchronous ejb java-ee ejb-3.1

我正在编写一个企业Java应用程序,它使用异步EJB 3.1方法并行执行许多任务.为了支持取消长时间运行的任务,我一直在尝试使用Future接口.

不幸的是,future.cancel(true)从客户端应用程序调用似乎对执行任务的bean的会话上下文没有影响,尽管取消调用正在返回true.

我有一个简单的界面:

public interface AsyncInterface
{
    Future<Integer> run() throws Exception;
}
Run Code Online (Sandbox Code Playgroud)

使用bean实现如下:

@Stateless
@Remote(AsyncInterface.class)
public class AsyncBean
{
    @Resource SessionContext myContext;

    @Asynchronous
    public Future<Integer> run() throws Exception
    {
        Integer result = 0;

        System.out.println("Running AsyncBean");

        while(myContext.wasCancelCalled() == false)
        {
            Thread.sleep(2000);
            System.out.println("Working");
        }      

        System.out.println("AsyncBean cancelled");

        return new AsyncResult<Integer>(result);
     }
}
Run Code Online (Sandbox Code Playgroud)

客户端代码很简单:

InitialContext ctx = new InitialContext();
AsyncInterface async = (AsyncInterface)ctx.lookup("AsyncBean/remote");
Future<Integer> future = async.run();

if( future.cancel(true) )
{
     System.out.println("future.cancel() returned true");
}
else
{
     System.out.println("future.cancel() returned false");
}
Run Code Online (Sandbox Code Playgroud)

豆子的输出是"工作"的源源不断; 它永远不会检测到取消.

如果它是相关的,我正在JBoss Application Server 6.0.0上运行该应用程序.我没有找到使用Future接口的取消功能的示例代码,所以我想知道我是否正确使用Future.这种用法看起来是否正确?是否有更好的选项来取消异步EJB方法调用?

Ade*_*ari 2

您必须是return一种Future对象类型,而不是null. 顺便问一下,你没有获得NPE吗?我希望有一个,你的代码有问题。

此外,cancel()不应该被调用。请参阅此处的文档。顺便说一句,根据文档cancel(),不仅不应调用方法,也不应调用任何实例方法。这就引出了一个问题:为什么方法应该返回。我根本不知道,也许它是供将来使用的。但类级别注释表明所有方法都是为了方便向容器提供结果。AsyncResult

因此,我不确定是否可以取消异步 EJB 调用。

[经过一番研究后编辑]

尝试这个实现,

@Stateless
@Remote(AsyncInterface.class)
public class AsyncBean
{
    @Resource SessionContext myContext;

    @Asynchronous
    public Integer run() throws Exception
    {
        Integer result = 0;

        System.out.println("Running AsyncBean");

        while(myContext.wasCancelCalled() == false)
        {
            Thread.sleep(2000);
            System.out.println("Working");
        }      

        System.out.println("AsyncBean cancelled");

        return result;
     }
}
Run Code Online (Sandbox Code Playgroud)

  • @Adeel:async.run() 调用涉及两个 future。第一个(Future 类型)立即返回,第二个(AsyncResult 类型)在调用结束时返回。返回 AsyncResult 将结果设置在第一个 Future 上,可以使用 future.get() 检索该结果。允许在第一个 Future 上调用取消。请参阅此处的文档http://download.oracle.com/javase/1.5.0/docs/api/java/util/concurrent/Future.html (2认同)