EJB 3.1.Нужна ли аннотация @Local? - PullRequest
7 голосов
/ 29 января 2012

До сих пор я почти всегда работал с EJB без интерфейса и немного понимал необходимость аннотации @Local.Рассмотрим пример:

public interface MyBeanIntf { void doStuff(); }

@Stateless
public class MyBean implements MyBeanIntf { public void doStuff(){ } }

Должен ли MyBeanIntf быть помечен как @Local?Я не вижу никакой выгоды от этого, потому что даже когда я не аннотирую его как @Local, я все еще могу использовать DI , чтобы правильно внедрить его в UI Controller:

@Named
@SessionScoped
public class TestController implements Serializable {

  // injection works perfectly, even when MyBeanIntf is not marked as @Local
  @Inject
  private MyBeanIntf myBean;

  // or even like this:
  // @EJB
  // private MyBeanIntf myBean;

}

Давайте сделаем это более сложным:

public interface MyBeanIntf { void doStuff(); }
public class MySuperBean implements MyBeanIntf { public void doStuff() { } }

@Stateless
public class MyBean extends MySuperBean { }

Является ли MyBean теперь допустимым Local EJB бином?У меня есть некоторые сомнения, потому что он реализует интерфейс косвенно.

1 Ответ

8 голосов
/ 29 января 2012

Если ваш EJB реализует некоторый интерфейс, но вы не указываете (ни на EJB, ни на самом интерфейсе), какой интерфейс у него (@Remote, @Local), чем предполагается, что он является @Local.

Следовательно, ваш код:

public interface MyBeanIntf { void doStuff(); }

@Stateless
public class MyBean implements MyBeanIntf { public void doStuff(){ } }

семантически идентичен следующему:

@Local
public interface MyBeanIntf { void doStuff(); }

@Stateless
public class MyBean implements MyBeanIntf { public void doStuff(){ } }

Когда речь идет о второй части вашего вопроса, я думаю, что раздел 4.9.2.1 Суперклассы Session Bean из спецификации EJB 3.1 FR были бы вам интересны.Насколько я понимаю (так что это может быть неправильно), кажется, что ваш компонент не должен рассматриваться как представляющий действительный локальный интерфейс из-за следующей выдержки:

@Stateless
public class A implements Foo { ... }

@Stateless
public class B extends A implements Bar { ... }

Предполагается, что Foo и Barлокальные бизнес-интерфейсы, и нет никакого связанного дескриптора развертывания, сессионный компонент A предоставляет локальный бизнес-интерфейс Foo, а сессионный компонент B предоставляет локальный бизнес-интерфейс Bar, но не нужен Foo .

сессионный компонент Bявно включить Foo в набор открытых представлений для этого интерфейса.

Обновление:

В качестве дополнения еще одна выдержка из спецификации:

Класс сессионных компонентов может иметь суперклассы, которые сами являются классами сессионных компонентов.Однако для этого случая нет специальных правил, применимых к обработке аннотаций или дескриптора развертывания.В целях обработки определенного класса сессионных компонентов вся обработка суперкласса идентична независимо от того, являются ли суперклассы самими классами сессионных компонентов.

...