I noticed that there are different bean scopes like:
@RequestScoped
@ViewScoped
@FlowScoped
@SessionScoped
@ApplicationScoped
What is the purpose of each? How do I choose a proper scope for my bean?
Sign Up to our social questions and Answers Engine to ask questions, answer people’s questions, and connect with other people.
Login to our social questions & Answers Engine to ask questions answer people’s questions & connect with other people.
Lost your password? Please enter your email address. You will receive a link and will create a new password via email.
Please briefly explain why you feel this question should be reported.
Please briefly explain why you feel this answer should be reported.
Please briefly explain why you feel this user should be reported.
Introduction
It represents the scope (the lifetime) of the bean. This is easier to understand if you are familiar with "under the covers" working of a basic servlet web application: How do servlets work? Instantiation, sessions, shared variables and multithreading.
@Request/View/Flow/Session/ApplicationScopedA
@RequestScopedbean lives as long as a single HTTP request-response cycle (note that an Ajax request counts as a single HTTP request too). A@ViewScopedbean lives as long as you’re interacting with the same JSF view by postbacks which call action methods returningnull/voidwithout any navigation/redirect. A@FlowScopedbean lives as long as you’re navigating through the specified collection of views registered in the flow configuration file. A@SessionScopedbean lives as long as the established HTTP session. An@ApplicationScopedbean lives as long as the web application runs. Note that the CDI@Modelis basically a stereotype for@Named @RequestScoped, so same rules apply.Which scope to choose depends solely on the data (the state) the bean holds and represents. Use
@RequestScopedfor simple and non-ajax forms/presentations. Use@ViewScopedfor rich ajax-enabled dynamic views (ajaxbased validation, rendering, dialogs, etc). Use@FlowScopedfor the "wizard" ("questionnaire") pattern of collecting input data spread over multiple pages. Use@SessionScopedfor client specific data, such as the logged-in user and user preferences (language, etc). Use@ApplicationScopedfor application wide data/constants, such as dropdown lists which are the same for everyone, or managed beans without any instance variables and having only methods.Abusing an
@ApplicationScopedbean for session/view/request scoped data would make it to be shared among all users, so anyone else can see each other’s data which is just plain wrong. Abusing a@SessionScopedbean for view/request scoped data would make it to be shared among all tabs/windows in a single browser session, so the enduser may experience inconsitenties when interacting with every view after switching between tabs which is bad for user experience. Abusing a@RequestScopedbean for view scoped data would make view scoped data to be reinitialized to default on every single (ajax) postback, causing possibly non-working forms (see also points 4 and 5 here). Abusing a@ViewScopedbean for request, session or application scoped data, and abusing a@SessionScopedbean for application scoped data doesn’t affect the client, but it unnecessarily occupies server memory and is plain inefficient.Note that the scope should rather not be chosen based on performance implications, unless you really have a low memory footprint and want to go completely stateless; you’d need to use exclusively
@RequestScopedbeans and fiddle with request parameters to maintain the client’s state. Also note that when you have a single JSF page with differently scoped data, then it’s perfectly valid to put them in separate backing beans in a scope matching the data’s scope. The beans can just access each other via@ManagedPropertyin case of JSF managed beans or@Injectin case of CDI managed beans.See also:
@CustomScoped/NoneScoped/DependentIt’s not mentioned in your question, but (legacy) JSF also supports
@CustomScopedand@NoneScoped, which are rarely used in real world. The@CustomScopedmust refer a customMap<K, Bean>implementation in some broader scope which has overriddenMap#put()and/orMap#get()in order to have more fine grained control over bean creation and/or destroy.The JSF
@NoneScopedand CDI@Dependentbasically lives as long as a single EL-evaluation on the bean. Imagine a login form with two input fields referring a bean property and a command button referring a bean action, thus with in total three EL expressions, then effectively three instances will be created. One with the username set, one with the password set and one on which the action is invoked. You normally want to use this scope only on beans which should live as long as the bean where it’s being injected. So if a@NoneScopedor@Dependentis injected in a@SessionScoped, then it will live as long as the@SessionScopedbean.See also:
Flash scope
As last, JSF also supports the flash scope. It is backed by a short living cookie which is associated with a data entry in the session scope. Before the redirect, a cookie will be set on the HTTP response with a value which is uniquely associated with the data entry in the session scope. After the redirect, the presence of the flash scope cookie will be checked and the data entry associated with the cookie will be removed from the session scope and be put in the request scope of the redirected request. Finally the cookie will be removed from the HTTP response. This way the redirected request has access to request scoped data which was been prepared in the initial request.
This is actually not available as a managed bean scope, i.e. there’s no such thing as
@FlashScoped. The flash scope is only available as a map viaExternalContext#getFlash()in managed beans and#{flash}in EL.See also: