Yagwto

Loading...

Flash Player 9 (or above) is needed to view presentations.
We have detected that you do not have it on your computer. To install it, go here.

0 comments

Post a comment

    Post a comment
    Embed Video
    Edit your comment Cancel

    Favorites, Groups & Events

    Yagwto - Presentation Transcript

    1. YA GWT O GOOGLE WEB TOOLKIT
    2. YA GWT O GOOGLE WEB TOOLKIT
    3. RIA? RICH INTERNET APPLICATION UNA NUOVA USER EXPERIENCE!
    4. Problematiche Gli sviluppatori possono impiegare anche il 90% del loro tempo per:
        • problemi di compatibilità tra i browser
        • mantenere molto codice Javascript
        • gestire il ciclo di vita del software
        • utilizzare correttamente AJAX
    5. La risposta è GWT Cosa non saranno più nostre preoccupazioni?
        • incompatibilità tra i browser
        • gestione corretta della history del browser
        • localizzazione senza refresh della pagina
        • offuscamento del codice
        • riduzione del codice
        • image bundle
        in poche parole OTTIMIZZAZIONE
    6. GWT = JAVA TO JAVASCRIPT Perchè Java? Una sola risposta: TOOL
    7. GWT contro tutti VS.
    8. Hello JUG! applicationCreator it.pronetics.gwt. client .HelloJUGApp  
    9. Moduli *.gwt.xml In GWT è possibile definire dei moduli . Ogni modulo è configurato in un file con estensione: gwt.xml     < module >     < inherits name =&quot;com.google.gwt.user.User&quot;/>     < entry-point class =&quot;com.example.foo.MyModule&quot;/>  </ module >   Qui definiamo l'entry-point MyModule che sarà il &quot;main&quot; del nostro applicativo
    10. Tags *.gwt.xml <inherits name=&quot;logical-module-name&quot; /> : Per importare altri moduli   <entry-point class=&quot;classname&quot; /> : La classe entry point dell'applicazione   <source path=&quot;path&quot; //> : Definisce in quale package riesodo i sorgenti della parte client, per default il package è client <public path=&quot;path&quot;/> : Il percorso dove risiedono le componenti statiche e componenti di terze parti (javascript, html, immagini, etc, etc).   <servlet path=&quot;url-path&quot; class=&quot;classname&quot;/> : Definisce il componente lato server per le chiamate RPC.   <script src=&quot;js-url&quot;/>,<stylesheet src=&quot;css-url&quot;/> : Per includere javascript e css   <extend-property name=&quot;client-property-name&quot; values=&quot;comma-separated-values&quot;/> : Per aggiungere delle proprietà
    11. Creare moduli esterni
        • I moduli esterni stanno a GWT   come le librerie a Java
        • Hanno in comune l'estensione JAR
        • Il nostro progetto li può includere tramite il tag inherits . Nelle prossime slide useremo:
          • <inherits name=&quot;com.google.gwt.json.JSON&quot; />
          • <inherits name=&quot;com.google.gwt.http.HTTP&quot; />
        • Il jar deve avere la seguente struttura :
          • it/pronetics/module/Test.gwt.xml
          • it/pronetics/module/client/.../*.java
          • it/pronetics/module/client/.../*.class
        • il package client è obbligatorio, se ne usiamo uno diverso lo dobbiamo specificare tramite il tag source :
          • <source path=&quot;util&quot; />
    12. EntryPoint
        • Le classi definite come EntryPoint devono implementare l'omonima interfaccia e definire il metodo public void onModuleLoad() Questo è il metodo che viene invocato quando viene richiesta la url dell'entry point dell'applicazione per la prima volta.
        • RootPanel rappresenta, nella pagina, il contenitore di più alto livello (body html o un elemento div da noi definito). Per aggiungere elementi a RootPanel è sufficente chiamare:
             RootPanel.get().add(myPanel);
    13. Vi ricordate Swing?
    14. Hello JUG! ./HelloJUG-shell
    15. Ecco il codice!   public void onModuleLoad() { Image img = new Image( &quot;http://code.google.com/webtoolkit/logo-185x175.png&quot; ); Button button = new Button( &quot;Click me&quot; ); ... VerticalPanel vPanel = new VerticalPanel(); ... vPanel.add(button); // Add image and button to the RootPanel RootPanel.get().add(vPanel); // Create the dialog box final DialogBox dialogBox = new DialogBox(); dialogBox.setText( &quot;Welcome to GWT!&quot; ); dialogBox.setAnimationEnabled(true); Button closeButton = new Button( &quot;close&quot; ); VerticalPanel dialogVPanel = new VerticalPanel(); ... closeButton.addClickListener( new ClickListener() { public void onClick(Widget sender) { dialogBox.hide(); } }); dialogBox.setWidget(dialogVPanel); button.addClickListener( new ClickListener() { public void onClick(Widget sender) { dialogBox.center(); dialogBox.show(); } }); } }
    16. Architettura classica
    17. Remote Procedure Call Una Remote Procedure Call è una funzione implementata lato server invocata dal client.   GWT RPC NON è la stessa tecnologia su cui sono basati i web services SOAP o REST .
    18. RPC gwt.xml   Nel nostro file gwt.xml dovremmo configurare la classe che implementa il servizio lato server.   Dobbiamo mappare inoltre anche la path alla quale tale implementazione risponderà   ... <servlet path=&quot; /countVisitors &quot;  class=&quot; it.jk.server.VisitorsCountServiceImpl &quot;/> ...
    19. RPC diagrama del'interazione Cosa ci serve?
      • L'interfaccia del servizio MyService
      • L'interfaccia MyServiceAsync
      • L'implementazione lato server MyServiceImpl
    20. RPC interfaccie package it.jk.client; import com.google.gwt.user.client.rpc.RemoteService; import com.google.gwt.user.client.rpc.RemoteServiceRelativePath;   @RemoteServiceRelativePath(&quot;countVisitors&quot;) public interface VisitorsCountService extends RemoteService {     public String getVisitors (String name); } package it.jk.client; import com.google.gwt.user.client.rpc.RemoteService; import com.google.gwt.user.client.rpc.RemoteServiceRelativePath; import com.google.gwt.user.client.rpc.AsyncCallback; public interface VisitorsCountServiceAsync {     void getVisitors (String name, AsyncCallback async); }
    21. RPC Server package it.jk.server; import com.google.gwt.user.client.rpc.RemoteServiceRelativePath; import com.google.gwt.user.server.rpc.RemoteServiceServlet; import it.jk.client.VisitorsCountService; @RemoteServiceRelativePath(&quot;countVisitors&quot;) public class VisitorsCountServiceImpl extends RemoteServiceServlet implements VisitorsCountService {     public String getVisitors (String name) {         VISITORS++;         return &quot;Ciao &quot; + name + &quot; è il click numero &quot; + VISITORS;     }     private static int VISITORS = 0; }
    22. RPC Client private void getVisitorInfo(String userName) {         // Iniziallizza il proxy per il servizio         if (visitorCountService == null) {             visitorCountService = GWT.create(VisitorsCountService.class) ;         }         // Prepara l'ogetto per la callback         AsyncCallback <String> callback = new AsyncCallback <String>() {             public void onFailure(Throwable caught) {                 // TODO: Gestione errore             }             public void onSuccess(String result) {                 salutoLabel.setText(result);             }         };         // Chiama il metodo per sapere quante visite ci sono state         visitorCountService.getVisitors(userName, callback);     }
    23. Screenshot esempio RPC  
    24. Maven?   Archetype per la generazione del progetto mvn archetype:create -DarchetypeGroupId=com.totsp.gwt -DarchetypeArtifactId=maven-googlewebtoolkit2-archetype -DarchetypeVersion=1.0.4 -DremoteRepositories=http://gwt-maven.googlecode.com/svn/trunk/mavenrepo -DgroupId=myGroupId -DartifactId=myArtifactId Comando per eseguire l'applicazione mvn com.totsp.gwt:maven-googlewebtoolkit2-plugin:gwt Vantaggi
      • Compila anche la componente lato server
      • Generazione automatica file WAR
      • Gestione dipendenze
      • Scarica in automatico GWT da un repository di Maven
    25. Flickr Mash-up Miliardi di informazioni sparse per la rete   Fare un applicativo Mash-up vuol dire sviluppare  un software capace di aggregarle in un solo punto
    26. Ringraziamo le API...                 ...e vediamo quelle che usa Flickr http://www.flickr.com/services/api/   REST + JSON
    27. Prima prova di contatto... String url =  &quot; http://www.flickr.com/services/rest/?format=json& method =flickr.interestingness.getList& api_key =a1234567a1ce1bd1aba1234 aaec123e1& user_id =1234567@N01 &quot;; RequestBuilder builder = new RequestBuilder(RequestBuilder.GET, apiUrl); Request req = builder.sendRequest(null, new JsonRequestCallBack());     public class JsonRequestCallBack implements RequestCallback {      public void onError(Request request, Throwable exception) {             //gestisco richiesta in errore          }          public void onResponseReceived(Request req, Response response) {             //gestisco richiesta avvenuta con successo         } }        
    28. ...ma non funziona AJAX non permette richieste CROSS-SITE Questo a causa del principio di sicurezza SOP (same origin policy) Abbiamo 3 soluzioni:   1) configurare un alias dell'host remoto in modo da poterlo chiamare come se fosse localhost   2) Creare un componente server-side che faccia da proxy   3) Imbrogliare : l'unica risorsa che possiamo richiedere esternamente è Javascript...uhm...interessante
    29. Ok, imbrogliamo! L'output dei servizi REST+JSON di Flickr (ma anche Google e altri) può avvenire in due modi:  
        • jsonFlickrApi({&quot;photos&quot;:{&quot;page&quot;:1, &quot;pages&quot;:5, &quot;perpage&quot;:100, &quot;total&quot;:500, &quot;photo&quot;:[{&quot;id&quot;:&quot;3123...)
        •   myCallbackFunction ({&quot;photos&quot;: {&quot;page&quot;:1, &quot;pages&quot;:5, &quot;perpage&quot;:100, &quot;total&quot;:500, ...)
        myCallbackFunction sarà il nome di una funzione Javascript a cui sarà passato l'oggetto JSON ritornato da Flickr   L'url è diventato: String url =  &quot; http://.../rest/?format=json& method =...& api_key =a...1& user_id =1234567@N01& jsoncallback = myCallbackFunction &quot;;
    30. Un problema ed una soluzione: JSNI Problema
        • il nome del metodo di callback deve essere predefinito  
        • GWT rinomina i metodi per ridurre le dimensioni del js
      Soluzione   Con JSNI definiamo codice Javascript in una una classe public native static void getJson(String callback , String url, MyHandler h ) /*-{ var script = document.createElement(&quot;script&quot;);  script.setAttribute(&quot;src&quot;, url+ callback ); script.setAttribute(&quot;type&quot;, &quot;text/javascript&quot;); window[callback] = function(jsonObj){ h .@ it.pronetics.MyHandler::handle (Lcom/google/gwt/core/client/JavaScriptObject;)( obj );     window[callback + &quot;done&quot;] = true; }        document.body.appendChild(script); }-*/;
    31. Ancora J ava S cript N ative I nterface package it.pronetics; ...   public class MyHandler {      public void handle(JavaScriptObject javaScriptObject) {         //creiamo l'oggetto JSON         JSONObject object = new JSONObject(javaScriptObject);         // isObject() e isArray() ritornano null in caso di errore,         // il valore recuperato in caso di successo         JSONArray photos = object.get( &quot;photos&quot; ).isObject().get( &quot;photo&quot; ).isArray();         String thumbnail = buildPhotoUrl(photoJson, &quot;s&quot;);         ....         Image image = new Image(thumbnail);         gallery.setWidget(row, column, image);      } ... bla bla bla ... }
    32. Finalmente...
    33. Il mio widget public class ImageSlide extends Composite { //estendere la classe Composite come consigliato da GWT public ImageSlide(String thumbnail, String preview, final String link) {          VerticalPanel mainPanel = new VerticalPanel();         HorizontalPanel details = new HorizontalPanel();                  Image thumbnailImage = new Image(thumbnail);         mainPanel.add(thumbnailImage);         mainPanel.add(details);         mainPanel.setBorderWidth(1);                  Button show = new Button(&quot;Show&quot;);         Button open = new Button(&quot;Open&quot;);         details.add(show);         details.add(open);                  final PopupPanel popup = new PopupPanel();            Image previewImage = new Image(preview);         VerticalPanel imagePanel = new VerticalPanel();         imagePanel.add(previewImage);                  previewImage.addClickListener(new ClickListener(){ public void onClick(Widget sender) { popup.hide(); }  });         popup.setWidget(imagePanel);                  show.addClickListener(new ClickListener(){ public void onClick(Widget sender) { popup.show(); } });                  open.addClickListener(new ClickListener(){ public void onClick(Widget sender) { Window.open(link, &quot;_blank&quot;,&quot;enabled&quot;);}});                  initWidget(mainPanel); //chiamata obbligatoria!     } }
    34. Già stiamo migliorando...
    35. ...ma questa è meglio...
    36. ...c'è anche qualche info...
    37. ...ma come abbiamo fatto?     public ImageSlide(String thumbnail, String preview, String title, final String link) {        ... creo vari panel ...                  Image thumbnailImage = new Image(thumbnail);         thumbnailImage.setStyleName(&quot;image-panel&quot;);         mainPanel.add(thumbnailImage);         mainPanel.setCellHorizontalAlignment(thumbnailImage, HasHorizontalAlignment.ALIGN_CENTER);         mainPanel.add(details);                  Button open = new Button(&quot;View on Flickr&quot;, new OpenLinkOnClick(link));         open.setWidth(&quot;100%&quot;);         Button close = new Button(&quot;Close me!&quot;, new ClosePopupPanelOnClick(popup));         close.setWidth(&quot;100%&quot;);                  Image previewImage = new Image(preview);         VerticalPanel imagePanel = new VerticalPanel();         imagePanel.add(previewImage);                  infoPanel.add(new Label(title, true));         infoPanel.add(open);         infoPanel.add(close);                  previewTab.add(imagePanel, &quot;Image&quot;);         previewTab.add(infoPanel, &quot;Get Info&quot;);         previewTab.selectTab(0);         previewTab.setAnimationEnabled(true);                  previewImage.addClickListener(new ClosePopupPanelOnClick(popup));             thumbnailImage.addClickListener(new DisplayPopupOnClick(popup));                  initWidget(mainPanel); //chiamata obbligatoria!     }
    38. Ma soprattutto CSS E' stato modificato il file FlickrGWT.css   .image-panel {     background: url('img/bg.png') no-repeat top center;     padding: 0px 10px 10px 10px; } Ricordate : GWT in fondo crea semplici pagine HTML i cui stili possono essere impostati con semplici CSS
    39. La versione finale!
        • Modifichiamo il file FlickrGWT.html creando un layout HTML
        • Specifichiamo l'id del div che conterrà la nostra applicazione: RootPanel.get(&quot;flickr-gallery&quot;).add(gallery);
        • Scriviamo un po' di css e html e...
    40. Image Bundle? Problema Troppe request uccidono i nostri server Soluzione Una sola request per le immagini usate nel nostro applicativo
    41. Image Bundle con GWT
        • L'unione di tutte le immagini in una sola è automatica
        • Basta definire una interfaccia interface ToolBarImage extends ImageBundle {          @Resource ( &quot;img/open.png&quot; )         AbstractImagePrototype open();         ....         @Resource ( &quot;img/save.png&quot; )         AbstractImagePrototype save();  }
        • L'utilizzo è ancora più semplice ToolBarImage bundle = (ToolBarImage)GWT.create(ToolBarImage. class ); Image save = bundle.save().createImage(); toolbar.add(save);
    42. Plugin e widget per la view
    43. Alcune librerie utili
        • Spring Security + GWT http://www.insideit.fr/post/2009/02/19/How-to-:-Spring-Security-ex-Acegi-and-GWT
        • Dependency injection
          • GIN - http://code.google.com/p/google-gin/
          • SUCO - http://code.google.com/p/suco/
          • RocketGWT - http://code.google.com/p/rocket-gwt/
          • SpringME - http://springframework.me
        • Altri Framework
          • GWT Toolbox - http://code.google.com/p/gwt-toolbox/
          • GWT Widget Library -http://gwt-widget.sourceforge.net/
          • GWITTIR - http://code.google.com/p/gwittir/
        • Hibernate + GWT
          • Gilead - http://noon.gilead.free.fr/gilead/
        • Sviluppo Server Side
          • Enunciate - http://enunciate.codehaus.org/
    44. Usciamo dal browser con PRISM Mozilla Prism è un plugin per Firefox che permette la trasformazione di applicazioni web in applicazioni desktop
    45. Usciamo dalla rete con Google Gears
        • Database SQL
        • Geo localizzazione
        • Interazione col desktop
        • Local server per file, immagini, javascript, css
    46. Una combinazione vincente GWT + GEAR + PRISM = COOL APPLICATION
        • http://code.google.com/webtoolkit/
        • http://www.ociweb.com/mark/programming/GWT.html
        • http://code.google.com/p/gwt-google-apis/
        • http://gears.google.com/
        • http://www.gwtsite.com/
        • http://www.ongwt.com 
        • http://labs.mozilla.com/projects/prism/
      Link & Libri
        • Davide Cerbo [email_address] http://davide.cerbo.born-to-co.de
        • Stefano Linguerri stefano.linguerri @pronetics.it http://www.eljeko.net
      Contatti
    47. Q&A  

    + maraexceptionmaraexception, 6 months ago

    custom

    558 views, 0 favs, 1 embeds more stats

    by Davide Cerbo e Stefano Linguerri

    La programmazi more

    More info about this document

    © All Rights Reserved

    Go to text version

    • Total Views 558
      • 550 on SlideShare
      • 8 from embeds
    • Comments 0
    • Favorites 0
    • Downloads 7
    Most viewed embeds
    • 8 views on http://www.jugroma.it

    more

    All embeds
    • 8 views on http://www.jugroma.it

    less

    Flagged as inappropriate Flag as inappropriate
    Flag as inappropriate

    Select your reason for flagging this presentation as inappropriate. If needed, use the feedback form to let us know more details.

    Cancel
    File a copyright complaint
    Having problems? Go to our helpdesk?

    Categories