Java RMI - 将客户端变成服务器
如果我想在我的 RMI 应用程序中启用“双向”通信(即允许服务器调用客户端上的方法,以及允许客户端调用服务器上的方法),最简单的方法就是让客户端进入还有远程课程吗?
另外,如果我打算将客户端实例作为方法参数传递给服务器,我认为不需要将“客户端类”添加到 rmiregistry 中是否正确?
最后一个问题是,我的所有类是否仍然需要在同一个地方编译? IE 我可以在两台完全独立的机器上编译服务器和客户端并期望它们能够正常通信吗?
* 编辑 **
还有一个问题,我的问题引用了我的客户端界面 (IClient):它有一个数组列表(所以我有 ArrayList
)来存储新的客户端的实例,以便服务器可以跟踪注册的客户端。当我尝试在另一台计算机上编译服务器时,它抱怨找不到 IClient - 显然,因为 IClient 在客户端计算机上。我该如何解决这个问题?
If i want to enable 'two way' communication in my RMI Application (That is, allow the server to invoke methods on the client, as well as the client to invoke methods on the server), is the simplest way to make the client into a Remote class as well?
Also if i intend to pass instances of my client to server as a method parameter, am i correct in thinking that there is no need to add the 'client class' to the rmiregistry?
And one final question, do all of my classes still need to be compiled in the same place? I.E can i compile server and client on two entirely independent machines and expect them to communicate properly?
* EDIT **
One more question, my question makes reference to my client interface (IClient): it has an arraylist (so i have ArrayList<IClient>
) to store new instances of the client so the server can keep track of registered clients. When i attempt to compile the server on a different machine, it complains that it cant find IClient - obviously, as IClient is on the client machine. How do i get around this?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(3)
你所有的假设都是对的。
您不必将可远程调用的客户端类添加到 rmi 注册表中,但仍然需要导出它们。
编译的唯一警告是它们必须使用相同版本的 java 和相同的编译器设置(至少是那些影响 RMI 存根生成的设置)来完成。
You're right in all your assumptions.
You don't have to add your remotely callable client classes to the rmi registry but you still have to export them.
The only caveat with the compilation is that they have to be done with the same version of java with the same compiler settings (at least those affecting RMI stub generation).
如果您要求客户端或服务器在未来的部署中位于防火墙后面,请远离 RMI。你这是在自找麻烦。
特别是如果您希望服务器调用客户端。
以下是两个对我们来说效果很好的替代解决方案:
让客户端调用服务器,服务器阻止调用,直到数据可供客户端使用。这会占用每个客户端一个线程(如果您不使用 NIO),但很容易实现。
偶尔返回 null,以防止来自客户端的长时间运行的调用被防火墙关闭(当然,取决于防火墙配置)
如果您想要使用漂亮的 java 接口,请考虑 Hessian 非常轻量级,运行在 HTTP 之上,并且不需要 RMI 注册表或类似的东西
如果您打算向其他客户端开放服务器端,Hessian 仍然是一个不错的选择,但如果担心扩展,请考虑 RESTful 架构风格。
If you have any requirements that the client or server will be behind a firewall in the future deployments, stay away from RMI. You are asking for trouble.
Especially if you want the server to call the client.
Here are two alternative solutions that worked well for us:
have the client call the server with the server blocking the call until data is available for the client. This uses up a thread per client (if you don't use NIO), but is easy to implement.
Return null once in a while to prevent a long running call from the client to be closed by the firewall (depending on the firewall config, of course)
if you want nice java interfaces to play with, consider Hessian which is very light-weight, runs on top of HTTP and does not bother with an RMI registry or similar stuff
if you intend to open up the server side to other clients, Hessian is still a good choice, but if scaling out is a concern, look into a RESTful architectur style.
关于您的最后一个问题,远程接口类及其依赖的所有类等等递归地直到两台主机上都必须存在闭包。
Re your final question, the remote interface classes and all classes they depend on and so on recursively until closure must be present on both hosts.