Подтвердить что ты не робот

Я не понимаю, как поддержка Async в API сервлетов 3.0

Я исхожу из фона Java SE, и я сделал несколько уроков сервлетов и прочитал Head First JSP и сервлет. Я читаю статью JavaWorld.com о поддержке Async, но я не совсем понимаю ее.

Что такое Async? В чем разница между Ajax и Servlet Async?

P.S У меня есть PHP-фон с ajax, и я знаю это понятие, но я не пробовал его с помощью java

4b9b3361

Ответ 1

В традиционной модели Servlet обычно бывает, что 1 запрос соответствует 1 потоку.

Эти потоки обычно поступают из пула, который управляется контейнером Servlet. Контейнер Servlet может обрабатывать только новые запросы, если в этом пуле есть свободные потоки. Пока ваш собственный код занят обработкой запроса, поток не является бесплатным.

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

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

Пример:

@WebServlet(urlPatterns = "/somepath", asyncSupported = true)
public class AsyncServlet extends HttpServlet {

    @EJB
    private AsyncBean asyncBean;

    public void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
        AsyncContext asyncContext = request.startAsync();

        // The following line will not block and return immediately
        asyncBean.doAsyncStuff(asyncContext);

    } // Shortly after this method has ended, thread will be returned to pool
}

С AsyncBean реализуется как:

@Stateless
public class AsyncBean {

    @Asynchronous
    public void doAsyncStuff(AsyncContext asyncContext) throws IOException {
        asyncContext.getResponse().getWriter().write("test");
    }
}

В приведенном выше коде, где-то вскоре после возврата из метода AsyncServlet#doGet() поток Servlet будет возвращен в пул. "Запрос" (задача) для выполнения AsyncBean#doAsyncStuff() будет помещен в очередь для сбора пула потоков EJB.

Ответ на ПОЧЕМУ и КОГДА вы будете использовать это не так просто. Если вы просто хотите сохранить потоки, то в приведенном выше случае вы бы обменяли один поток из одного пула потоков для другого (в данном случае пул сервлетов против пула асинхронных EJB), а чистая выгода не будет такой. Вы могли бы также дать вашему потоку потока сервлета дополнительный поток.

В более сложных сценариях вы можете, однако, выполнять более мелкомасштабное управление запросами; разделите их на несколько задач и попросите пул потоков обслуживать эти задачи. Например. Представьте себе 100 запросов на загрузку 10 МБ файла, обработанных 10 потоками, которые round-robin дают 100 Кбайт времени для каждого запроса.

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