Когда начинающий разработчик сталкивается с сервлетами, ему бывает очень сложно понять, как он работает и от чего зависит эта работа. Всё потому, что все примеры и видеоуроки рассчитаны на людей, понимающих природу сервлетов и что за чем следует. Поэтому я решил написать руководство по созданию самых простых сервлетов. Возможно, эта статья кому-нибудь поможет.
Итак.
Предположим, что Вы уже где-то скачали пример с применением maven и Вам удалось задеплоить Ваш код на Tomcat (с этого обычно начинается познание сервлетов) любым способом (WAR-архивом или прямо из среды разработки). Вы имеете структуру приложения, в которой присутствует файл web.xml. C него и надо начинать создание страниц.
Первое и самое важное: машина не видит прямой связи между куском адресной строки и одноимённой страницей в Вашем проекте. localhost:8080/имя_WAR/test и test.jsp — не одно и то же. /test — это «url-метка» сервлета. По которой машина находит нужный Java-файл и тот уже указывает на test.jsp.
Путь от чтения кода машиной и до отображения страницы в браузере выглядит так:
webapp/WEB-INF/web.xml -> servlet
---> ru.user.project/web/ClassName -> request
---> page.jsp
Да, пока ничего не понятно, но мы ещё вернёмся к этой схеме. Если описать её простыми человеческими словами, то это будет выглядеть так:
Из файла web.xml через сервлет машина получает путь к Java-классу, который, в свою очередь, направляет машину на искомую страницу.
Это было лирическое отступление, переходим к коду.
Итак, мы имеем задеплоенный на Tomcat проект, главная страница которого открывается по вызову localhost:8080/имя_WAR (если мы деплоили WAR-файл).
Открываем web.xml. Этот файл сканируется Tomcat'ом в первую очередь. Здесь мы и зададим начало пути. Вот код нашего web.xml:
<web-app xmlns="http://xmlns.jcp.org/xml/ns/javaee"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee
http://xmlns.jcp.org/xml/ns/javaee/web-app_3_1.xsd"
version="3.1">
<display-name>Test</display-name>
<servlet>
<servlet-name>testServlet</servlet-name>
<servlet-class>ru.user.project.web.TestServlet</servlet-class>
</servlet>
<servlet-mapping>
<servlet-name>testServlet</servlet-name>
<url-pattern>/test</url-pattern>
</servlet-mapping>
</web-app>
Сервлет связывает ссылку из адресной строки и Java-класс. Java-класс, в нашем случае, открывает JSP-страницу. Сервлет состоит из 2 составляющих:
<servlet> //здесь прописан путь к Java-классу
<servlet-name>testServlet</servlet-name>
<servlet-class>ru.user.project.web.TestServlet</servlet-class>
</servlet>
<servlet-mapping> //здесь прописан путь к куску адресной строки, вызывающей сервлет
<servlet-name>testServlet</servlet-name>
<url-pattern>/test</url-pattern>
</servlet-mapping>
Прописываем <servlet-class>. По этому пути хранится Java-класс, который обработается при вызове адресной строки. Потом дописываем <servlet-mapping>. Это кусок адреса из адресной строки, привязанный к сервлету. Когда мы допишем к нашей первоначальной строке /test, начнётся магия. Но пока мы ещё не дописали остальную часть кода. Пишем Java-файл. Он у нас находится по адресу ru.user.project.web (для этого нужно создать папку web, если её нет).
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
/**
* Created by promoscow on 17.07.17.
*/
public class TestServlet extends HttpServlet {
@Override
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
request.getRequestDispatcher("/test.jsp").forward(request, response);
}
}
Класс надо унаследовать от HttpServlet и переопределить метод doGet(); В переопределённом методе мы пишем название строки, на которую будет осуществлён переход (в нашем случае, это "/test.jsp".
Таким образом, при вызове адреса localhost:8080/имя_WAR/test Tomcat находит нужный <url-pattern>, выясняет, что он принадлежит testServlet, далее видит, что этому testServlet принадлежит Java-файл TestSevlet, исполняет его, а в Java-файле идёт переход на test.jsp. Осталось написать test.jsp:
<%--
Created by IntelliJ IDEA.
User: promoscow
Date: 17.07.17
Time: 23:22
To change this template use File | Settings | File Templates.
--%>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
<title>Test</title>
</head>
<body>
Hey there! It's test servlet page!
</body>
</html>
Теперь, когда пользователь допишет /test к изначальному адресу, выполнится алгоритм, описанный в начале статьи (помните, я обещал к ней вернуться?) и браузер покажет содержимое файла test.jsp. Также, можно, например, написать в стартовом файле (например, index.html) ссылку:
<a href="test">Test page</a>
И произойдёт вышеописанная цепь событий, которая вызовет, в итоге, страницу test.jsp.
Надеюсь, эта статья поможет барахтающимся в поисках здравого смысла начинающим разработчикам написать первый сервлет, а уже в дальнейшем к этому пониманию постепенно будет присоединяться всё остальное (как это обычно бывает).