background image

 

 

www.devcastzone.com 

 

Z

AAWANSOWANE  WYKORZYSTANIE  BIBLIOTEKI 

EXT

 

GWT

  W  APLIKACJACH  OPARTYCH  O 

G

OOGLE 

W

EB 

T

OOLKIT

 

Moduł 5: Komunikacja aplikacji z serwerem 

Ćwiczenie 1: Callback 

Treść: 

Stworzyd  funkcję  zwrotną,  która  będzie  reagowała  na  zwrot  listy  łaocuchów  tekstowych. 
Jeżeli lista zostanie zwrócona to należy każdy jej element wyświetlid w konsoli. Jeżeli lista nie 
została  poprawnie  zwrócona  należy  wydelegowad  go  do  nowo  rzucanego  wyjątku  klasy 
RunntimeException. 

Instrukcja rozwiązania: 

1.  Stworzyd  funkcję  zwrotną  klasy  asyncCallback  wraz  z  typem  generycznym 

określającym listę ciągów tekstowych. 

2.  Zaimplementowad  metodę  onFailure,  która  rzuca  nowy  wyjątek  klasy 

RuntimeException, i przekazuje wyjątek z funkcji zwrotnej 

3.  Zaimplementowad  metodę  onSuccess,  w  której  należy  przeiterowad  zwraaną  listę  a 

następnie każdy element wyświetlid na ekranie. 

Rozwiązanie: 
 

 

Ćwiczenie 2: Asynchronous interface 

Treść: 

Stworzyd interfejs asynchroniczny do serwisu posiadającego następujące metody: 

 

  

interface

 UserService { 

 

    AsyncCallback<List<String>> callback = 

new

 

AsyncCallback<List<String>>() { 
       
      @Override 
      

public

 

void

 onFailure(Throwable caught) { 

        

throw

 

new

 RuntimeException(caught); 

      } 
       
      @Override 
      

public

 

void

 onSuccess(List<String> result) { 

        

for

 (String row : result) { 

          System.out.println(

"Row: "

 + row); 

        } 
      } 
    }; 

background image

 

 

www.devcastzone.com 

 

    

public

 

void

 updateUserName(Long id, String userName); 

 
    

public

 String getUserName(Long id); 

 
    

public

 List getUserNamesListByFilter(String filter); 

  } 

 

Instrukcja rozwiązania: 

1.  Należy zdefiniowad nowy interfejs o nazwie UserListAsync 
2.  Należy  dodad  deklarację  nowej  metody  updateUserName,  która  nic  nie  zwraca,  z 

przyjmowanymi parametrami: identyfikator, funkcja zwrotna , nic nie zwracająca  

3.  Należy  dodad  deklarację  nowej  metody  getUserName,  która  nic  nie  zwraca,  z 

przyjmowanymi  parametrami:  identyfikator,  funkcja  zwrotna  zwracająca  tekstowy 
typ danych 

4.  Należy  dodad  deklarację  nowej  metody  getUserNameListByFilter,  która  nic  nie 

zwraca, z przyjmowanymi parametrami: tekstowy filtr, funkcja zwrotna , zwracająca 
listę typów tekstowych 

Rozwiązanie: 
 

 

Ćwiczenie 3: GWT-RPC 

Treść: 

Stworzyd interfejs synchroniczny, asynchroniczy oraz implementację do komunikacji za 
pomocą GWT-RPC. Potencjalne wywołanie metody getFeedList serwisu powinno zwrócid 
listę łaocuchów tekstowych: (Blog BNSIT, Blog Xperios, Google, News). Serwis ma byd 
dostępny pod adresem "FeedList".

 

Instrukcja rozwiązania: 

1.  Należy  stworzyd  interfejs 

FeedListService dziedziczący po RemoteService I 

adnotacją RemoteServiceRelativePath ustawioną na FeedList

 

2.  Dodad do interfejsu metodę getFeedList, która zwraca listę typów tekstowych 
3.  Stworzyd  interfejs  o  nazwie  FeedListServiceAsync  z  metodą  o  nazwie  getFeedList, 

która  nie  zwraca  nic  i  przyjmuje  jedynie  jako  parametr  funkcję  zwrotną  listy  typów 
tekstowych 

  

interface

 UserListAsync { 

     
    

public

 

void

 updateUserName(Long id, String user, AsyncCallback<Void> 

callback); 
     
    

public

 void getUserName(Long id, AsyncCallback<String> callback); 

     
    

public

 void getUserNameListByFilter(String filter, AsyncCallback< 

List<String>> callback); 
  } 

background image

 

 

www.devcastzone.com 

 

4.  Stworzyd klasę FeedService, która dziedziczy po RemoteServiceServlet i implementuje 

FeedListService 

5.  W stworzonej klasie należy zaimplementowad metodę getFeedList 
6.  W  implementacji  należy  stworzyd  obiekt  listy,  do  której  należy  dodad  kolejno  „Blog 

BNSIT”, „Blog Xperios”, „Google”, „News”, który następnie należy zwrócid. 

Rozwiązanie: 
 

 

  @RemoteServiceRelativePath(

"FeedList"

  

interface

 FeedListService 

extends

 RemoteService { 

     
    

public

 List<String> getFeedList(); 

  } 
   
  

interface

 FeedListServiceAsync { 

     
    

public

 

void

 getFeedList(AsyncCallback<List<String>> callback); 

  } 
   
  

class

 FeedService 

extends

 RemoteServiceServlet 

implements

 

FeedListService { 
     
    @Override 
    

public

 List<String> getFeedList() { 

      ArrayList<String> out = 

new

 ArrayList<String>(); 

      out.add(

"Blog BNSIT"

); 

      out.add(

"Blog Xperios"

); 

      out.add(

"Google"

); 

      out.add(

"News"

); 

      

return

 out; 

    } 
  } 

background image

 

 

www.devcastzone.com 

 

Ćwiczenie 4: DTO 

Treść: 

Stworzyd model persystencyjny, który za pomocą metody DTO pozwoli na wprowadzenie 
danych w części klienckiej, zapisanie ich w bazie danych oraz pobranie ich i wysłanie z 
powrotem. Należy stworzyd model persystencyjny Person, który będzie posiadał właściwości 
id, name i dateOfBirth oraz releatedList jako listę osób spokrewnionych. Obiekty tego 
modelu muszą byd zapisywalne w bazie danych za pomocą Hibernate a także z niej 
odczytywane. 
Należy opracowad metodę komunikacyjną, pozwoli na przesłanie danych z części klienckiej i 
zapisanie ich do bazy danych. Po poprawnym zapisie danych ma zostad pobrana lista 
wszystkich elementów modelu i odesłana do klienta. 

Instrukcja rozwiązania: 

1.  .Należy  stworzyd  model  danych  Person  z  adnotacją  @Entity  i  nad  właściwościami 

pododawad  adnotacje:  @Id  nad  identyfikatorem,  @Temoral  nad  polem  daty, 
@OneToMany nad polem listy. 

2.  Stworzyd model dto  o  nazwie PersonDTO, który posiada te same właściwości co do 

typów i nazw bez żadnej adnotacji. 

3.  Do  klasy  Person  dodad  statyczne  metody  pozwalające  na  konwersję  obiektów 

PersonDTO do Person i na odwrót 

4.  Stworzyd  plik  konfiguracyjny  Hibernate  wraz  z  dodanym  wpisem  mapping  class  ze 

wskazaniem na klasę Person 

5.  Stworzyd  klasę  pomocniczą  HibernateUtil,  która  skonfiguruje  Hibernate  a  także 

pozwoli na pobranie obiektu sesji. 

6.  Stworzyd  interfejs  synchroniczny  wraz  z  metodą:  persistAndGetAllPerson,  która 

przyjmowad będzie obiekt PersonDTO, natomiast zwracad będzie List<PersonDTO> 

7.  Stworzyd interfejs asynchroniczny 
8.  Dodad odpowiednie mapowanie w pliku web.xml 
9.  Stworzyd  implementację  serwisu,  która  pozwoli  na  zainicjonowanie  danych  w  bazie 

danych 

10. Implementacja  metody  powinna  umożliwiad  konwersję  obiektów  PersonDTO  na 

obiekty  klasy  Person,  zapis  obiektu  Person  do  bazy,  odczyt  wszystkich  elementów 
Person  z  bazy,  konwersję  wszystkich  zwróconych  elementów  do  PersonDTO  oraz 
odesłanie danych do klienta. 

Rozwiązanie: 

background image

 

 

www.devcastzone.com 

 

Model danych: 

 

package

 pl.bnsit.rpc.server; 

 

import

 java.util.ArrayList; 

import

 java.util.Date; 

import

 java.util.List; 

import

 javax.persistence.CascadeType; 

import

 javax.persistence.Entity; 

import

 javax.persistence.FetchType; 

import

 javax.persistence.GeneratedValue; 

import

 javax.persistence.GenerationType; 

import

 javax.persistence.Id; 

import

 javax.persistence.OneToMany; 

import

 javax.persistence.Temporal; 

import

 javax.persistence.TemporalType; 

import

 pl.bnsit.rpc.shared.PersonDTO; 

 

 
@Entity 

public

 

class

 Person { 

 
  @Id 
  @GeneratedValue(strategy = GenerationType.AUTO) 
  Long id; 
  String name; 
  @Temporal(TemporalType.DATE) 
  Date dateOfBirth; 
  @OneToMany(cascade = CascadeType.ALL, fetch = FetchType.LAZY) 
  List<Person> relativeList; 
 
  

public

 Person() { 

  } 
 
  

public

 Person(Long id, String name, Date dateOfBirth, 

List<Person> relativeList) { 
    

this

.id = id; 

    

this

.name = name; 

    

this

.dateOfBirth = dateOfBirth; 

    

this

.relativeList = relativeList; 

  } 
 
 
//setters and getters 
 
  @Override 
  

public

 String toString() { 

    

return

 

"Person{"

 + 

"id="

 + id + 

", name="

 + name + 

", 

dateOfBirth="

 + dateOfBirth + 

", relativeList="

 + relativeList + 

'}'

  } 
 
  

background image

 

 

www.devcastzone.com 

 

DTO: 

 

Metody konwertujące zawarte w klasie Person.java: 

 

package

 pl.bnsit.rpc.shared; 

 

import

 java.util.Date; 

import

 java.util.List; 

 

public

 

class

 PersonDTO { 

 
  Long id; 
  String name; 
  Date dateOfBirth; 
  List<PersonDTO> relativeList; 
 
  

public

 PersonDTO() { 

  } 
 
  

public

 PersonDTO(Long id, String name, Date dateOfBirth, 

List<PersonDTO> relativeList) { 
    

this

.id = id; 

    

this

.name = name; 

    

this

.dateOfBirth = dateOfBirth; 

    

this

.relativeList = relativeList; 

  } 
// getters and setters 
  @Override 
  

public

 String toString() { 

    

return

 

"PersonDTO{"

 + 

"id="

 + id + 

", name="

 + name + 

", 

dateOfBirth="

 + dateOfBirth + 

", relativeList="

 + relativeList + 

'}'

  }  
}

 

  

public

 

static

 PersonDTO convertToDto(Person object) { 

    

if

 (object == 

null

) { 

      

return

 

null

    } 
    PersonDTO out = 

new

 PersonDTO(); 

    out.setId(object.getId()); 
    out.setName(object.getName()); 
    out.setDateOfBirth(object.getDateOfBirth()); 
    out.setId(object.getId()); 
    List<Person> relativeListObject = object.getRelativeList(); 
    

if

 (relativeListObject == 

null

) { 

      

return

 out; 

    } 
    List<PersonDTO> relativeListDTO = 

new

 ArrayList<PersonDTO>(); 

    

for

 (Person person : relativeListObject) { 

      relativeListDTO.add(convertToDto(person)); 
    } 
    out.setRelativeList(relativeListDTO); 
    

return

 out; 

  } 

background image

 

 

www.devcastzone.com 

 

 

Przykładowy plik konfiguracyjny hibernate: 

 

HibernateUtil: 

public

 

static

 Person convertFromDto(PersonDTO dto) { 

    

if

 (dto == 

null

) { 

      

return

 

null

    } 
    Person out = 

new

 Person(); 

    out.setId(dto.getId()); 
    out.setName(dto.getName()); 
    out.setDateOfBirth(dto.getDateOfBirth()); 
    out.setId(dto.getId()); 
    List<PersonDTO> relativeListDto = dto.getRelativeList(); 
    

if

 (relativeListDto == 

null

) { 

      

return

 out; 

    } 
    List<Person> relativeList = 

new

 ArrayList<Person>(); 

    

for

 (PersonDTO personDTO : relativeListDto) { 

      relativeList.add(convertFromDto(personDTO)); 
    } 
    out.setRelativeList(relativeList); 
    

return

 out; 

  }   

<?

xml

 version=

"1.0"

 encoding=

"UTF-8"

?>

 

<!

DOCTYPE

 

hibernate-configuration

 

PUBLIC

 

"-//Hibernate/Hibernate 

Configuration DTD 3.0//EN"

 

"http://hibernate.sourceforge.net/hibernate-configuration-
3.0.dtd"

>

 

<

hibernate-configuration

>

 

  

<

session-factory

>

 

    

<

property

 

name=

"hibernate.dialect"

>

org.hibernate.dialect.DerbyDialect

</

prop

erty

>

 

    

<

property

 

name=

"hibernate.connection.driver_class"

>

org.apache.derby.jdbc.Cl

ientDriver

</

property

>

 

    

<

property

 

name=

"hibernate.connection.url"

>

jdbc:derby://localhost:1527/sampl

e

</

property

>

 

    

<

property

 name=

"hibernate.connection.username"

>

app

</

property

>

 

    

<

property

 name=

"hibernate.connection.password"

>

app

</

property

>

 

    

<

property

 

name=

"hibernate.current_session_context_class"

>

thread

</

property

>

 

    

<

property

 name=

"hibernate.hbm2ddl.auto"

>

create-

drop

</

property

>

 

    

<

mapping

 class=

"pl.bnsit.rpc.server.Person"

/>

 

  

</

session-factory

>

 

</

hibernate-configuration

>

 

 

background image

 

 

www.devcastzone.com 

 

 

Interfejs synchroniczny: 

 

package

 pl.bnsit.rpc.server; 

 

import

 org.hibernate.cfg.AnnotationConfiguration; 

import

 org.hibernate.SessionFactory; 

 

/** 
 * Hibernate Utility class with a convenient method to get 
Session Factory 
 * object. 
 */

 

public

 

class

 HibernateUtil { 

 
  

private

 

static

 

final

 SessionFactory sessionFactory; 

   
  

static

 { 

    

try

 { 

      

// Create the SessionFactory from standard 

(hibernate.cfg.xml)  

      

// config file. 

      sessionFactory = 

new

 

AnnotationConfiguration().configure().buildSessionFactory(); 
    } 

catch

 (Throwable ex) { 

      

// Log the exception.  

      System.err.println(

"Initial SessionFactory creation 

failed."

 + ex); 

      

throw

 

new

 ExceptionInInitializerError(ex); 

    } 
  } 
   
  

public

 

static

 SessionFactory getSessionFactory() { 

    

return

 sessionFactory; 

  } 

package

 pl.bnsit.rpc.client; 

 

import

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

import

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

import

 java.util.List; 

import

 pl.bnsit.rpc.shared.PersonDTO; 

 
@RemoteServiceRelativePath(

"PersonService"

public

 

interface

 PersonListService 

extends

 RemoteService { 

 
  

public

 List<PersonDTO> persistAndGetAllPerson(PersonDTO 

person); 

background image

 

 

www.devcastzone.com 

 

Interfejs asynchroniczny: 

 

Mapowanie serwletu: 

 

Implementacja serwisu: 

package

 pl.bnsit.rpc.client; 

 

import

 com.google.gwt.user.client.rpc.AsyncCallback; 

import

 java.util.List; 

import

 pl.bnsit.rpc.shared.PersonDTO; 

 

public

 

interface

 PersonListServiceAsync { 

 
  

public

 

void

 persistAndGetAllPerson(PersonDTO person, 

AsyncCallback<List<PersonDTO>> callback); 
   

<?

xml

 

version

=

"1.0"

 

encoding

=

"UTF-8"

?>

 

<

web-app

 

version

=

"2.4"

 

xmlns

=

"http://java.sun.com/xml/ns/j2ee"

 

  xmlns:web

=

"http://java.sun.com/xml/ns/j2ee/web-app_2_4.xsd"

 

xmlns:xsi

=

"http://www.w3.org/2001/XMLSchema-instance"

 

  xsi:schemaLocation

=

"http://java.sun.com/xml/ns/j2ee 

http://java.sun.com/xml/ns/j2ee/web-app_2_4.xsd"

>

 

  <

servlet

>

 

    <

servlet-name

>

 PersonService

 </

servlet-name

>

 

    

<

servlet-class

>

pl.bnsit.rssreader.server.FeedServiceImpl

</

servlet-

class

>

 

    

</

servlet

>

 

    

<

servlet-mapping

>

 

      

<

servlet-name

>

PersonService

</

servlet-name

>

 

        

<

url-pattern

>

/MainModule/ PersonService

 </

url-pattern

>

 

    

</

servlet-mapping

>

 

    

<

servlet

>

 

      

<

servlet-name

>

 PersonService

 </

servlet-name

>

 

      

<

servlet-class

>

pl.bnsit.rpc.server.PersonListServiceImpl

</

servlet-

class

>

 

    

</

servlet

>

 

    

<

welcome-file-list

>

 

      

<

welcome-file

>

MainModule.html

</

welcome-file

>

 

    

</

welcome-file-list

>

 

</

web-app

>

 

background image

 

 

www.devcastzone.com 

10 

 

 

package

 pl.bnsit.rpc.server; 

 

import

 com.google.gwt.user.server.rpc.RemoteServiceServlet; 

import

 pl.bnsit.rpc.client.PersonListService; 

 

import

 java.util.ArrayList; 

import

 java.util.Date; 

import

 java.util.List; 

import

 org.hibernate.Transaction; 

import

 org.hibernate.classic.Session; 

import

 pl.bnsit.rpc.shared.PersonDTO; 

 

public

 

class

 PersonListServiceImpl 

extends

 RemoteServiceServlet 

implements

 PersonListService { 

  

static

 { 

    System.out.println(

"Initializing person data"

); 

    Session session = 
HibernateUtil.getSessionFactory().openSession(); 
    Transaction transaction = session.beginTransaction(); 
    transaction.begin(); 
    List<Person> personList = 

new

 ArrayList<Person>(); 

    personList.add(

new

 Person(

null

"Sister"

new

 Date(), 

null

)); 

    personList.add(

new

 Person(

null

"Brother"

new

 Date(), 

null

)); 

    personList.add(

new

 Person(

null

"Me"

new

 Date(), 

null

)); 

    session.save(

new

 Person(

null

"Father"

new

 Date(), 

personList)); 
    transaction.commit(); 
  } 
  @Override 
  

public

 List<PersonDTO> persistAndGetAllPerson(PersonDTO 

person) { 
    Session session = 
HibernateUtil.getSessionFactory().openSession(); 
    Transaction transaction = session.beginTransaction(); 
    transaction.begin(); 
    session.save(Person.convertFromDto(person)); 
    transaction.commit(); 
    

return

 getPersonDto(); 

  } 
  

public

 

static

 List<Person> getPersonList() { 

    Session session = 
HibernateUtil.getSessionFactory().openSession(); 
    

return

 session.createCriteria(Person.

class

).list(); 

  } 
 
  

public

 

static

 List<PersonDTO> getPersonDto() { 

    List<PersonDTO> out = 

new

 ArrayList<PersonDTO>(); 

    

for

 (Person person : getPersonList()) { 

      out.add(Person.convertToDto(person)); 
    } 
    

return

 out; 

  } 

background image

 

 

www.devcastzone.com 

11 

 

Częśd kliencka (wywołująca): 

 

package

 pl.bnsit.rpc.client; 

 

import

 com.google.gwt.core.client.EntryPoint; 

import

 com.google.gwt.core.client.GWT; 

import

 com.google.gwt.user.client.Window; 

import

 com.google.gwt.user.client.rpc.AsyncCallback; 

import

 com.sencha.gxt.widget.core.client.box.MessageBox; 

import

 java.util.Date; 

import

 java.util.List; 

import

 pl.bnsit.rpc.shared.PersonDTO; 

 

public

 

class

 MainModule 

implements

 EntryPoint{ 

 
  @Override 
  

public

 

void

 onModuleLoad() { 

    PersonListServiceAsync service = 
GWT.create(PersonListService.

class

); 

    PersonDTO person = 

new

 PersonDTO(

null

"Me"

new

 Date(), 

null

); 

    service.persistAndGetAllPerson(person, 

new

 

AsyncCallback<List<PersonDTO>>() { 
 
      @Override 
      

public

 

void

 onFailure(Throwable caught) { 

        Window.alert(

"error occured: "

+caught.getMessage()); 

      } 
 
      @Override 
      

public

 

void

 onSuccess(List<PersonDTO> result) { 

        Window.alert(

"People in db: I"

+result.size()+

""

); 

      } 
    }); 
  }