Mastering JavaServer Faces 2.2
上QQ阅读APP看书,第一时间看更新

The application scope

The application scope lives as long as the web application lives.

An application scope extends the session scope with the shared state across all users' interactions with a web application; this scope lives as long as the web application lives. Since the beans in the application scope lives until the application shuts down (or they are programmatically removed), we can say that this scope lives most. More precisely, objects settled on the application scope can be accessed from any page that is part of the application (for example, JSF, JSP, and XHTML).

Note

The application scope should be used only for data that is safe to be shared. Since an application scoped bean is shared by all users, you need to be sure that the bean has an immutable state or you need to synchronize access.

Usually, application scope objects are used as counters, but they can be used for many other tasks, such as initializations and navigations. For example, the application scope can be used to count how many users are online or to share that information with all users. Practically, it can be used to share data among all sessions, such as constants, common settings, and tracking variables.

Note

The application scope annotation is @ApplicationScoped and is defined in the javax.enterprise.context package for CDI, and in the javax.faces.bean package for JSF.

If you put the PlayersBean managed bean in the application scope, then the list of randomly extracted players will be available across all sessions. You can do it as shown in the following code:

import javax.enterprise.context.ApplicationScoped;
import javax.inject.Named;

@Named
@ApplicationScoped
public class PlayersBean {
  ...
}

The JSF version is shown in the following code:

import javax.faces.bean.ApplicationScoped;
import javax.faces.bean.ManagedBean;

@ManagedBean
@ApplicationScoped
public class PlayersBean {
  ...
}

For testing the application scope, you need to open multiple browsers or use multiple machines.

Be careful when you provide data from an application scoped bean to multiple sessions beans (for example, using injection), since the data shared by all sessions can be modified by each session separately. This can lead to inconsistent data across multiple users; therefore, be sure that the exposed application data isn't modified in sessions.

Note

A method annotated with @PostConstruct will be called only when the application scoped bean is instantiated. Subsequent requests will use this instance. Usually, this happens when the application starts; therefore, place inside this method the initialization tasks specific to the application in the context of this bean.

Programmatically, you can access the application map using the following code:

FacesContext context = FacesContext.getCurrentInstance();
Map<String, Object> applicationMap = context.getExternalContext().getApplicationMap();

The case of the CDI bean is wrapped into the application named ch3_3_1, while the case of the JSF bean is wrapped into the application named ch3_3_2.