Ответ 1
Проверьте интерфейс LifecycleListener:
http://glassfish.java.net/nonav/docs/v3/api/index.html?com/sun/appserv/server/LifecycleListener.html
http://docs.oracle.com/cd/E18930_01/html/821-2418/beamc.html
У меня есть программа/поток Java, которые я хочу развернуть на сервере приложений (GlassFish). Поток должен запускаться как "служба", которая запускается, когда Сервер приложений запускается и останавливается, когда сервер приложений закрывается.
Как мне это сделать? Это не сеанс Bean или MDB. Это просто поток.
Проверьте интерфейс LifecycleListener:
http://glassfish.java.net/nonav/docs/v3/api/index.html?com/sun/appserv/server/LifecycleListener.html
http://docs.oracle.com/cd/E18930_01/html/821-2418/beamc.html
Я только сделал это с Tomcat, но он должен работать в Glassfish.
Создайте класс Listener, который реализует javax.servlet.ServletContextListener
, затем поместите его в web.xml. Он будет уведомлен о запуске и уничтожении вашего веб-приложения.
Простой класс слушателя:
public class Listener implements javax.servlet.ServletContextListener {
MyThread myThread;
public void contextInitialized(ServletContextEvent sce) {
myThread = new MyThread();
myThread.start();
}
public void contextDestroyed(ServletContextEvent sce) {
if (myThread != null) {
myThread.setStop(true);
myThread.interrupt();
}
}
}
Это происходит в web.xml после вашего последнего "контекстного параметра" и перед вашим первым "сервлетом":
<listener>
<listener-class>atis.Listener</listener-class>
</listener>
Не знаю, рекомендуются ли такие вещи или нет, но в прошлом это отлично работало для меня.
Это не то, что вы должны делать на любом сервере приложений, если только у вас нет доступа к управляемым потокам, предоставляемым сервером приложений. Я не знаком с Glassfish, но вы можете сделать это в Websphere или Weblogic, используя обычный WorkManager.
По-видимому, то же самое можно сделать в Glassfish и JBOSS через JCA WorkManager (с которым я не знаком).
Создайте сервлет, метод init которого запускает поток, который является основной программой.
public void init() throws ServletException {
mailThread = new MailSendThread();
mailThread.start();
}
В нашем приложении файл web.xml добавляет сервлет, который включает элемент загрузки при запуске, где число - это порядок, в котором он запускается.
<servlet>
<servlet-name>Mail Sending Servlet</servlet-name>
<servlet-class>MailServlet</servlet-class>
<load-on-startup>2</load-on-startup>
</servlet>
Мне также нужно создать несколько потоков, где каждый поток откроет сокет для других удаленных процессов, работающих в моем приложении Glassfish. Сервер. Я заглянул в LifecycleListener bean, предоставленный Glassfish, который вам нужно реализовать.
Я создал прототип для выполнения работы с потоками и сокетами в реализации LifecycleListener, и это действительно не помогло в управлении этими ресурсами. Чтобы получить доступ к LifecycleListener, мне пришлось установить публичный статический метод, который выполнил бы нужные действия.
Я не вижу значения в LifecycleListener, потому что я мог бы выполнить ту же самую работу внутри моего EJB, который является клиентом, вызывающим LifecycleListener. Потому что на самом деле нет правильного управления Thread и Socket в bean.
Мне сказали, что JCA может быть лучшим способом. Я не пробовал это.
Я запускаю объект с таймером со службой таймера и только одно однократное истечение. Затем, в таймаут, я делаю то, что хочу делать с потоком.
http://onjava.com/pub/a/onjava/2004/10/13/j2ee-timers.html
Для меня это сработало, поскольку он использует компоненты J2EE и представляет собой другой поток.