SlideShare a Scribd company logo
Leif Åstrand
Product Manager
Comparing GWT
Transport Mechanisms
lördag 24 januari 15
Transport
lördag 24 januari 15
RequestBuilder builder = new RequestBuilder(RequestBuilder.GET, url);
try {
builder.sendRequest(requestDataString, new RequestCallback() {
@Override
public void onResponseReceived(Request request, Response response) {
int statusCode = response.getStatusCode();
String text = response.getText();
}
@Override
public void onError(Request request, Throwable exception) {
// TODO Handle asynchronous problems
}
});
} catch (RequestException e) {
// TODO Handle synchronous problems
}
RequestBuilder
lördag 24 januari 15
Good
• It just works
Bad
• Low level
RequestBuilder
lördag 24 januari 15
Real world usage
8 %
lördag 24 januari 15
What to send?
lördag 24 januari 15
public class Contact {
private String name;
private int yearOfBirth;
private List<String> emailAddresses;
private Address address;
public static class Address {
private String street;
private String city;
}
// + Getters and setters
}
Contact
lördag 24 januari 15
String data = contact.getName();
data += "," + contact.getYearOfBirth();
String[] parts = data.split(",");
contact.setName(parts[0]);
contact.setYearOfBirth(Integer.parseInt(parts[1]));
String conversion
lördag 24 januari 15
String data = contact.getName();
data += "," + contact.getYearOfBirth();
String[] parts = data.split(",");
contact.setName(parts[0]);
contact.setYearOfBirth(Integer.parseInt(parts[1]));
String conversion
lördag 24 januari 15
{
	 name: "John Doe",
	 yearOfBirth: 1900,
	 address: {
	 	 street: "Happy Street 1",
	 	 city: "Turku"
	 },
	 emailAddresses: ["john@doe.com", "johndoe@gmail.com"]
}
JSON
lördag 24 januari 15
JSONObject json = JSONParser.parseStrict(string).isObject();
contact.setName(json.get("name").isString().stringValue());
contact.setYearOfBirth(
(int) json.get("yearOfBirth").isNumber().doubleValue());
contact.setAddress(
parseAddress(json.get("address").isObject()));
JSONArray emailAddresses =
json.get("emailAddresses").isArray();
for (int i = 0; i < emailAddresses.size(); i++) {
contact.getEmailAddresses().add(
emailAddresses.get(i).isString().stringValue());
}
}
JSONValue parsing
lördag 24 januari 15
Good
• It’s standard
• Human readable
format
• Compact format
Bad
• Not completely
typesafe
• Boilerplate
• Client only
JSONValue
lördag 24 januari 15
What about the
server?
lördag 24 januari 15
ObjectMapper mapper = new ObjectMapper();
try {
Contact contact = mapper.readValue(string, Contact.class);
} catch (VariousExceptions e) {
// Do something sensible
}
Jackson on the server
lördag 24 januari 15
Reflection
Code generation
lördag 24 januari 15
public static interface ContactMapper extends
ObjectMapper<Contact> {}
public Contact parseContact(String string) {
ContactMapper mapper = GWT.create(ContactMapper.class);
Contact contact = mapper.read(jsonString);
return contact;
}
gwt-jackson
lördag 24 januari 15
Good
• Minimal boiler plate
• Can share code
between server and
client
Bad
• Only creating and
reading strings
Jackson
lördag 24 januari 15
Where to send?
lördag 24 januari 15
public interface ContactService {
public void saveContact(Contact contact);
public List<Contact> getContacts();
}
Remote Procedure Call
lördag 24 januari 15
public interface ContactService {
public AsyncResult<Void> saveContact(Contact contact);
public AsyncResult<List<Contact>> getContacts();
}
Asynchronous
public interface ContactServiceAsync {
public void saveContact(Contact contact,
AsyncCallback<Void> callback);
public void getContacts(AsyncCallback<List<Contact>>
callback);
}
lördag 24 januari 15
Good
• Simple but powerful
concept
• The default solution
• Optimized format
Bad
• Sending the entire
object graph
• Polymorphism can
cause huge files
• Optimized format
GWT-RPC
lördag 24 januari 15
Most popular!
51 %
lördag 24 januari 15
Where to send
JSON?
lördag 24 januari 15
GET /contacts
DELETE /contacts/5
PUT /contacts { name: "John Doe", ... }
REST
lördag 24 januari 15
@Path("/contacts")
public interface ContactsService {
@GET
public List<Contact> listContacts();
@Path("/{id}")
@DELETE
public void deleteContact(@PathParam("id") int id);
@PUT
public void createContact(Contact contact);
}
JAX-RS
lördag 24 januari 15
@Path("/contacts")
public interface ContactsService extends DirectRestService {
// Same content
}
ContactsService contactsService =
GWT.create(ContactsService.class);
REST.withCallback(myContactListCallback).
call(contactsService).listContacts();
resty-gwt
lördag 24 januari 15
Good
• Any server
• Any client
Bad
• Some boilerplate
resty-gwt
lördag 24 januari 15
Real world usage
6 %
lördag 24 januari 15
Wild ideas
lördag 24 januari 15
Send interfaces
instead of objects
lördag 24 januari 15
public interface Contact {
public void setName(String name);
public String getName();
public void setYearOfBirth(int yearOfBirth);
public int getYearOfBirth();
public void setAddress(Address address);
public Address getAddress();
public void setEmailAddresses(List<String> addresses);
public List<String> getEmailAddresses();
}
Contact interface
lördag 24 januari 15
New possibilities
Send partial updates
Manage entity identity
Use instance methods for RPC
lördag 24 januari 15
Good
• Entities do not need
to be GWT
compatible
• Combines RPC and
entity management
• Automatic request
handling
Bad
• Complex setup
• Heavy coupling with
the server
RequestFactory
lördag 24 januari 15
Define message
Generate code
lördag 24 januari 15
message Contact {
required string name = 1;
required int32 yearOfBirth = 2;
repeated string emailAddresses = 3;
optional Address address = 4;
}
Contact message
lördag 24 januari 15
Good
• Any language
• Google's data
interchange format
• Backwards
compatible
Bad
• Binary format
• Not very widely
used
Protocol Buffers
lördag 24 januari 15
What if we put
the server in
control?
lördag 24 januari 15
lördag 24 januari 15
public class ContactState extends SharedState {
public String name;
@DelegateToWidget
public int yearOfBirth;
}
@OnStateChange("name")
private void updateName() {
doSomethingWithTheName(getState().name);
}
@Override
protected ContactState getState() {
return (ContactState) super.getState();
}
State synchronization
lördag 24 januari 15
public interface ContactRpc extends ServerRpc {
public void deleteContact(int id);
}
// Register RPC handler on the server
registerRpc(new ContactRpc() {
@Override
public void deleteContact(int id) {
ContactDAO.deleteById(id);
}
});
// Send RPC from the client
public void sendDelete(int contactId) {
getRpcProxy(ContactRpc.class).deleteContact(contactId);
}
RPC
lördag 24 januari 15
Good
• Stateful server
• Server push
Bad
• Stateful server
• Tied to the
framework
Vaadin Connectors
lördag 24 januari 15
What if we
completely hide
the transport?
lördag 24 januari 15
// Fire event
@Inject
Event<Contact> contactEvent;
public void updateContact(Contact contact) {
contactEvent.fire(contact);
}
// Listen to event
public void contactUpdateObserver(@Observes Contact contact) {
ContactDAO.updateContact(contact);
}
CDI events
lördag 24 januari 15
Good
• Transparent
communication
• Server push
Bad
• Transparent
communication
• Tied to the
framework
Errai Bus
lördag 24 januari 15
Questions?
Answers?
Please rate the talk at
gwtcreate.com/agenda
? leif@vaadin.com
lördag 24 januari 15

More Related Content

PDF
DOM-based Test Adequacy Criteria for Web Applications
PDF
Understanding JavaScript Event-based Interactions
PPTX
Hidden-Web Induced by Client-Side Scripting: An Empirical Study
PPTX
Introduction to R2DBC
PPTX
Kostas Kloudas - Complex Event Processing with Flink: the state of FlinkCEP
PDF
Challenges in knowledge graph visualization
PDF
Git Intermediate Workshop slides v1.3
PPTX
Flink Forward Berlin 2017: Kostas Kloudas - Complex Event Processing with Fli...
DOM-based Test Adequacy Criteria for Web Applications
Understanding JavaScript Event-based Interactions
Hidden-Web Induced by Client-Side Scripting: An Empirical Study
Introduction to R2DBC
Kostas Kloudas - Complex Event Processing with Flink: the state of FlinkCEP
Challenges in knowledge graph visualization
Git Intermediate Workshop slides v1.3
Flink Forward Berlin 2017: Kostas Kloudas - Complex Event Processing with Fli...

What's hot (14)

PDF
Gyula Fóra - RBEA- Scalable Real-Time Analytics at King
PDF
Streaming Analytics & CEP - Two sides of the same coin?
PDF
ETW - Monitor Anything, Anytime, Anywhere (Velocity NYC 2017)
PDF
Analyzing Blockchain Transactions in Apache Spark with Jiri Kremser
PPTX
Fabian Hueske_Till Rohrmann - Declarative stream processing with StreamSQL an...
PDF
Git intermediate workshop slides v1.4
PDF
Apache Flink Meetup: Sanjar Akhmedov - Joining Infinity – Windowless Stream ...
PPTX
Event sourcing anug 20190227
PPTX
Stephan Ewen - Stream Processing as a Foundational Paradigm and Apache Flink'...
PPT
Creating Cubes using Cognos 8 Framework Manager
PDF
Kotlin + spring boot = decision making platform
PPTX
Keynote: Stephan Ewen - Stream Processing as a Foundational Paradigm and Apac...
PDF
Processing large-scale graphs with Google(TM) Pregel by MICHAEL HACKSTEIN at...
Gyula Fóra - RBEA- Scalable Real-Time Analytics at King
Streaming Analytics & CEP - Two sides of the same coin?
ETW - Monitor Anything, Anytime, Anywhere (Velocity NYC 2017)
Analyzing Blockchain Transactions in Apache Spark with Jiri Kremser
Fabian Hueske_Till Rohrmann - Declarative stream processing with StreamSQL an...
Git intermediate workshop slides v1.4
Apache Flink Meetup: Sanjar Akhmedov - Joining Infinity – Windowless Stream ...
Event sourcing anug 20190227
Stephan Ewen - Stream Processing as a Foundational Paradigm and Apache Flink'...
Creating Cubes using Cognos 8 Framework Manager
Kotlin + spring boot = decision making platform
Keynote: Stephan Ewen - Stream Processing as a Foundational Paradigm and Apac...
Processing large-scale graphs with Google(TM) Pregel by MICHAEL HACKSTEIN at...
Ad

Similar to Comparing GWT Transport Mechanisms (16)

PDF
Comparing GWT Transport Mechanisms
PDF
Vaadin 7
PDF
Introduction to Vaadin 7
PPTX
Gwt session
PPT
Gwt and rpc use 2007 1
PPTX
Gwt session
PDF
JavaCro'15 - GWT integration with Vaadin - Peter Lehto
PPT
Google Web Toolkits
PDF
Javaland 2014 / GWT architectures and lessons learned
PDF
GWT integration with Vaadin
PPT
Gwt Presentation1
PPT
Google Dev Day2007
PPT
Google Web Toolkit Introduction - eXo Platform SEA
PDF
Building Blueprint With Gwt
PDF
Gwt Presentation
PPTX
YaJUG: What's new in GWT2
Comparing GWT Transport Mechanisms
Vaadin 7
Introduction to Vaadin 7
Gwt session
Gwt and rpc use 2007 1
Gwt session
JavaCro'15 - GWT integration with Vaadin - Peter Lehto
Google Web Toolkits
Javaland 2014 / GWT architectures and lessons learned
GWT integration with Vaadin
Gwt Presentation1
Google Dev Day2007
Google Web Toolkit Introduction - eXo Platform SEA
Building Blueprint With Gwt
Gwt Presentation
YaJUG: What's new in GWT2
Ad

Recently uploaded (20)

PDF
SAP S4 Hana Brochure 3 (PTS SYSTEMS AND SOLUTIONS)
PDF
wealthsignaloriginal-com-DS-text-... (1).pdf
PPTX
Computer Software and OS of computer science of grade 11.pptx
PPTX
Agentic AI Use Case- Contract Lifecycle Management (CLM).pptx
PDF
EN-Survey-Report-SAP-LeanIX-EA-Insights-2025.pdf
PPTX
Odoo POS Development Services by CandidRoot Solutions
PDF
Upgrade and Innovation Strategies for SAP ERP Customers
PDF
Understanding Forklifts - TECH EHS Solution
PDF
Internet Downloader Manager (IDM) Crack 6.42 Build 41
PDF
Cost to Outsource Software Development in 2025
PDF
Designing Intelligence for the Shop Floor.pdf
PPTX
Lecture 3: Operating Systems Introduction to Computer Hardware Systems
PPTX
Log360_SIEM_Solutions Overview PPT_Feb 2020.pptx
PDF
Odoo Companies in India – Driving Business Transformation.pdf
PDF
Adobe Premiere Pro 2025 (v24.5.0.057) Crack free
PDF
Design an Analysis of Algorithms II-SECS-1021-03
PDF
Design an Analysis of Algorithms I-SECS-1021-03
PDF
System and Network Administraation Chapter 3
PDF
Nekopoi APK 2025 free lastest update
PPTX
Operating system designcfffgfgggggggvggggggggg
SAP S4 Hana Brochure 3 (PTS SYSTEMS AND SOLUTIONS)
wealthsignaloriginal-com-DS-text-... (1).pdf
Computer Software and OS of computer science of grade 11.pptx
Agentic AI Use Case- Contract Lifecycle Management (CLM).pptx
EN-Survey-Report-SAP-LeanIX-EA-Insights-2025.pdf
Odoo POS Development Services by CandidRoot Solutions
Upgrade and Innovation Strategies for SAP ERP Customers
Understanding Forklifts - TECH EHS Solution
Internet Downloader Manager (IDM) Crack 6.42 Build 41
Cost to Outsource Software Development in 2025
Designing Intelligence for the Shop Floor.pdf
Lecture 3: Operating Systems Introduction to Computer Hardware Systems
Log360_SIEM_Solutions Overview PPT_Feb 2020.pptx
Odoo Companies in India – Driving Business Transformation.pdf
Adobe Premiere Pro 2025 (v24.5.0.057) Crack free
Design an Analysis of Algorithms II-SECS-1021-03
Design an Analysis of Algorithms I-SECS-1021-03
System and Network Administraation Chapter 3
Nekopoi APK 2025 free lastest update
Operating system designcfffgfgggggggvggggggggg

Comparing GWT Transport Mechanisms

  • 1. Leif Åstrand Product Manager Comparing GWT Transport Mechanisms lördag 24 januari 15
  • 3. RequestBuilder builder = new RequestBuilder(RequestBuilder.GET, url); try { builder.sendRequest(requestDataString, new RequestCallback() { @Override public void onResponseReceived(Request request, Response response) { int statusCode = response.getStatusCode(); String text = response.getText(); } @Override public void onError(Request request, Throwable exception) { // TODO Handle asynchronous problems } }); } catch (RequestException e) { // TODO Handle synchronous problems } RequestBuilder lördag 24 januari 15
  • 4. Good • It just works Bad • Low level RequestBuilder lördag 24 januari 15
  • 5. Real world usage 8 % lördag 24 januari 15
  • 6. What to send? lördag 24 januari 15
  • 7. public class Contact { private String name; private int yearOfBirth; private List<String> emailAddresses; private Address address; public static class Address { private String street; private String city; } // + Getters and setters } Contact lördag 24 januari 15
  • 8. String data = contact.getName(); data += "," + contact.getYearOfBirth(); String[] parts = data.split(","); contact.setName(parts[0]); contact.setYearOfBirth(Integer.parseInt(parts[1])); String conversion lördag 24 januari 15
  • 9. String data = contact.getName(); data += "," + contact.getYearOfBirth(); String[] parts = data.split(","); contact.setName(parts[0]); contact.setYearOfBirth(Integer.parseInt(parts[1])); String conversion lördag 24 januari 15
  • 10. { name: "John Doe", yearOfBirth: 1900, address: { street: "Happy Street 1", city: "Turku" }, emailAddresses: ["john@doe.com", "johndoe@gmail.com"] } JSON lördag 24 januari 15
  • 11. JSONObject json = JSONParser.parseStrict(string).isObject(); contact.setName(json.get("name").isString().stringValue()); contact.setYearOfBirth( (int) json.get("yearOfBirth").isNumber().doubleValue()); contact.setAddress( parseAddress(json.get("address").isObject())); JSONArray emailAddresses = json.get("emailAddresses").isArray(); for (int i = 0; i < emailAddresses.size(); i++) { contact.getEmailAddresses().add( emailAddresses.get(i).isString().stringValue()); } } JSONValue parsing lördag 24 januari 15
  • 12. Good • It’s standard • Human readable format • Compact format Bad • Not completely typesafe • Boilerplate • Client only JSONValue lördag 24 januari 15
  • 14. ObjectMapper mapper = new ObjectMapper(); try { Contact contact = mapper.readValue(string, Contact.class); } catch (VariousExceptions e) { // Do something sensible } Jackson on the server lördag 24 januari 15
  • 16. public static interface ContactMapper extends ObjectMapper<Contact> {} public Contact parseContact(String string) { ContactMapper mapper = GWT.create(ContactMapper.class); Contact contact = mapper.read(jsonString); return contact; } gwt-jackson lördag 24 januari 15
  • 17. Good • Minimal boiler plate • Can share code between server and client Bad • Only creating and reading strings Jackson lördag 24 januari 15
  • 18. Where to send? lördag 24 januari 15
  • 19. public interface ContactService { public void saveContact(Contact contact); public List<Contact> getContacts(); } Remote Procedure Call lördag 24 januari 15
  • 20. public interface ContactService { public AsyncResult<Void> saveContact(Contact contact); public AsyncResult<List<Contact>> getContacts(); } Asynchronous public interface ContactServiceAsync { public void saveContact(Contact contact, AsyncCallback<Void> callback); public void getContacts(AsyncCallback<List<Contact>> callback); } lördag 24 januari 15
  • 21. Good • Simple but powerful concept • The default solution • Optimized format Bad • Sending the entire object graph • Polymorphism can cause huge files • Optimized format GWT-RPC lördag 24 januari 15
  • 22. Most popular! 51 % lördag 24 januari 15
  • 24. GET /contacts DELETE /contacts/5 PUT /contacts { name: "John Doe", ... } REST lördag 24 januari 15
  • 25. @Path("/contacts") public interface ContactsService { @GET public List<Contact> listContacts(); @Path("/{id}") @DELETE public void deleteContact(@PathParam("id") int id); @PUT public void createContact(Contact contact); } JAX-RS lördag 24 januari 15
  • 26. @Path("/contacts") public interface ContactsService extends DirectRestService { // Same content } ContactsService contactsService = GWT.create(ContactsService.class); REST.withCallback(myContactListCallback). call(contactsService).listContacts(); resty-gwt lördag 24 januari 15
  • 27. Good • Any server • Any client Bad • Some boilerplate resty-gwt lördag 24 januari 15
  • 28. Real world usage 6 % lördag 24 januari 15
  • 29. Wild ideas lördag 24 januari 15
  • 30. Send interfaces instead of objects lördag 24 januari 15
  • 31. public interface Contact { public void setName(String name); public String getName(); public void setYearOfBirth(int yearOfBirth); public int getYearOfBirth(); public void setAddress(Address address); public Address getAddress(); public void setEmailAddresses(List<String> addresses); public List<String> getEmailAddresses(); } Contact interface lördag 24 januari 15
  • 32. New possibilities Send partial updates Manage entity identity Use instance methods for RPC lördag 24 januari 15
  • 33. Good • Entities do not need to be GWT compatible • Combines RPC and entity management • Automatic request handling Bad • Complex setup • Heavy coupling with the server RequestFactory lördag 24 januari 15
  • 35. message Contact { required string name = 1; required int32 yearOfBirth = 2; repeated string emailAddresses = 3; optional Address address = 4; } Contact message lördag 24 januari 15
  • 36. Good • Any language • Google's data interchange format • Backwards compatible Bad • Binary format • Not very widely used Protocol Buffers lördag 24 januari 15
  • 37. What if we put the server in control? lördag 24 januari 15
  • 39. public class ContactState extends SharedState { public String name; @DelegateToWidget public int yearOfBirth; } @OnStateChange("name") private void updateName() { doSomethingWithTheName(getState().name); } @Override protected ContactState getState() { return (ContactState) super.getState(); } State synchronization lördag 24 januari 15
  • 40. public interface ContactRpc extends ServerRpc { public void deleteContact(int id); } // Register RPC handler on the server registerRpc(new ContactRpc() { @Override public void deleteContact(int id) { ContactDAO.deleteById(id); } }); // Send RPC from the client public void sendDelete(int contactId) { getRpcProxy(ContactRpc.class).deleteContact(contactId); } RPC lördag 24 januari 15
  • 41. Good • Stateful server • Server push Bad • Stateful server • Tied to the framework Vaadin Connectors lördag 24 januari 15
  • 42. What if we completely hide the transport? lördag 24 januari 15
  • 43. // Fire event @Inject Event<Contact> contactEvent; public void updateContact(Contact contact) { contactEvent.fire(contact); } // Listen to event public void contactUpdateObserver(@Observes Contact contact) { ContactDAO.updateContact(contact); } CDI events lördag 24 januari 15
  • 44. Good • Transparent communication • Server push Bad • Transparent communication • Tied to the framework Errai Bus lördag 24 januari 15
  • 45. Questions? Answers? Please rate the talk at gwtcreate.com/agenda ? leif@vaadin.com lördag 24 januari 15