Saturday, December 30, 2017

GWT and Spring MVC

In this post I'd like to share the code I developed in May of 2011 when started to work with GWT.

The first thing I did not like was the way how it integrated with the server side. The typical usage of server is to work with it through the RPC using the Servlets. Ok good, but what if I use another technology built a top of Servlets? SparkJava, Spring MVC, whatever? Any framework which follows the Front Controller / MVC paradigm.

Check these resources to get know on which patterns Spring MVC is built around:
https://martinfowler.com/eaaCatalog/frontController.html, https://martinfowler.com/eaaCatalog/applicationController.html, https://martinfowler.com/eaaCatalog/pageController.html).

It violates these principles since I need to add some Servlets responsible for the RPC somewhere aside. For example what if I need to get current Locale or cover with Filter security (f.e. Spring Security) in the code of that Servlets? For the Spring MVC Controller I have it all out of the box. Also I do not like mixing Servlet code which is infrastructure code with the logical/business code: when I need to create the RPC endpoint I need to extend the com.google.gwt.user.server.rpc.RemoteServiceServlet class which is servlet and put the business code there.

To solve these problems I developed very elegant integration with Spring MVC (Spring Framework) where you as the developer can focus on business and forget about the infrastructure and utilize all the power of Spring Framework.

Here it is: https://github.com/deventh/gwt.rpc.springmvc. This is upgraded version of the previous version: https://github.com/deventh/gwtrpcspringmvc with some changes: GWT RequestFactory approach is dropped and Async. Servlet 3.0 approach is added. So the performance is must be better now due no blocking nature. Find the framework and examples how to use there.

So now just forget about the Servlets stuff and start to build the software in the Spring way. The Eclipse IDE GWT plugin generates sample demo application with the greeting service (http://www.gwtproject.org/doc/latest/tutorial/create.html) as the demo project. Lets change it using my framework. How it will look like?

Client service looks the same

package com.github.deventh.gwt.rpc.springmvc.application.client;

import com.google.gwt.user.client.rpc.RemoteService;
import com.google.gwt.user.client.rpc.RemoteServiceRelativePath;

@RemoteServiceRelativePath("greet/greetingService.gwt")
public interface GreetingService extends RemoteService {
 String greetServer(String name);
}

But it implementation looks different: no need to extend the Servlet anymore and somehow get the reference to the current Spring Context and extract beans form there. So here it is:


package com.github.deventh.gwt.rpc.springmvc.application.server;

import com.github.deventh.gwt.rpc.springmvc.application.client.AnotherService;
import com.github.deventh.gwt.rpc.springmvc.application.client.GreetingService;
import org.springframework.stereotype.Service;

import java.text.MessageFormat;

@Service("greetingService")
public class GreetingServiceImpl implements GreetingService, AnotherService {
 @Override
 public String greetServer(String name) throws IllegalArgumentException {
  return MessageFormat.format("Hello, {0}!", name);
 }
}

How this Remote Service is published and how it takes care about the serving the request - this is what this framework does. Even more as I mentioned above the server performance (capacity) is better due it async. nature. It is built using Java 8, Servlet 3.0 and Spring Framework 4.x. If you need downgrade in some technologies - try to use prev. version or make the modifications you need.

In this repo you can find some examples how to use it. You can also define the the way Application Exceptions are mapped to the client Exceptions and how to sue it with the Spring Security for some situations like session is expired.

Just a few works about how it is working under the hood. The new Handler mapping is registered which is responsible for the serving requests. It uses the  in the com.google.gwt.user.server.rpc.RemoteServiceServlet async way if allowed. But before that is scans for all the available Spring Beans which extend the Remote Service.

So that's is, develop nice apps with the cool logic using GWT and forget about the infrastructure!



No comments:

Post a Comment

Design Patterns Wrapper revisited

 Now lots of software designed and developed following microservice architecture. Components need to communicate with each other via VO (val...