Самое первое web-приложение Оглавление Самое первое web-приложение ............................................................................................................................ 1 Самый настоящий «Hello, World!» ...............................................................................................................1 HelloWorldServlet.java ...................................................................................................................................2 Дескриптор (web.xml) ....................................................................................................................................3 Скрипт сборки (build.xml) ..............................................................................................................................3 Развёртываем (деплоим) ............................................................................................................................6 Проверяем, что всё работает ......................................................................................................................6 Самый настоящий «Hello, World!» Пришло время почувствовать всё на практике. Для экспериментов будем использовать JBoss 4.2.3. Новый проект будет иметь следующую структуру (можно создать в любой IDE). Я обычно не полагаюсь на ту структуру, которую предлагают IDE для web/enterprise приложений (они делают это так, как им нравится), у меня есть своя, проверенная опытом структура проекта: HelloProject +-bin +-dist +-lib +-ee-lib javaee.jar +-src +-com +-company +-hello +-servlets HelloWorldServlet.java +-web-res +-WEB-INF web.xml build.xml javaee.jar содержит нужные базовые классы, но используется только на этапе компиляции, т. е. не кладётся в сборку, т. к. классы, которые в этой jar-ке определены, есть в любом сервере приложений. HelloWorldServlet.java package com.company.hello.servlets; import java.io.IOException; import javax.servlet.ServletException; import javax.servlet.http.HttpServlet; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; public class HelloWorldServlet extends HttpServlet { @Override protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException { resp.getOutputStream().println("<html><head/><body><h1>" + "Hello, World!" + "</h1></body></html>"); } } Это сервлет. Он представляет собой достаточно примитивный интерфейс для работы с входящими HTTP-запросами и является по сути дела тем самым обработчиком, про которые шла речь ранее. Некоторые всерьез полагают, что в сервлетах нужно писать генерацию HTML-страницы. Это не так. В общем случае, сервлеты используются как диспетчеры запросов и переадресуют обработку внутрь приложения, но в нашем случае мы просто распечатаем сообщение. Как следует из кода, метод doGet() вызовется при выполнении GET-запроса. В этом же классе можно переопределить и другие методы, соответствующие разным видам HTTPзапросов. PUT/DELETE/HEAD/POST... Чаще всего нужны только doGet() и doPost(). Часто делают даже так, чтобы doGet() вызывал doPost() или наоборот, если есть желание обрабатывать эти два запроса аналогично. Дескриптор (web.xml) <?xml version="1.0" encoding="UTF-8"?> <web-app id="WebApp_ID" version="2.5" xmlns="http://java.sun.com/xml/ns/javaee" xmlns:web="http://java.sun.com/xml/ns/javaee/web-app_2_5.xsd" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/webapp_2_5.xsd"> <display-name>HelloApp</display-name> <servlet> <servlet-name>JustServletName</servlet-name> <servlet-class>com.company.hello.servlets.HelloWorldServlet</servlet-class> <load-on-startup>1</load-on-startup> </servlet> <servlet-mapping> <servlet-name>JustServletName</servlet-name> <url-pattern>/say/*</url-pattern> </servlet-mapping> </web-app> Вот простой дескриптора, в котором мы объявили всего один сервлет и связали его с URL /say/*. Имя сервлета нужно для того, чтобы связать две секции – объявление и mapping, это имя может быть произвольным. Один и тот же сервлет может иметь несколько mapping'ов. Дескриптор в war-файле может быть только один. По мере необходимости его нужно расширять новыми объявлениями, но как станет ясно в дальнейшем, он не будет меняться часто. Осталось всё это собрать. Скрипт сборки (build.xml) Будем использовать Ant. Делать будем следующее. Необходимо получить следующую сборку (содержимое WAR-файла): META-INF MANIFEST.MF // Ant сам это сгенерит WEB-INF +-lib // Библиотек у нас пока нет, но они кладутся в эту директорию +-classes +-com +-company +-hello +-servlets HelloSorldServlet.class web.xml Следующий скрипт делает всё что нужно: <project name="HelloProject" basedir="." default="build-web"> <property name="eelib.dir" value="ee-lib"/> <property name="lib.dir" value="lib"/> <property name="src.dir" value="src"/> <property name="build.dir" value="bin"/> <property name="dist.dir" value="dist"/> <property name="tmp.dir" value="tmp"/> <property name="res.dir" value="web-res"/> <property name="pname" value="hello"/> <path id="compile.classpath"> <fileset dir="${lib.dir}"> <include name="**/*.jar"/> </fileset> <fileset dir="${eelib.dir}"> <include name="**/*.jar"/> </fileset> </path> <target name="clean"> <delete dir="${dist.dir}"/> <delete dir="${build.dir}"/> </target> <target name="prepare"> <mkdir dir="${build.dir}"/> <mkdir dir="${dist.dir}"/> </target> <target name="compile" depends="clean,prepare"> <javac srcdir="${src.dir}" destdir="${build.dir}" debug="true"> <classpath refid="compile.classpath"/> </javac> </target> <target name="build-web"> <mkdir dir="${tmp.dir}/WEB-INF/classes"/> <copy todir="${tmp.dir}"> <fileset dir="${res.dir}"/> </copy> <copy todir="${tmp.dir}/WEB-INF/lib"> <fileset dir="${lib.dir}"/> </copy> <copy todir="${tmp.dir}/WEB-INF/classes"> <fileset dir="${build.dir}"/> </copy> <copy todir="${tmp.dir}/"> <fileset dir="${res.dir}"/> </copy> <jar destfile="${dist.dir}/${pname}.war" basedir="${tmp.dir}"/> <delete dir="${tmp.dir}"/> </target> </project> Развёртываем (деплоим) Запускаем JBoss. Для этого переходим в директорию, где он установлен, и далее в bin. Запускаем run.bat. После того, как в логе появится сообщение 2010-03-13 12:34:00,759 INFO [org.jboss.system.server.Server] JBoss (MX MicroKernel) [4.2.3.GA (build: SVNTag=JBoss_4_2_3_GA date=200807181439)] Started in 1m:18s:116ms файл hello.war из директории %JBOSS%/server/default/deploy. HelloProject/dist копируем в После того, как в нужной директории окажется файлик, сервер его автоматически подхватит (autodeploy) и выдаст такое сообщение в лог: 18:12:11,904 INFO [TomcatDeployer] deploy, ctxPath=/hello, warUrl=.../tmp/deploy/tmp8234995566681197264helloexp.war/ Проверяем, что всё работает Заходим сюда http://localhost:8080/hello/say и наслаждаемся чудесным HTML-ным Hello, World-ом. Удаление файла тоже будет обработано и приложение раздеплоится.