АвтоАвтоматизацияАрхитектураАстрономияАудитБиологияБухгалтерияВоенное делоГенетикаГеографияГеологияГосударствоДомДругоеЖурналистика и СМИИзобретательствоИностранные языкиИнформатикаИскусствоИсторияКомпьютерыКулинарияКультураЛексикологияЛитератураЛогикаМаркетингМатематикаМашиностроениеМедицинаМенеджментМеталлы и СваркаМеханикаМузыкаНаселениеОбразованиеОхрана безопасности жизниОхрана ТрудаПедагогикаПолитикаПравоПриборостроениеПрограммированиеПроизводствоПромышленностьПсихологияРадиоРегилияСвязьСоциологияСпортСтандартизацияСтроительствоТехнологииТорговляТуризмФизикаФизиологияФилософияФинансыХимияХозяйствоЦеннообразованиеЧерчениеЭкологияЭконометрикаЭкономикаЭлектроникаЮриспунденкция

Remote Address: 127.0.0.1

Читайте также:
  1. AI makes robots smarter
  2. Economy of Russia
  3. Effective Cross Cultural Communication Skills
  4. Electrical measurement. Electrical measuring instruments and their classification.
  5. EMPLOYMENT
  6. English-Russian Glossary
  7. Ghetto Tourism and Graffiti Travel
  8. I. Перевести текст. 4 страница
  9. Internet Information Services
  10. IP – адресация в сети
  11. Language in use
  12. Lawyers at work

Header INFO:

accept = image/gif, image/x-xbitmap, image/jpeg, image/pjpeg, application/x-shockwave-flash, application/vnd.ms-excel, application/vnd.ms-powerpoint, application/msword, */*
referer = http://localhost:8080/FirstProject/index.jsp
accept-language = ru
content-type = application/x-www-form-urlencoded
accept-encoding = gzip, deflate
user-agent = Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.1; SV1)
host = localhost:8080
content-length = 0
connection = Keep-Alive
cache-control = no-cache
cookie = JSESSIONID=91014EB2B2208BCA18AE898424B71CEF

Сервлет RequestServlet следует попробовать вызывать с различных компьютеров локальной сети или вызвать несколько раз сервлет из нескольких браузеров, запущенных на одном компьютере.

Когда клиент переходит по адресу URL, который обрабатывается сервлетом, контейнер сервлета перехватывает запрос и вызывает метод doGet() или doPost(). Эти методы вызываются после конфигурации объектов, наследующих интерфейсы HttpServletRequest, HttpServletResponse. Задача методов doGet() и doPost() – взаимодействие с HTTP-запросом клиента и создание HTTP-ответа, основанного на данных запроса. Метод getWriter() объекта-ответа возвращает поток PrintWriter, который используется для записи символьных данных ответа.

Интерфейсы ServletResponse и HttpServletResponse

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

Можно получить ссылки на потоки вывода одним из двух методов:

ServletOutputStream getOutputStream() – извлечение ссылки на поток ServletOutputStream для передачи бинарной информации;

PrintWriter getWriter() – извлечение ссылки на поток типа PrintWriter для передачи символьной информации;

Если метод getOutputStream() уже был вызван для этого ответа, то генерируется IllegalStateException. Обратное также верно.

В интерфейсе HttpServletResponse, наследующем интерфейс ServletResponse, есть еще несколько полезных методов:

void setContentType(String type) – установка MIME-типа генерируемых документов;

void addCookie(Cookie c) – добавление cookie к объекту ответа для последующей пересылки на клиентский компьютер;

void sendError(int sc, String msg) – сообщение о возникших ошибках, где sc – код ошибки, msg – текстовое сообщение;

void setDateHeader(String name, long date) – добавление даты в заголовок ответа;

void setHeader(String name, String value) – добавление параметров в заголовок ответа. Если параметр с таким именем уже существует, то он будет заменен.

Обработка запроса

Распределенное приложение может быть эффективным только в случае, если оно способно принимать информацию от физически удаленных клиентов. В следующем примере сервлет извлекает данные пользовательской формы, переданные вместе с запросом по методу GET.

Приведенная на рисунке 18.1 форма является результатом отображения JSP-страницы index.jsp, находящейся в папке /webapps/FirstProject3.

В форме имеется текстовое поле с именем name и значением по умолчанию «Название проекта». Значение поля можно изменить непосредственно на странице.

Рис. 18.1. JSP-форма

В форме заданы две группы по два элемента ввода типа radio, каждая из которых имеет свое имя. При наличии на странице нескольких полей, имеющих одно имя, можно выбрать только один из них. Им задаются соответствующие значения, и при выборе одной из кнопок значение, заданное соответствующей кнопке, заносится в значение своего элемента. По умолчанию для радиогрупп принято задавать одно из значений при помощи свойства checked.

В итоге пользователь может изменить значения текстового поля и радиогрупп. При нажатии кнопки типа происходит подтверждение формы и вызывается сервлет.

В форме задан метод POST, при помощи которого происходит передача данных формы в виде отдельных заголовков. Если не задавать этот метод, то по умолчанию будет использоваться метод GET, и данные формы будут передаваться через универсальный запрос (URL), в который к адресу будут добавлены значения соответствующих элементов.

<!-- пример # 3: стартовая страница: index.jsp-->

<%@ page language="java" contentType=

"text/html; charset=utf-8" pageEncoding="utf-8"%>

<html><body>

<FORM action="testform" method=POST>

<H3>Название проекта:

<INPUT type="text" name="Имя проекта" value="-задать!-">

Технологии:

<TABLE BORDER=5> <tr>

<td>JSPX</td><td><INPUT type="radio"

name="Технология"

value="JSP в формате XML"></td>

<td>JSTL</td><td><INPUT type="radio"

name="Технология"

value="Библиотека тегов JSTL"></td>

</tr></TABLE>

Язык программирования:

<TABLE BORDER=5> <tr>

<td>Java 6<INPUT type="radio"

name="Язык"

value="Java SE 6"></td>

<td>Java 5<INPUT type="radio"

name="Язык"

value="Java 1.5.0" checked></td>

</tr></TABLE></H3>

<INPUT type="submit" value="Принять"> <BR>

</FORM>

</body></html>

При подтверждении из формы вызывается сервлет FormRequest. Сервлет получает и извлекает значения всех переменных формы и отображает их вместе
с именами переменных. Для обработки данных, полученных из полей формы, используется приведенный ниже сервлет.

/* пример # 4: обработка запроса клиента: FormRequest.java:

ParameterOutput.java */

package chapt18;

import javax.servlet.ServletException;

import javax.servlet.http.HttpServlet;

import javax.servlet.http.HttpServletRequest;

import javax.servlet.http.HttpServletResponse;

 

public class FormRequest extends HttpServlet {

protected void doPost(HttpServletRequest req,

HttpServletResponse resp)

throws ServletException {

performTask(req, resp);

}

private void performTask(HttpServletRequest req,

HttpServletResponse resp) {

RequestOutput.generate(resp, req);

}

}

В методе performTask() происходит обращение к другому классу-обработчику запроса пользователя с передачей ему объектов HttpServletRequest req и HttpServletResponse resp.

/* пример # 5: извлечение информации из запроса клиента: RequestOutput.java */

package chapt18;

import java.io.IOException;

import java.io.PrintWriter;

import java.util.Enumeration;

import javax.servlet.http.HttpServletRequest;

import javax.servlet.http.HttpServletResponse;

 

public class RequestOutput {

public static void generate(HttpServletResponse resp,

HttpServletRequest req) {

try {

String name, value;

resp.setContentType("text/html; charset=utf-8");

PrintWriter out = resp.getWriter();

 

out.print("<HTML><HEAD>");

out.print("<TITLE>Результат</TITLE>");

out.print("</HEAD><BODY>");

out.print("<TABLE BORDER=3>");

Enumeration names = req.getParameterNames();

while (names.hasMoreElements()) {

name = (String) names.nextElement();

value = req.getParameterValues(name)[0]; /*

name = new String(name.getBytes("ISO-8859-1"), "utf-8");

value = new String(value.getBytes("ISO-8859-1"), "utf-8");

*/

out.print("<TR>");

out.print("<TD>" + name + "</TD>");

out.print("<TD>" + value + "</TD>");

out.print("</TR>");

}

out.print("</TABLE></BODY></HTML>");

out.close();

} catch (IOException e) {

e.printStackTrace();

}

}

}

В классе в объекте resp задается тип содержимого text/html и кодировка UTF-8, если нужно отобразить кириллицу. После этого объект out устанавливается в выходной поток resp.getWriter(), в который будут помещаться данные. Из запроса HttpServletRequest req извлекается объект типа Enumeration с текстовыми значениями имен переменных формы. Далее, итерируя по элементам этого объекта, последовательно извлекаются все параметры. Для каждого имени переменной можно при необходимости (если не указана кодовая страница) произвести перекодировку: вначале извлекается объект итерации
в кодировке, в которой он передается, а именно ISO-8859-1, после создается новая строка с необходимой кодировкой, в данном случае UTF-8. Для каждой из переменных извлекаются из запроса соответствующие им значения при помощи метода getParameterValues(name). Тем же способом их кодировка может быть изменена и добавлена в выходной поток.

Класс сервлета относится к пакету chapt18, поэтому файл
FormRequest.class должен быть размещен в папке

/webapps/FirstProject3/WEB-INF/classes/chapt18

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

<servlet>

<servlet-name> MyForm </servlet-name>

<servlet-class> chapt18.FormRequest </servlet-class>

</servlet>

<servlet-mapping>

<servlet-name> MyForm </servlet-name>

<url-pattern> /testform </url-pattern>

</servlet-mapping>

Обращение к сервлету производится по его URL-имени testform. Результат выполнения:

Рис. 18.2. Результат выполнения запроса

Метод getParameterValues() возвращает значения любой переменной формы по имени этой переменной. Массив возвращается потому, что некоторые переменные формы могут иметь несколько значений, например группа флажков или радиокнопок. Другой метод доступа не предполагает предварительного знания их имен. Метод getParameterNames() возвращает объект Enumeration, в котором содержатся все имена переменных, извлеченных из формы.

Многопоточность

Контейнер сервлетов будет иметь несколько потоков выполнения, распределяемых согласно запросам клиентов. Вероятна ситуация, когда два клиента одновременно вызовут методы doGet() или doPost(). Метод service() должен быть написан с учетом вопросов многопоточности. Любой доступ к разделяемым ресурсам, которыми могут быть файлы, объекты, необходимо защитить ключевым словом synchronized. Ниже приведен пример посимвольного вывода строки сервлетом с паузой между выводом символов в 500 миллисекунд, что позволяет другим клиентам, вызвавшим сервлет, успеть вклиниться в процесс вывода при отсутствии синхронизации.

/* пример # 6: доступ к синхронизированным ресурсам:

ServletSynchronization.java */

package chapt18;

import java.io.*;

import javax.servlet.ServletException;

import javax.servlet.http.*;

public class ServletSynchronization extends HttpServlet {

// синхронизируемый объект

private StringBuffer locked = new StringBuffer();

 

protected void doGet(HttpServletRequest req,

HttpServletResponse res)

throws ServletException, IOException {

performTask(req, res);

}

private void performTask(HttpServletRequest req,

HttpServletResponse res)

throws ServletException, IOException {

try {

Writer out = res.getWriter();

out.write(

"<HTML><HEAD>"

+ "<TITLE>SynchronizationDemo</TITLE>"

+ "</HEAD><BODY>");

out.write(createString());

out.write("</BODY></HTML>");

out.flush();

out.close();

} catch (IOException e) {

throw new RuntimeException(

"Failed to handle request: " + e);

}

}

protected String createString() {

// оригинал строки

final String SYNCHRO = "SYNCHRONIZATION";

 

synchronized (locked) {

try {

for (int i = 0; i < SYNCHRO.length(); i++) {

locked.append(SYNCHRO.charAt(i));

Thread.sleep(500);

}

} catch (InterruptedException e) {

e.printStackTrace();

}

String result = locked.toString();

locked.delete(0, SYNCHRO.length() - 1);

return result;

}

}

}

Результаты работы сервлета при наличии и отсутствии синхронизации представлены на рисунках.

Рис. 18.3. Результат работы сервлета Synchronization
с блоком синхронизации

 

Рис. 18.4. Результат работы сервлета Synchronization
без синхронизации

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

Электронная почта

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

Следующий пример использует интерфейсы API JavaMail для работы с электронной почтой в сервлетах и JSP. API JavaMail содержит классы, с помощью которых моделируется система электронной почты. Класс javax.mail.Session представляет сеанс почтовой связи, класс javax.mail.Message – почтовое сообщение, класс javax.mail.internet.InternetAddress – адреса электронной почты.

Рис. 18.5. Формирование запроса на отправку письма

Для работы с данной частью платформы J2EE необходимо скачать zip-файлы, расположенные по адресу http://java.sun.com/products/javamail/, содержащие архивы mail.jar и activation.jar. И добавить эти файлы в каталог jar-файлов серверам приложений (common/lib для Tomcat). Также необходимо запустить почтовую программу James, являющуюся также одним из проектов apache.org.

Ниже приведена страница JSP, содержащая форму для заполнения основных полей: «Кому» – «to», «От кого» – «from», «Тема сообщения» – «subj»

<!-- пример # 7: страница создания электронного письма: index.jsp-->

<%@ page language="java" contentType=

"text/html; charset=UTF-8" pageEncoding="UTF-8"%>

<html><head><title>SendMail Application</title></head>

<b>Мой почтовый сервер</b>

< form method="post" action="sendmail" >

<table>

<tr><td><b>To(email):</b></td><td>

<input name="to" type="text" size=40> </td></tr>

<tr><td><b>From(email):</b></td><td>

<input name="from" type="text" size=40> </td></tr>

<tr><td><b>Subject:</b></td><td>

<input name="subj" type="text" size=40> </td></tr>

</table>

<hr>

<textarea name="body" type="text" rows=5 cols=45>

Добрый день!</textarea>

<br>

<input type="submit" value="Отправить!">

</form>

</body></html>

Параллельные процессы по отправке письма и предложению пользователю в это же самое время создать новое письмо организуются с применением потока
в следующем сервлете.

/* пример # 8: доступ к синхронизированным ресурсам:

SendMailServlet.java */

package chapt18;

import javax.mail.Message;

import javax.mail.MessagingException;

import javax.mail.Session;

import javax.mail.Transport;

import javax.mail.internet.AddressException;

import javax.mail.internet.InternetAddress;

import javax.mail.internet.MimeMessage;

import javax.activation.*;

import javax.servlet.ServletConfig;

import javax.servlet.ServletException;

import javax.servlet.http.HttpServletRequest;

import javax.servlet.http.HttpServletResponse;

import java.io.IOException;

import java.io.PrintWriter;

 

public class SendMailServlet

extends javax.servlet.http.HttpServlet

implements javax.servlet.Servlet {

//объект почтовой сессии

private Session mailSession = null;

 

public void init(ServletConfig config)

throws ServletException {

//mailSession = Session.getDefaultInstance(System.getProperties());

final String host = "mail.smtphost";

final String port = "mail.smtpport";

//запрос параметров почтового сервера из web.xml

String hostvalue = config.getInitParameter(host);

String portvalue = config.getInitParameter(port);

java.util.Properties props = new java.util.Properties();

//загрузка параметров почтового сервера в объект свойств

props.put(host, hostvalue);

props.put(port, portvalue);

//загрузка параметров почтового сервера в объект почтовой сессии

mailSession = Session.getDefaultInstance(props, null);

}

protected void doPost(HttpServletRequest request,

HttpServletResponse response)

throws ServletException, IOException {

//извлечение параметров письма из запроса

String from = request.getParameter("from");

String to = request.getParameter("to");

String subject = request.getParameter("subj");

String content = request.getParameter("body");

if ((from == null) || (to == null)

|| (subject == null) || (content == null)) {

/*при отсутствии одного из параметров предлагается повторить

ввод*/

response.sendRedirect("index.jsp");

return;

}

//запуск процесса отправки почты в отдельном потоке

(new MailSender(to, from, subject, content)).start();

//формирование страницы с предложение о создании нового письма

response.setContentType("text/html; charset=CP1251");

PrintWriter out = response.getWriter();

out.println("<html><head><title>");

out.println("SendMail Application</title></head>");

out.println(" Message to <b>" + to

+ "</b> sending in progress ");

out.println(" <a href = \"index.jsp\">New message </a>");

out.println("</body></html>");

}

private class MailSender extends Thread {

private String mailTo;

private String mailFrom;

private String mailSubject;

private String mailContent;

MailSender(String mailTo, String mailFrom,

String mailSubject, String mailContent) {

setDaemon(true);

this. mailTo = mailTo;

this. mailFrom = mailFrom;

this. mailSubject = mailSubject;

this. mailContent = mailContent;

}

public void run() {

try {

//создание объекта почтового сообщения

Message message = new MimeMessage(mailSession);

//загрузка параметров в объект почтового сообщения

message.setFrom(new InternetAddress(mailFrom));

message.setRecipient(Message.RecipientType.TO,

new InternetAddress(mailTo));

message.setSubject(mailSubject);

message.setContent(mailContent, "text/plain");

//отправка почтового сообщения

Transport.send(message);

} catch (AddressException e) {

e.printStackTrace();

System. err. print("Ошибка адреса");

} catch (MessagingException e) {

e.printStackTrace();

System. out. print("Ошибка сообщения");

}

}

}

}

В результате в браузер будет выведено:

Message to blinov@gmail.com sending in progress New message

где New message представляет собой активную ссылку, перенаправляющую при запуске на index.jsp для создания еще одного письма. Процесс же отправки письма будет функционировать независимо от дальнейшей работы приложения.

Файл web.xml для данного приложения имеет вид:

<?xml version="1.0" encoding="UTF-8"?>

<web-app id="WebApp_ID" version="2.4" xmlns="http://java.sun.com/xml/ns/j2ee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/j2ee http://java.sun.com/xml/ns/j2ee/web-app_2_4.xsd">

<display-name>FirstMail</display-name>

<servlet>

<display-name>

SendMailServlet</display-name>

<servlet-name>SendMailServlet</servlet-name>

<servlet-class>

SendMailServlet</servlet-class>

<init-param>

<param-name> mail.smtphost </param-name>

<param-value> mail.bsu.bsu </param-value>

</init-param>

<init-param>

<param-name> mail.smtpport </param-name>

<param-value> 25 </param-value>

</init-param>

</servlet>

<servlet-mapping>

<servlet-name>chapt18.SendMailServlet</servlet-name>

<url-pattern>/sendmail</url-pattern>

</servlet-mapping>

<welcome-file-list>

<welcome-file>index.jsp</welcome-file>

</welcome-file-list>

</web-app>

В качестве значения параметра mail.smtphost можно попробовать использовать адрес почтового сервера mail.attbi.com.

Задания к главе 18

Вариант А

Создать сервлет и взаимодействующие с ним пакеты Java-классов и JSP-страницы, выполняющие следующие действия:

1. Генерация таблиц по переданным параметрам: заголовок, количество строк и столбцов, цвет фона.

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

3. Поиск слова, введенного пользователем. Поиск и определение частоты встречаемости осуществляется в текстовом файле, расположенном на сервере.

4. Вычисление объемов тел (параллелепипед, куб, сфера, тетраэдр, тор, шар, эллипсоид и т.д.) с точностью и параметрами, указываемыми пользователем.

5. Поиск и (или) замена информации в коллекции по ключу (значению).

6. Выбор текстового файла из архива файлов по разделам (поэзия, проза, фантастика и т.д.) и его отображение.

7. Выбор изображения по тематике (природа, автомобили, дети и т.д.)
и его отображение.

8. Информация о среднесуточной температуре воздуха за месяц задана
в виде списка, хранящегося в файле. Определить:

а) среднемесячную температуру воздуха; б) количество дней, когда температура была выше среднемесячной; в) количество дней, когда температура опускалась ниже 0ºC; г) три самых теплых дня.

9. Игра с сервером в “21”.

10. Реализация адаптивного теста из цепочки в 3–4 вопроса.

11. Определение значения полинома в заданной точке. Степень полинома
и его коэффициенты вводятся пользователем.

12. Вывод фрагментов текстов шрифтами различного размера. Размер шрифта и количество строк задаются на стороне клиента.

13. Информация о точках на плоскости хранится в файле. Выбрать все точки, наиболее приближенные к заданной прямой. Параметры прямой
и максимальное расстояние от точки до прямой вводятся на стороне клиента.

14. Осуществить сортировку введенного пользователем массива целых чисел. Числа вводятся через запятую.

15. Реализовать игру с сервером в крестики-нолики.

16. Осуществить форматирование выбранного пользователем текстового файла, так чтобы все абзацы имели отступ ровно 3 пробела, а длина каждой строки была ровно 80 символов и не имела начальными и конечными символами пробел.

Вариант B

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

Тестовые задания к главе 18


1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | 53 | 54 | 55 | 56 | 57 | 58 | 59 | 60 | 61 | 62 | 63 | 64 | 65 | 66 | 67 | 68 | 69 | 70 | 71 | 72 | 73 | 74 | 75 | 76 | 77 | 78 | 79 | 80 | 81 | 82 | 83 | 84 | 85 | 86 | 87 | 88 | 89 | 90 | 91 | 92 | 93 | 94 | 95 | 96 | 97 | 98 | 99 | 100 | 101 | 102 | 103 | 104 | 105 | 106 | 107 | 108 | 109 | 110 | 111 | 112 | 113 | 114 | 115 | 116 | 117 | 118 | 119 | 120 | 121 | 122 | 123 | 124 | 125 | 126 | 127 | 128 | 129 | 130 | 131 | 132 | 133 | 134 | 135 | 136 | 137 | 138 | 139 | 140 | 141 | 142 | 143 |

Поиск по сайту:



Все материалы представленные на сайте исключительно с целью ознакомления читателями и не преследуют коммерческих целей или нарушение авторских прав. Студалл.Орг (0.057 сек.)