Модераторы: LSD, AntonSaburov
  

Поиск:

Ответ в темуСоздание новой темы Создание опроса
> инициализация фабрикой сессионного бина (EJB3) 
V
    Опции темы
tool
Дата 8.6.2008, 21:45 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 7
Регистрация: 8.6.2008

Репутация: нет
Всего: нет



Изучаю EJB3. Посему вопросы наверное примитивные.

1. 
Имею session bean, бизнес интерфейс которого (A) возвращает ссылку на другой  бизнес интерфейс (B - отдельный bean). По-сути - A - фабрика B.
Вопрос - как в EJB 3 можно выполнить инициализацию бина с состоянием не добавляет метод инициализации в его бизнес (remote) интерфейс? Грубо говоря, я не хочу допускать инициализации (B) за пределами моей фабрики (A). 

2.
Поясните разницу между @local локальными и @remote удалёнными вызовами (методами) в EJB3. Ранее, насколько помню, это должны были быть совершенно различные интерфейсы, теперь методы можно смешивать внутри одного бизнес-интерфейса (не понятно как это работает).
PM MAIL   Вверх
powerOn
Дата 8.6.2008, 22:53 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


software saboteur
****


Профиль
Группа: Участник
Сообщений: 4367
Регистрация: 7.10.2005

Репутация: 28
Всего: 159



Цитата(tool @  8.6.2008,  22:45 Найти цитируемый пост)
Имею session bean, бизнес интерфейс которого (A) возвращает ссылку на другой  бизнес интерфейс (B - отдельный bean). По-сути - A - фабрика B.
Вопрос - как в EJB 3 можно выполнить инициализацию бина с состоянием не добавляет метод инициализации в его бизнес (remote) интерфейс? Грубо говоря, я не хочу допускать инициализации (B) за пределами моей фабрики (A). 


На вряд ли это будет фабрикой в такой ситуации. Скорее это ближе к сервис-локатору, чем к фабрике.
Инициализация EJB компонента производится самим компонентом, поскольку создаётся он контейнером EJB. 
Инициализировать можно в конструкторе без параметров и в методе помеченном аннотацией @PostConstruct (последний будет выполнен после инжекции бинов, от которых он зависит).

Если ситуация такая, что нужно инициализировать бин, перед его использованием, то можно можно сделать это в "@PostConstruct" методе того компонента куда он был инжектирован. (т.е. если бину A засеттить бин B, то инициализацию бина B можно сделать в методе помеченном аннотацией @PostConstruct бина A). 

Цитата(tool @  8.6.2008,  22:45 Найти цитируемый пост)
Грубо говоря, я не хочу допускать инициализации (B) за пределами моей фабрики (A). 

А как кстати ссылки на бины стали доступны вашей фабрике? Они были инжектированы контейнером EJB? Если так то ещё можно произвести инициализацию в методе @PostConstruct вашей фабрики. 

Цитата(tool @  8.6.2008,  22:45 Найти цитируемый пост)
Поясните разницу между @local локальными и @remote удалёнными вызовами (методами) в EJB3.

При вызове методов @Local интерфейса параметры можно передавать по ссылке. Т.е. то что передашь, может быть изменено в вызываемом методе и результат будет доступен в вызывающем (например, тот же callback в данном случае прокатит). С параметрами  методов @Remote интерфейса такой фокус не пройдёт. Вероятно по тому, что контейнер подготавливает параметры для удаленного вызова (проксирует, сериализует). Отсюда и простой вывод, то для увеличения производительности не стоит использовать @Remote интерфейс где в нем нет необходимости (т.е. не предполагается удалённого вызова).




--------------------
user posted image нет времени думать - нужно писать КОД!

PM MAIL   Вверх
Maksym
Дата 7.11.2008, 13:34 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


.
***


Профиль
Группа: Участник Клуба
Сообщений: 1456
Регистрация: 19.8.2005
Где: Odessa, Black Sea

Репутация: 24
Всего: 62



Возможно ли вызвать методы @Local интерфейса бина B если он был получен как Remote (внутри бина А)? и наоборот..?
Либо бин можно получить только однозначно либо для Remote, либо для Local использования (одно из двух, но не оба одновременно)?
PM MAIL   Вверх
powerOn
Дата 7.11.2008, 15:38 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


software saboteur
****


Профиль
Группа: Участник
Сообщений: 4367
Регистрация: 7.10.2005

Репутация: 28
Всего: 159



@Remote интерфейс насколько мне известно проксируется. Т.е. при его инъекции мы получаем прокси, которая дополнительно сериализует и десериальзует параметры вызова т.к. это необходимо для удалённых клиентов (отсюда нельзя в remote интерфейс передавать параметры по ссылке). А @Local интерфейс - это обыкновенный интерфейс в который можно передавать значения по ссылке.
Можно ли привести @Remote интерфейс к локальному? Думаю что нет, это как минимум нелогично. А привести ссылку на local к remote интерфейсу вполне должно получиться. Так же думаю, что попробовать поиграть с instanceof думаю никто не помешает.


--------------------
user posted image нет времени думать - нужно писать КОД!

PM MAIL   Вверх
Maksym
Дата 7.11.2008, 17:19 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


.
***


Профиль
Группа: Участник Клуба
Сообщений: 1456
Регистрация: 19.8.2005
Где: Odessa, Black Sea

Репутация: 24
Всего: 62



Спасибо за мысли. Поиграюсь -- напишу о результате.
PM MAIL   Вверх
Maksym
Дата 9.11.2008, 15:03 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


.
***


Профиль
Группа: Участник Клуба
Сообщений: 1456
Регистрация: 19.8.2005
Где: Odessa, Black Sea

Репутация: 24
Всего: 62



Код

@Remote
public interface MyInterfaceRemote {
    public void remoteCall();
}

@Local
public interface MyInterfaceLocal {
    public void localInitialization();
}

@Stateful
public class MyBeanImplementation implements MyInterfaceRemote , MyInterfaceLocal {
    public void remoteCall() {}
    public void localInitialization() {}
}

@Remote
public interface MyBeanCallerInterface {
    public MyInterfaceRemote getMyBean();
}

@Stateful
@EJBs({
    @EJB(name="myBean",beanInterface=MyInterfaceRemote.class),
    @EJB(name="myBean",beanInterface=MyInterfaceLocal.class)
})
public class MyBeanCaller implements MyBeanCallerInterface {
    public MyInterfaceRemote getMyBean() {
        MyInterfaceRemote myBean = (MyInterfaceRemote) context.lookup("myBean");
        MyInterfaceLocal myLocalBean = (MyInterfaceLocal) myBean;
        myLocalBean.localInitialization();
        return myBean;
    }
}


Приведенный пример не работает, потому что (myBean instanceof MyInterfaceLocal) в методе getMyBean() вернет false -- не получается откастить к локальному интерфейсу.
В то же время если в этом примере MyInterfaceLocal объявить как @Remote то кастинг от одного ремоут интерфеса к другому будет успешным и методы обоих будут корректно вызываться на одном и том же инстасе бина.
Но мне необходимо скрыть инициализацию (вызов localInitialization()) от внешних потребителей. @PostConstruct и т.п. методы не подходят потому что в реальном примере в localInitialization() каждый раз передается текущее состояние вызывающего бина (в примере MyBeanCaller).
PM MAIL   Вверх
powerOn
Дата 9.11.2008, 15:51 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


software saboteur
****


Профиль
Группа: Участник
Сообщений: 4367
Регистрация: 7.10.2005

Репутация: 28
Всего: 159



Я написал похожий тест, но только с инъекцией. Просмотрел типы объектов и понял, что контейнер всегда инжектирует прокси. Будь это локалный или удаленный интерфейс, но вероятно с разной имплементацией. Доля логики в этом конечно же есть. Ведь по спецификации контейнер не гарантирует что один и тот же вызов сделанный 2 раза будет выполнен на одном stateless бине (а я тестировал именно на stateless), заглушка для stateless бина запросто может вытаскивать для каждого вызова свободный объект из пула. Привести типы естественно не удалось.

Код

@Local
public interface ILocal1 {
    public void local1Call();
}

@Local
public interface ILocal2 {
    public void local2Call();
}

@Remote
public interface IRemote1 {
    public void remote1Call();
}

@Remote
public interface IRemote2 {
    public void remote2Call();
}

@Stateless
public class SimpleEJB implements ILocal1, ILocal2, IRemote1, IRemote2 {
    public void local1Call() {
        System.out.println("local1Call");
    }
    public void local2Call() {
        System.out.println("local2Call");
    }
    public void remote1Call() {
        System.out.println("remote1Call");
    }
    public void remote2Call() {
        System.out.println("remote2Call");
    }
}

@WebService
@Stateless
public class SimpleService {

    @EJB
    private ILocal1 iLocal1;
    @EJB
    private IRemote1 iRemote1;

    @WebMethod
    public void testRemote() {
        System.out.println(iRemote1.getClass().getName());

        System.out.println("IRemote1 instanceof ILocal2 : " + (iRemote1 instanceof ILocal2));
        System.out.println("IRemote1 instanceof ILocal1 : " + (iRemote1 instanceof ILocal1));
        System.out.println("IRemote1 instanceof IRemote2 : " + (iRemote1 instanceof IRemote2));
    }

    @WebMethod
    public void testLocal() {
        System.out.println(iLocal1.getClass().getName());

        System.out.println("ILocal1 instanceof ILocal2 : " + (iLocal1 instanceof ILocal2));
        System.out.println("ILocal1 instanceof IRemote1 : " + (iLocal1 instanceof IRemote1));
        System.out.println("ILocal1 instanceof IRemote2 : " + (iLocal1 instanceof IRemote2));
    }
}


Цитата

simpleejb._IRemote1_Wrapper
IRemote1 instanceof ILocal2 : false
IRemote1 instanceof ILocal1 : false
IRemote1 instanceof IRemote2 : false

$Proxy222
ILocal1 instanceof ILocal2 : false
ILocal1 instanceof IRemote1 : false
ILocal1 instanceof IRemote2 : false


Попробую написать тест и для stateful бина.

Цитата(Maksym @  9.11.2008,  15:03 Найти цитируемый пост)
context.lookup("myBean");

Такой вызов кстати возвращает ссылку на Remote интерфейс. Поскольку только они регистрируются в JNDI.



--------------------
user posted image нет времени думать - нужно писать КОД!

PM MAIL   Вверх
Maksym
Дата 10.11.2008, 14:37 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


.
***


Профиль
Группа: Участник Клуба
Сообщений: 1456
Регистрация: 19.8.2005
Где: Odessa, Black Sea

Репутация: 24
Всего: 62



powerOn
Спасибо за исследование!
Пока четкости понимания у меня нет. Должен же быть способ локально достучаться из бина к бину внутри контейнера и поработать с ним по ссылке...
PM MAIL   Вверх
powerOn
Дата 10.11.2008, 15:05 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


software saboteur
****


Профиль
Группа: Участник
Сообщений: 4367
Регистрация: 7.10.2005

Репутация: 28
Всего: 159



Цитата(Maksym @  10.11.2008,  14:37 Найти цитируемый пост)
Должен же быть способ локально достучаться из бина к бину внутри контейнера и поработать с ним по ссылке... 


Я могу ошибаться, но думаю такого способа нет (только если решлекшином из проксей выцеплять, или самому написать бин таким образом, что бы он ссылку на себя выдавал наверх). Все таки это контейнеро-управляемые сущности и доступ к ним должен быть всегда через промежуточное звено. Контейнер и прокси в данном случае одно и тоже. Это важно, например, при выполнении транзакций и разраничения прав доступа - прокси и транзакцию начнёт и права проверит. 



--------------------
user posted image нет времени думать - нужно писать КОД!

PM MAIL   Вверх
Maksym
Дата 10.11.2008, 20:30 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


.
***


Профиль
Группа: Участник Клуба
Сообщений: 1456
Регистрация: 19.8.2005
Где: Odessa, Black Sea

Репутация: 24
Всего: 62



powerOn
Исходя из этих рассуждений архитектура, в которой все бины отдаются через один управляющий бин, который их инициализирует, -- идеологически неверна. Контейнер должен сам дать готовый к использованию бин. Получается так.
И исходя из этого невозможно, например, расшарить между несколькими бинами такие вещи как секьюрити конекст (кастомный), разделяемый ресурс и т.п.
Или я что-то путаю?


PM MAIL   Вверх
powerOn
Дата 11.11.2008, 09:45 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


software saboteur
****


Профиль
Группа: Участник
Сообщений: 4367
Регистрация: 7.10.2005

Репутация: 28
Всего: 159



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




--------------------
user posted image нет времени думать - нужно писать КОД!

PM MAIL   Вверх
  
Ответ в темуСоздание новой темы Создание опроса
Правила форума "Java"
LSD   AntonSaburov
powerOn   tux
  • Прежде, чем задать вопрос, прочтите это!
  • Книги по Java собираются здесь.
  • Документация и ресурсы по Java находятся здесь.
  • Используйте теги [code=java][/code] для подсветки кода. Используйтe чекбокс "транслит", если у Вас нет русских шрифтов.
  • Помечайте свой вопрос как решённый, если на него получен ответ. Ссылка "Пометить как решённый" находится над первым постом.
  • Действия модераторов можно обсудить здесь.
  • FAQ раздела лежит здесь.

Если Вам помогли, и атмосфера форума Вам понравилась, то заходите к нам чаще! С уважением, LSD, AntonSaburov, powerOn, tux.

 
0 Пользователей читают эту тему (0 Гостей и 0 Скрытых Пользователей)
0 Пользователей:
« Предыдущая тема | Java EE (J2EE) и Spring | Следующая тема »


 




[ Время генерации скрипта: 0.0540 ]   [ Использовано запросов: 22 ]   [ GZIP включён ]


Реклама на сайте     Информационное спонсорство

 
По вопросам размещения рекламы пишите на vladimir(sobaka)vingrad.ru
Отказ от ответственности     Powered by Invision Power Board(R) 1.3 © 2003  IPS, Inc.