java - 在 Java 类中注入(inject) EJB 时出现 NullPointerException

标签 java jsf ejb

我认为出现这个问题是因为我对 EJB 没有了解。我的实体有一个服务类,它是@Stateless。当我通过在 session 范围的表示模型中注入(inject) @EJB 来使用它时,一切正常。但是现在我想在一个 DataModel 中使用这个 EJB 服务,我已经覆盖了它以用于我的表示模型:

public class LazyUserDataModel extends LazyDataModel<User> {

    @EJB
    private UserService service;

    @Override
    public List<User> load(int first, int pageSize, String sortField, SortOrder sortOrder, Map filters) {
        List<User> users;
        users= service.findAllUsers();
        this.setRowCount(users.size());
        return users; 
    }
}

在执行时,我在位置“users= service.findAllUsers();”处得到一个 NullPointerException当我在我的演示模型中覆盖此 DataModel 时,同样有效:

@Named
@SessionScoped
public class UserPM {
    @EJB
    private UserService service;

    private LazyDataModel<User> lazyUsers;

    public UserPM() {

            // Don't works
            //lazyUsers = new LazyUserDataModel();

            lazyUsers = new LazyDataModel() {
            @Override
                public List<User> load(int first, int pageSize, String sortField, SortOrder sortOrder, Map filters) {
                    List<User> users;
                    users = service.findAllUsers();
                    this.setRowCount(users .size());
                    return users ; 
                }
        };
    }
}

难道不能在普通 Java 类中注入(inject) EJB 吗?我必须做什么才能不必在表示模型中定义数据模型?

谢谢

最佳答案

EJB 仅注入(inject)托管 bean。当一个 bean 被一些注入(inject)容器管理时,它被管理,例如通过 JSF 自己的 @ManagedBean,CDI 的 @Named 等。您甚至可以在另一个 EJB 中注入(inject)一个 EJB。您不能在非托管类中注入(inject) EJB(但是您可以手动从 JNDI 中获取它,但这很丑陋)。

您基本上有以下选项:

  1. 在托管 bean 的 @PostConstruct 中,构建数据模型,您将结果作为参数传递(请注意,这也是标准数据模型(如 ListDataModel)的工​​作方式)。

    @PostConstruct
    public void init() {
        lazyUsers = new LazyUserDataModel(service.findAllUsers());
    }
    

  2. LazyUserDataModel 抽象化,从而要求用户提供结果。

    public abstract class LazyUserDataModel extends LazyDataModel<User> {
    
        @Override
        public List<User> load(int first, int pageSize, String sortField, SortOrder sortOrder, Map filters) {
            List<User> users;
            users = findAllUsers();
            this.setRowCount(users.size());
            return users ; 
        }
    
        public abstract List<User> findAllUsers();
    
    }
    

    这样匿名类的伤害就小

    lazyUsers = new LazyUserDataModel() {
        @Override
        public List<User> findAllUsers() {
            return service.findAllUsers();
        }
    };
    

  3. 也将 LazyUserDataModel 设为托管 bean 并将其注入(inject)。

    @Named @RequestScoped
    public class LazyUserDataModel extends LazyDataModel<User> {
        // ...
    }
    

    @Inject
    private LazyUserDataModel lazyUsers;
    

  4. 像您想象的那样创建一个完整的匿名实例。


与具体问题无关,没有必要通过 LazyDataModel 提供所有 记录。它的目的是让您可以根据当前分页状态使用 SQL 功能(LIMITOFFSET 和 friend )仅请求一个子集或记录,这样您就不必不需要在 Java 内存中有成百上千条记录,但只需要十条左右。换句话说,如果您从不使用 load() 方法的 first 和/或 pageSize 参数,您很可能正在接近它完全错误。

关于java - 在 Java 类中注入(inject) EJB 时出现 NullPointerException,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/18017008/

相关文章:

java - 如何使用 "org.apache.shiro.UnavailableSecurityManagerException"修复 "SecurityUtils.getSubject()"错误

java - AsyncTask已经完成

java - 如何在 JSF/Richfaces 上设置 HttpOnly 标志

java - Spring+Hibernate 与 Hibernate 配置。 UnsupportedOperationException : Not supported by BasicDataSource 的原因

java - 如何在 Liferay 6.0.6 中的 JSF portlet 中上传文件

http - 确保 JSF 网页未根据 YSlow 进行缓存

java - Glassfish 还是 Tomcat+OpenEJB?哪种变体更适合小型应用程序?

jsf - 在EJB中进行验证时,如何在jsf中显示多条错误消息?

Java:格式说明符 %x 和 %h 有什么区别?

java - Windows 10 不支持请求方法 'HEAD'