The J2EETM Tutorial
Home
TOC
Index
PREV TOP NEXT Search
Feedback

Method Invocations in RosterApp

To show how the various components interact, this section describes the sequence of method invocations that occur for particular functions. The source code for the components is in the j2eetutorial/examples/src/ejb/cmproster directory.

Creating a Player

1. RosterClient

The RosterClient invokes the createPlayer business method of the RosterEJB session bean. In the following line of code, the type of the myRoster object is Roster, the remote interface of RosterEJB. The argument of the createPlayer method is a PlayerDetails object, which encapsulates information about a particular player.

myRoster.createPlayer(new PlayerDetails("P1", "Phil Jones",	
    "goalkeeper", 100.00));
 

2. RosterEJB

The createPlayer method of the RosterEJB session bean creates a new instance of the PlayerEJB entity bean. Because the access PlayerEJB is local, the create method is defined in the local home interface, LocalPlayerHome. The type of the playerHome object is LocalPlayerHome. Here is the source code for the createPlayer method:

public void createPlayer(PlayerDetails details) { 	
	
try {	
        LocalPlayer player = playerHome.create(details.getId(),	
           details.getName(), details.getPosition(),   	
           details.getSalary());	
    } catch (Exception ex) {	
        throw new EJBException(ex.getMessage());	
    }	
}
 

3. PlayerEJB

The ejbCreate method assigns the input arguments to the bean's persistent fields by calling the set access methods. After invoking the ejbCreate method, the container saves the persistent fields in the database by issuing a SQL INSERT statement. The code for the ejbCreate method follows.

public String ejbCreate (String id, String name, 	
    String position,double salary) throws CreateException {	
	
    setPlayerId(id);	
    setName(name);	
    setPosition(position);	
    setSalary(salary);	
    return id;	
}
 

Adding a Player to a Team

1. RosterClient

The RosterClient calls the addPlayer business method of the RosterEJB session bean. The P1 and T1 parameters are the primary keys of the PlayerEJB and TeamEJB instances, respectively.

 myRoster.addPlayer("P1", "T1");
 

2. RosterEJB

The addPlayer method performs two steps. First, it calls findByPrimaryKey to locate the PlayerEJB and TeamEJB instances. Second, it invokes the addPlayer business method of the TeamEJB entity bean. Here is the source code for the addPlayer method of the RosterEJB session bean:

public void addPlayer(String playerId, String teamId) { 	
	
    try {	
        LocalTeam team = teamHome.findByPrimaryKey(teamId);	
        LocalPlayer player =	
            playerHome.findByPrimaryKey(playerId);	
        team.addPlayer(player);	
    } catch (Exception ex) {	
        throw new EJBException(ex.getMessage());	
    }	
}
 

3. TeamEJB

The TeamEJB entity bean has a relationship field named players, a Collection that represents the players that belong to the team. The access methods for the players relationship field are as follows:

public abstract Collection getPlayers();	
public abstract void setPlayers(Collection players);
 

The addPlayer method of TeamEJB invokes the getPlayers access method to fetch the Collection of related LocalPlayer objects. Next, the addPlayer method invokes the add method of the Collection interface. Here is the source code for the addPlayer method:

public void addPlayer(LocalPlayer player) {	
    try {	
        Collection players = getPlayers();	
        players.add(player);	
    } catch (Exception ex) {	
        throw new EJBException(ex.getMessage());	
    }	
}
 

Removing a Player

1. RosterClient

To remove player P4, the client would invoke the removePlayer method of the RosterEJB session bean:

myRoster.removePlayer("P4");
 

2. RosterEJB

The removePlayer method locates the PlayerEJB instance by calling findByPrimaryKey and then invokes the remove method on the instance. This invocation signals the container to delete the row in the database that corresponds to the PlayerEJB instance. The container also removes the item for this instance from the players relationship field in the TeamEJB entity bean. By this removal, the container automatically updates the TeamEJB-PlayerEJB relationship. Here is the removePlayer method of the RosterEJB session bean:

public void removePlayer(String playerId) { 	
    try {	
        LocalPlayer player =	
            playerHome.findByPrimaryKey(playerId);	
        player.remove();	
    } catch (Exception ex) {	
        throw new EJBException(ex.getMessage());	
    }	
}
 

Dropping a Player from a Team

1. RosterClient

To drop player P2 from team T1, the client would call the dropPlayer method of the RosterEJB session bean:

myRoster.dropPlayer("P2", "T1");
 

2. RosterEJB

The dropPlayer method retrieves the PlayerEJB and TeamEJB instances by calling their findByPrimaryKey methods. Next, it invokes the dropPlayer business method of the TeamEJB entity bean. The dropPlayer method of the RosterEJB session bean follows:

public void dropPlayer(String playerId, String teamId) {	
	
    try {	
        LocalPlayer player =	
            playerHome.findByPrimaryKey(playerId);	
        LocalTeam team = teamHome.findByPrimaryKey(teamId);	
        team.dropPlayer(player);	
    } catch (Exception ex) {	
        throw new EJBException(ex.getMessage());	
    }	
}
 

3. TeamEJB

The dropPlayer method updates the TeamEJB-PlayerEJB relationship. First, the method retrieves the Collection of LocalPlayer objects that correspond to the players relationship field. Next, it drops the target player by calling the remove method of the Collection interface. Here is the dropPlayer method of the TeamEJB entity bean:

public void dropPlayer(LocalPlayer player) {	
	
  try {	
        Collection players = getPlayers();	
        players.remove(player);	
    } catch (Exception ex) {	
        throw new EJBException(ex.getMessage());	
    }	
}
 

Getting the Players of a Team

1. RosterClient

The client can fetch a team's players by calling the getPlayersOfTeam method of the RosterEJB session bean. This method returns an ArrayList of PlayerDetails objects. A PlayersDetails object contains four variables--playerId, name, position, and salary--which are copies of the PlayerEJB persistent fields. The RosterClient calls the getPlayersOfTeam method as follows:

playerList = myRoster.getPlayersOfTeam("T2");
 

2. RosterEJB

The getPlayersOfTeam method of the RosterEJB session bean locates the LocalTeam object of the target team by invoking the findByPrimaryKey method. Next, the getPlayersOfTeam method calls the getPlayers method of the TeamEJB entity bean. Here is the source code for the getPlayersOfTeam method:

public ArrayList getPlayersOfTeam(String teamId) { 	
	
    Collection players = null;	
	
    try {	
        LocalTeam team = teamHome.findByPrimaryKey(teamId);	
        players = team.getPlayers();	
    } catch (Exception ex) {	
        throw new EJBException(ex.getMessage());	
    }	
	
    return copyPlayersToDetails(players);	
}
 

The getPlayersOfTeam method returns the ArrayList of PlayerDetails objects that is generated by the copyPlayersToDetails method:

private ArrayList copyPlayersToDetails(Collection players) {	
	
     ArrayList detailsList = new ArrayList();	
     Iterator i = players.iterator();	
	
     while (i.hasNext()) {	
         LocalPlayer player = (LocalPlayer) i.next();	
         PlayerDetails details = 	
             new PlayerDetails(player.getPlayerId(),	
                 player.getName(), player.getPosition(),	
                 player.getSalary());	
         detailsList.add(details);	
     }	
	
     return detailsList;	
} 
 

3. TeamEJB

The getPlayers method of the TeamEJB entity bean is an access method of the players relationship field:

public abstract Collection getPlayers();
 

This method is exposed to local clients because it is defined in the local interface, LocalTeam:

public Collection getPlayers();
 

When invoked by a local client, a get access method returns a reference to the relationship field. If the local client alters the object returned by a get access method, it also alters the value of the relationship field inside the entity bean. For example, a local client of the TeamEJB entity bean could drop a player from a team as follows:

LocalTeam team = teamHome.findByPrimaryKey(teamId);	
Collection players = team.getPlayers();	
players.remove(player);
 

If you want to prevent a local client from modifying a relationship field in this manner, you should take the approach described in the next section.

Getting a Copy of a Team's Players

In contrast to the methods discussed in the preceding section, the methods in this section demonstrate the following techniques:

1. RosterClient

If you wanted to hide the salary of a player from a remote client, you would require the client to call the getPlayersOfTeamCopy method of the RosterEJB session bean. Like the getPlayersOfTeam method, the getPlayersOfTeamCopy method returns an ArrayList of PlayerDetails objects. However, the objects returned by getPlayersOfTeamCopy are different--their salary variables have been set to zero. The RosterClient calls the getPlayersOfTeamCopy method as follows:

playerList = myRoster.getPlayersOfTeamCopy("T5");
 

2. RosterEJB

Unlike the getPlayersOfTeam method, the getPlayersOfTeamCopy method does not invoke the getPlayers access method that is exposed in the LocalTeam interface. Instead, the getPlayersOfTeamCopy method retrieves a copy of the player information by invoking the getCopyOfPlayers business method that is defined in the LocalTeam interface. As a result, the getPlayersOfTeamCopy method cannot modify the players relationship field of TeamEJB. Here is the source code for the getPlayersOfTeamCopy method of RosterEJB:

public ArrayList getPlayersOfTeamCopy(String teamId) { 	
	
    ArrayList playersList = null;	
	
    try {	
        LocalTeam team = teamHome.findByPrimaryKey(teamId);	
        playersList = team.getCopyOfPlayers();	
    } catch (Exception ex) {	
        throw new EJBException(ex.getMessage());	
    }	
	
    return playersList;	
}
 

3. TeamEJB

The getCopyOfPlayers method of TeamEJB returns an ArrayList of PlayerDetails objects. To create this ArrayList, the method iterates through the Collection of related LocalPlayer objects and copies information to the variables of the PlayerDetails objects. The method copies the values of PlayerEJB persistent fields--except for the salary field, which it sets to zero. As a result, a player's salary is hidden from a client that invokes the getPlayersOfTeamCopy method. The source code for the getCopyOfPlayers of TeamEJB follows.

public ArrayList getCopyOfPlayers() {	
	
    ArrayList playerList = new ArrayList();	
    Collection players = getPlayers();	
	
    Iterator i = players.iterator();	
    while (i.hasNext()) {	
        LocalPlayer player = (LocalPlayer) i.next();	
        PlayerDetails details = 	
            new PlayerDetails(player.getPlayerId(),	
            player.getName(), player.getPosition(), 0.00);	
        playerList.add(details);	
    }	
	
    return playerList;	
}
 

Finding the Players by Position

1. RosterClient

The client starts the procedure by invoking the getPlayersByPosition method of the RosterEJB session bean:

playerList = myRoster.getPlayersByPosition("defender");
 

2. RosterEJB

The getPlayersByPosition method retrieves the players list by invoking the findByPosition method of the PlayerEJB entity bean:

public ArrayList getPlayersByPosition(String position) {	
	
   Collection players = null;	
	
    try {	
        players = playerHome.findByPosition(position);	
    } catch (Exception ex) {	
        throw new EJBException(ex.getMessage());	
    }	
	
    return copyPlayersToDetails(players);	
}
 

3. PlayerEJB

The LocalPlayerHome interface defines the findByPosition method:

public Collection findByPosition(String posistion)	
    throws FinderException;
 

Because the PlayerEJB entity bean uses container-managed persistence, the entity bean class (PlayerBean) does not implement its finder methods. To specify the queries associated with the finder methods, EJB QL queries must be defined in the bean's deployment descriptor. For example, the findByPosition method has this EJB QL query:

SELECT DISTINCT OBJECT(p) FROM Player p	
WHERE p.position = ?1
 

The deploytool utility translates the EJB QL query into a SQL SELECT statement. At runtime, when the container invokes the findByPosition method, it will execute the SQL SELECT statement.

For details about EJB QL, please refer to Chapter 8. To learn how to view and edit an EJB QL query in deploytool, see the section Finder/Select Methods Dialog Box (PlayerEJB).

Getting the Sports of a Player

1. RosterClient

The client invokes the getSportsOfPlayer method of the RosterEJB session bean:

sportList = myRoster.getSportsOfPlayer("P28");
 

2. RosterEJB

The getSportsOfPlayer method returns an ArrayList of String objects that represent the sports of the specified player. It constructs the ArrayList from a Collection returned by the getSports business method of the PlayerEJB entity bean. Here is the source code for the getSportsOfPlayer method of the RosterEJB session bean:

public ArrayList getSportsOfPlayer(String playerId) { 	
	
ArrayList sportsList = new ArrayList();	
    Collection sports = null;	
	
    try {	
        LocalPlayer player =	
            playerHome.findByPrimaryKey(playerId);	
        sports = player.getSports();	
    } catch (Exception ex) {	
        throw new EJBException(ex.getMessage());	
    }	
  	
    Iterator i = sports.iterator();	
    while (i.hasNext()) {	
        String sport = (String) i.next();	
        sportsList.add(sport);	
    }	
    return sportsList;	
}
 

3. PlayerEJB

The getSports method is a wrapper for the ejbSelectSports method. Since the parameter of the ejbSelectSports method is of type LocalPlayer, the getSports method passes along a reference to the entity bean instance. The PlayerBean class implements the getSports method as follows:

public Collection getSports() throws FinderException {	
	
     LocalPlayer player = 	
         (team.LocalPlayer)context.getEJBLocalObject();	
     return ejbSelectSports(player);	
}
 

The PlayerBean class defines the ejbSelectSports method:

public abstract Collection ejbSelectSports(LocalPlayer player)	
    throws FinderException;
 

The bean's deployment descriptor specifies the following EJB QL query for the ejbSelectSports method:

SELECT DISTINCT t.league.sport	
FROM Player p, IN (p.teams) AS t	
WHERE p = ?1
 

Before deploying PlayerEJB, you run deploytool to generate SQL SELECT statements for the bean's EJB QL queries. Because PlayerEJB uses container-managed persistence, when the ejbSelectSports method is invoked the EJB container will execute its corresponding SQL SELECT statement.

Home
TOC
Index
PREV TOP NEXT Search
Feedback