GWT:在服务器端调用与客户端相同的RPC方法
这个问题可能看似愚蠢/琐碎,但我根本无法理解如何实现我的目标。 (对不起,如果标题是误导,想不到更好的一个)
我在App Engine服务器上有一个使用GWT的网页。 我得到了客户端代码和服务器代码。 客户端代码可以毫无问题地调用RPC方法(我的问题根本与“gwt-client” 无关 )。
我得到了以下课程:
//MyClassService.java - client package @RemoteServiceRelativePath("myService") public interface MyClassService extends RemoteService{ public doSomething(); } //MyClassServiceAsync.java - client package public interface MyClassServiceAsync{ public void doSomething(AsyncCallback callback); } //MyClassServiceImpl.java - server package public class MyClassServiceImpl extends RemoteServiceServlet implements MyClassService{ @Override public void doSomething() { //does something } }
一个场景和我想要做的事情:我有一个远程客户端,换句话说,一个客户端没有通过“GWT接口”通过页面连接,它是一个客户端,他只是简单地向路径发出GET,POST请求在服务器上(从其他地方)。 这个远程客户端根本没有“使用”GWT。 客户端通过HttpServlet连接,在这个servlet中我想重用RPC机制,这样我就不必重写接口,在客户端并使用依赖于客户端的代码(实现已经是服务器端) )。
要重用服务器端的现有方法,我可以创建一个MyClassServiceImpl.java实例并使用它们。 但正如您在上面所看到的,它们是作为同步方法实现的,因为GWT-RPC在使用GWT-RPC时会自动使调用异步。
我将如何在服务器端重用MyClassServiceImpl并将它们作为异步?
如果我对我正在采取的方法有误,请建议其他解决方案。 例如,一个解决方案可能是远程客户端直接与RemoteServiceServlet通信,而不是创建客户端连接的HttpServlet,但我不知道是否可能(如果是,请告诉我如何)!
谢谢!
编辑 (感谢下面的一些答案,我得到了一些见解,并将尝试改进我的问题):
方法的服务器端实现是SYNCHRONOUS。 意味着它们会阻塞,直到返回结果。 从gwt-client代码调用这些方法时,它们会被“自动”创建为ASYNCHRONOUS,可以通过执行以下操作来调用它们:
MyClassServiceAsync = (MyClassServiceAsync) GWT.create(MyClassService.class); ServiceDefTarget serviceDef = (ServiceDefTarget) service; serviceDef.setServiceEntryPoint(GWT.getModuleBaseURL() + "myService"); service.doSomething(new AsyncCallback() { @Override public void onSuccess(Void result) { //do something when we know server has finished doing stuff } @Override public void onFailure(Throwable caught) { } });
从上面的代码中可以看出,doSomething方法支持AsyncCallback,甚至没有实现它。 这是我在服务器端想要的,所以我不必使用线程或为“async-usage”创建新的实现。 对不起,如果我不清楚!
1)任何客户端都可以使用当前配置调用MyClassServiceImpl.doSomething()
。 MyClassServiceImpl
是一个servlet并且已正确公开。 为了以这种方式实现通信, 客户必须能够“说出”GWT方言以进行数据传输 。 Google可能会为您提供实施此function的库。 我没有用过任何东西,所以我无法提出建议。
一个示例,概念validation设置:检查与Firebug的网络通信,以了解正在发生的事情。 然后尝试用curl
调用服务。
2)如果您不想使用GWT方言,则可以轻松地公开与REST(JSON)或Web服务(SOAP)相同的服务。 有很多库,例如REST案例RestEasy和Jersey 。 你没有提到任何服务器端框架(Spring?Guice?CDI?),所以这个例子很简单。
我建议在一个独立于传输方法的类中实现您的业务方法:
public class MyBusinessLogic { public void doSomething() { ... } }
然后,传输实现使用此业务逻辑类,仅添加特定于传输的内容(例如注释):
GWT:
public class MyClassServiceImpl extends RemoteServiceServlet implements MyClassService{ @Override public void doSomething() { MyBusinessLogic bean = ... // get it from IoC, new, whatever bean.doSomething(); } }
JAX-RS:
@Path("myService") public class MyResource { @GET public void doSomething() { MyBusinessLogic bean = ... // get it from IoC, new, whatever bean.doSomething(); } }
因此,传输端点只是实际function的shell,在一个地方实现,即MyBusinessLogic
类。
这是一个真实的例子吗? 您的方法不带参数,也不返回任何数据。
无论如何,你可以创建一个新的servlet并通过普通的HTTP请求调用它。 然后servlet只调用目标方法:
public class MyNewServlet extends HttpServlet{ protected void doGet(HttpServletRequest request, HttpServletResponse response){ MyBusinessLogic bean = ... // get it from IoC, new, whatever bean.doSomething(); } }
- 如何在不创建新对象的情况下从另一个类访问变量
- AppEngine ClassNotFoundException:com.google.appengine.api.datastore.DatastoreServiceFactory
- 可以将Google模块与Google Plugin for Eclipse一起使用吗?
- Google ClientLogin身份validation
- 元素类型“META”必须由匹配的结束标记“”终止
- 我可以通过配置java.policy文件拒绝访问jvm类吗?
- java.security.AccessControlException:可通过浏览器访问但不在同一服务器内的文件
- 在谷歌应用引擎和GWT中使用SOAP Web服务
- 您何时在Objectify中注册GAE课程?
- Google App Engine Jersey错误格式json
- 在Cloud Endpoints Frameworks 2.0 for App Engine中增强端点