Which scope to use for a series of pages, each dep

2019-06-04 19:06发布

问题:

Currently I have four pages that are each backed by their own RequestScoped managed bean. An example of this would be the following...

backing search.xhtml

@RequestScoped
SearchBean

backing result.xhtml

@RequestScoped
ResultBean

backing detail.xhtml

@RequestScoped
DetailBean

backing action.xhtml

@RequestScoped
ActionBean

In each page (except for the search page), I inject the bean from the previous page to access the input parameters. For instance...

@RequestScoped
public class Result {

    @ManagedProperty("#{search}")
    private Search search;

    private ResultData resultData;

    private Service service;

    public Result() {

    }

    @PostConstruct
    public void init() {
        resultData = service.getResultData(search);
    }

    // getters & setters

}

@RequestScoped
public class Detail {

    @ManagedProperty("#{result}")
    private Result result;

    private DetailData detailData;

    private Service service;

    public Detail() {

    }

    @PostConstruct
    public void init() {
        detailData = service.getDetailData(result);
    }

    // getters & setters

}

@RequestScoped
public class Action {

    @ManagedProperty("#{detail}")
    private Detail detail;

    private ActionData actionData;

    private Service service;

    public Action() {

    }

    @PostConstruct
    public void init() {
        actionData = service.getActionData(detail);
    }

    // getters & setters

}

I want to use redirect so that I am able to use the back button, but while doing so I lose the input data from the managed bean in the request. I could use SessionScope for each bean, but I feel like I would be abusing it. Also, I am worried about the overhead by the time I get to the action page. At this point, since each bean injects the previous bean, all four ManagedBeans are created when the page is triggered. Is there a better way of doing this than using RequestScoped beans. I suppose I could have one SessionScoped bean for the series of pages and use it to carry input parameters across requests. This would also allow me to use the redirect feature and wouldn't load all four managed beans when the action page is finally hit. Any suggestions would be appreciated. Thanks.

回答1:

Depending on the tenure of the data you're storing, whether the pages actually occur in the sequence you listed and how much typing you're inclined to, you could use either

  1. Flash scope: This is scope is ideal for transfer of strictly temporary information between beans and pages. At first blush, it appears this scope would be ideal for your use case. I must emphasise the temporary nature of the data stored in this scope. It's also probably a good thing to point out that early versions of the implementations of this scope (especially with mojarra) had problems, so use at your own peril. I personally have not had any problems with the scope, so it really boils down to the version of JSF you're running

    Using the flash scope:

    • Understand Flash Scope in JSF2

    • How to keep JSF flash scope parameters on page reload?

  2. @SessionScoped: This scope, as you're already aware lasts really long. If the data you're using would likely outlast the beans/pages you've listed here, this is the way to go. It'll also survive refreshes and redirects without any problems (and there's the added benefit of doing less work to persist and reuse the data)