Here is a simple example that I'm working on. Input would be
appreciated. I'm sure there are different approaches, but I'm having
trouble finding one and having a particular issue with the level of
granularity of testing.
I know one answer, in advance, will be to not use GWTTestCase. I will heed that. But the example below represents a simpler situation where GWTTestCase will likely be needed. So, how would one do this with GWTTestCase (assuming the actual case I'll be testing for is a good candidate for GWTTestCase)?
I have a basic search form. It has fields on it like: first name, last
name, etc. There is also a Find button. When the Find button is
pressed, a list of people matching the criteria appear. Each row in the
list (CellTable) has person's name, date of birth, address, etc. Many items are
links (Hyperlinks). For example, the person's name is a Hyperlink that,
when clicked, goes to a new screen showing the person details. Basic
CRUD stuff.
There is a presenter, defined by the view.
public interface PersonSearchView extends IsWidget
{
public void setPresenter( Presenter listener );
public void setData( Vector<PersonSearchInfo> psinfos );
...
public interface Presenter
{
/**
* Find people that match certain criteria.
*
* @return
*/
void findPersons( String firstname, String lastname, int sortBy, int start, int cnt );
/**
* Navigate to a new Place in the browser.
*/
void goTo( Place place );
}
}
The PersonSearchActivity implements the Presenter.
public class PersonSearchActivity extends AbstractActivity implements PersonSearchView.Presenter
{
...
public void findPersons( String firstname, String lastname, int sortBy, int start, int cnt )
{
MyServiceAsync srv = GWT.create( MyService.class );
PersonSearchCallback personSearchCallback = new PersonSearchCallback ();
srv .findPersons( firstname, lastname, sortBy, start, cnt, personSearchCallback );
}
private class PersonSearchCallback extends AsyncCallback<Vector<PersonSearchInfo>>
{
public void onFail( Throwable caught )
{
caught.printStackTrace();
}
public void onSuccess( Vector<PersonSearchInfo> results )
{
clientFactory.getPersonSearchView().setData( results );
}
}
}
The PersonSearchViewImpl has a bunch of test fields on it (firstname,
lastname, find button, etc) and calls the activities method to actually
do work.
public class PersonSearchViewImpl extends ResizeComposite implements PersonSearchView
{
interface Binder extends UiBinder<Widget, PersonSearchViewImpl>
{
}
private static final Binder binder = GWT.create( Binder.class );
@UiField TextBox firstname;
@UiField TextBox lastname;
@UiField Button findButton;
/**
* Handle Search button - do the search.
*/
@UiHandler( "findButton" )
protected void onFindButtonClick( ClickEvent event )
{
...
listener.findPersons( firstname, lastname, sortby, start, cnt );
...
}
}
A couple of questions regarding a test I'd like to perform. Let's
assume that testing occurs with a live database (and GWT-RPC). I know
that contest of the database and what should be returned for certain
queries. I'd like to run tests that execute certain queries and make
sure they appear in the table (at certain positions).
1) How would I test the clicking within the results. For example, each
person's name appears (per row) as a Hyperlink in the results. This is
implemented in a CellTable with Hyperlinks. Normal behavior is that
when the Hyperlink is clicked, GWT goes to the new place. There is no
notification to the activity. I suppose a ClickHandler could be added,
but it would have no usefulness other than testing. Would it be better
to not use a Hyperlink (maybe a Label with a click handler) and add a
selectPerson() method to the Presenter. Then the activity could test
the selection and handle the advancing to the new Place?
2) I've seen a technique where a Display interface is created within the
Presenter. It contains a list of HasText and HasClickHandlers that
conceptually define the View. It seems pretty fine grained. Of
course, this has the same issue related to Hyperlinks.
Anway, I'd appreciate feedback on various approaches.