вторник, 22 сентября 2009 г.

glassfish thread pool

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


для начала необходимо его создать, через веб консоль администрирования и дать ему имя:
Configuration -> Thread Pools -> New


использовать так:
...
import com.sun.enterprise.connectors.ConnectorRuntimeException;
import com.sun.enterprise.connectors.work.WorkManagerFactory;
import javax.resource.spi.work.Work;
import javax.resource.spi.work.WorkException;
import javax.resource.spi.work.WorkManager;
...
    try {
        WorkManager workManager = WorkManagerFactory.getWorkManager("threadpoolname");
        Work work = new Work() {
            @Override
            public void release() {
//вызывается если необходимо остановить тред
            }
 
            @Override
            public void run() {
//код, который надо распараллелить
            }
        };
        workManager.scheduleWork(work);
    } catch (WorkException e) {
//что-то сделать
} catch (ConnectorRuntimeException e) {
//что-то сделать
...
}
и не забудьте подключить библиотеку glassfish_dir/lib/appserv-rt.jar

четверг, 17 сентября 2009 г.

жава ее Шедулер своими руками

Все мы иногда что-нибудь планируем, ставим себе галочки в уме что утром будем просыпаться и делать зарядку или что завтра ляжем спать не в два а часов в одинадцать. так вот, если нифига не получается - значит плохой планировщик задач. сегодня напишем свой планировщик задач для javaee app-сервера:
package myproject.ejb;

import java.util.Date;
import javax.annotation.Resource;
import javax.ejb.Stateless;
import javax.ejb.Timeout;
import javax.ejb.Timer;
import javax.ejb.TimerService;

@Stateless
public class UsualBean implements UsualLocal {

@Resource
TimerService timerService;

private static long intervalDuration = 3000;

private void makeMeHappy() {
System.out.println("i am so happy at " + new Date());
}

public void createTimer(long intervalDuration) {
//это что бы два раза не выполнить одно и то же задание
for (Object o : timerService.getTimers()) {
if (o instanceof Timer) {
((Timer) o).cancel();
}
}

this.intervalDuration = intervalDuration;
//обратите внимание на второй параметр, это может быть любой Serializable объект
Timer timer = timerService.createTimer(intervalDuration, "all your base are belong to us");
}

@Timeout
private void timeout(Timer timer) {
this.makeMeHappy();
//таймер срабатывает один раз, мне же надо через определенный интервал
timerService.createTimer(intervalDuration, timer.getInfo());
}
}


теперь осталось только запустить этот шедуллер методом createTimer, можно при старте app-сервера

вторник, 15 сентября 2009 г.

Как выполнить определенный код при старте app-сервера

На днях у меня возникла необходимость запустить шедулер на стороне app-сервера. Про сам шедулер я напишу в одном из следующих сообщений, а про технологию запуска чего-либо при старте апп-сервера расскажу сейчас...

Вообщем надо поправить файл web.xml , если вы не используете веб компоненту в своем энтерпрайз проекте, придется создать пустой проект с одним этим файлеком.


<web-app version="2.5" xmlns="http://java.sun.com/xml/ns/javaee" xsi="http://www.w3.org/2001/XMLSchema-instance" schemalocation="http://java.sun.co">
<listener>
<listener-class>myproject.ejb.MyContextListener</listener-class>
</listener>
</web-app>

Это тот класс, методы которого будут вызываться, когда изменяется контекст сервлета.

package myproject.ejb.MyContextListener;

import javax.servlet.ServletContextEvent;
import javax.servlet.ServletContextListener;

public class MyContextListener implements ServletContextListener {

public void contextDestroyed(ServletContextEvent sce) {
System.out.println("ServletContextListener::contextDestroyed");
}

public void contextInitialized(ServletContextEvent sce) {
System.out.println("ServletContextListener::contextInitialized");
}
}


как-то так :)