8. alberto@jooink.com +AlbertoMancini
TURDUCKEN
Turducken - Divide and Conquer large GWT apps with
multiple teams
Rob Keane, GWT.create 2013
https://www.slideshare.net/RobertKeane1/turducken-divide
-and-conquer-large-gwt-apps-with-multiple-teams
8
13. alberto@jooink.com +AlbertoMancini
Problems back from the past …
A problem investigated around 2010 ...
An pattern for GWT applications proposed in 2013 ...
A 2012 workaround for a ‘forthcoming’ HTML5 feature ….
that eventually disappeared and never really born :|
13
15. alberto@jooink.com +AlbertoMancini
Window.postMessage
As in the Turducken pattern Window.postMessage is our
swiss-knife; the one that opens the possibility of
communications in the browser (even Cross Origin :))
The first idea was to multiplex this communication channel to
drive both service and app messages but …
15
16. alberto@jooink.com +AlbertoMancini
Window.postMessage
- A lot of security concerns, target and origin to take care of
Well, definitely something we will prefer not to leave in the hands
of the users of this code if we can but …
16
17. alberto@jooink.com +AlbertoMancini
JsInterop(ping) MessageChannel
package com.jooink.gwt.innerapp.support.jsi;
import jsinterop.annotations.JsPackage;
import jsinterop.annotations.JsProperty;
import jsinterop.annotations.JsType;
@JsType(isNative = true, name="MessageChannel", namespace =
JsPackage.GLOBAL)
public class MessageChannel {
@JsProperty
public native MessagePort getPort1();
@JsProperty
public native MessagePort getPort2();
}
17
18. alberto@jooink.com +AlbertoMancini
MessagePort
package com.jooink.gwt.innerapp.support.jsi;
import jsinterop.annotations.JsPackage;
import jsinterop.annotations.JsProperty;
import jsinterop.annotations.JsType;
@JsType(isNative = true, name="MessagePort", namespace =
JsPackage.GLOBAL)
public abstract class MessagePort {
public native void postMessage(Object payload);
public native void start();
public native void close();
@JsProperty(name = "onmessage")
public native void setOnMessage(Consumer<MessageEvent> consumer);
}
18
20. alberto@jooink.com +AlbertoMancini
Revised architecture
The applications during the first contact (done via
Window.postMessage) exchange a messageChannel;
Later, postMessage is used for service messages (the library
handles this kind of messages) and the message channel is on
the other hand left available, untouched, for the business
messages. So the picture with 2 channels was not really
misleading.
20
26. alberto@jooink.com +AlbertoMancini
Guest Application
The Guest Package (in action)
GuestPackage guestPackage = GuestPackage.get();
...
guestPackage.askForFullSize();
...
guestPackage.postMessage("Ciao Host, I’m the Guest");
...
guestPackage.addMessageReceivedHandler(event -> …);
…
26
27. alberto@jooink.com +AlbertoMancini
Note on JSNI (helpful, Good Old JSNI)
Way simpler than using jsinterop here …
private native MyEventRegistration
addWindowMessageHandler(Consumer<MessageEvent> handler) /*-{
$wnd.addEventListener('message', handler, false);
return {
remove: function () {
$wnd.removeEventListener('message', handler, false);
}
};
}-*/;
27