我有一个Spring Web MVC应用程序,我需要使用外部设备驱动程序,每次设备收集一些新数据时都会以异步方式返回信息。我们需要在乞讨时将对象传递给start read方法。该对象实现了一个API定义的接口,它声明了回调方法。
当这个回调方法需要在Spring的会话范围内操作某个bean时,问题就会出现。因为当回调实现想要访问Spring bean时,在驱动程序的Thread中调用回调,它会产生一个异常,说明当前线程不在Spring的托管范围内。
我想知道是否有任何方法可以将实现回调接口的对象转换为某种代理,该代理知道有关构造它的会话上下文的信息,这样它就可以通过Spring的上下文对象调用bean方法?
答案 0 :(得分:0)
我认为你正在从错误的一方接近这个问题。我想你希望设备驱动程序回调在用户会话中放置一些结果。但这还不足以显示这些数据,所以(再次猜测)可能涉及一些长轮询,通过会话范围的bean查看会话。
有了这个假设,我建议你每次调用后端驱动程序时生成某种独特的requestId
,并将requestId
放在HTTP会话和回调中。调用回调时,它会将结果推送到某种映射,其中key是分配的requestId
。现在,客户端(谁也知道requestId
)可以查看地图并获取结果。你必须记住同步(普通HttpSession
也是如此)。
如果您有更高级的通知客户端的方式(Comet?WebSockets?),这也可以在此回调中完成。
请注意,从技术上讲,您可以将HttpSession
对象的实例传递给回调实例(但是您可以看到这不适用于Spring会话范围的bean)但是传递会话似乎并不好设计。提供一个间接级别更好。如果将来您希望将该代码重用于命令行或桌面客户端,该怎么办?