Логин:   Пароль:






Новости
Рассылки
Форум
Поиск


Java
- Апплеты
- Вопрос-ответ
- Классы
- Примеры
- Руководства
- Статьи
- IDE
- Словарь терминов
- Скачать

Мобильная Java
- Игры
- Примеры
- Статьи
- WAP, WML и пр.

JavaScript
- Вопрос-ответ
- Примеры
- Статьи

Веб-мастеринг
- HTML
- CSS
- SSI

Разминка для ума
Проекты
Книги
Ссылки
Программы
Юмор :)




Rambler's Top100
Rambler's Top100

Java: СтатьиJSP: Java Server Pages

JSP: Java Server Pages

Что такое JSP?

Технология Java Server Pages (tm) (JSP) позволяет разработчикам и дизайнерам web-приложений быстро разрабатывать и легко сопровождать web-страницы с динамическим наполнением информацией. Но описание практически каждой технологии подобного назначения (ASP, PHP, Net.Data) сопровождают подобные слова -- быстро и легко ...

При внешней схожести JSP отличают некоторые моменты, делающие данную технологию чем-то большим, чем ещё одно средство для создания динмически генерируемого содержания web-страниц.

Сначала простое перечисление:

  • действительно высокая межплатформенная переносимость; использование универсального языка высокого уровня Java в качестве скриптового;
  • JSP -- это не какое-то отдельно стоящее средство для решения достаточно узкого круга задач, пусть и достаточно мощное, а ещё одно в ряде целой плеяды технологий, объединяемых Java;
  • реальная возможность разделить задачи написания бизнес-логики web-приложения и пользовательского интерфейса, что позволяет разрабатывать и сопровождать различные части проекта независимо;
Технология JSP является прямым расширением ещё одной Java-технологии -- Servlets (tm) а также тесно связана с технологией Java Beans (tm) и использует XML-подобные теги (tags) и скриптлеты (scriptlets), написанные на языке программирования Java для введения логики создания динамического наполнения web-страницы, при этом HTML или XML-теги передаются клиентской стороне напрямую.

Количество тегов достаточно невелико, что упрощает начальное освоение данной технологии; впрочем, для простых вещей та же Net.Data или PHP тоже весьма просты. Как водится, рассмотрим примитивный случай класса Hello World!

<%@ page contentType="text/html; charset=ibm866" %>
<%@ page import ="java.net.*" %>
<%@ page import ="java.util.Date" %>
<HTML>
<HEAD>
<TITLE>Who Am I?</TITLE>
</HEAD>
<BODY>
<%
InetAddress localHost = InetAddress.getLocalHost();
Date localTime = new Date();
%>
<H1>Who Am I?</H1>
I am called <%= localHost.getHostName() %> (<%= localHost.getHostAddress() %>).<br>
This page last executed at <%= localTime.toString() %>.
</BODY>
</HTML>

Даже у человека, не знающего Java, понимание вышеприведенного кода, скорее всего, не вызовет проблем. Остановимся на некоторых моментах: код, находящийся внутри тегов <% %>, собственно и есть код скриптлета; всё находящееся между <%-- --%> -- комментарий; тег <%= позволяет вывести значение переменной в нужном месте страницы; <%@ page %> позволяет импортировать классы и также настраивать некоторые особенности в поведении страницы.

Если мощь таких конкурирующих (наверное, это всё-таки так ;-) инструментов, как PHP и Net.Data, обусловлены в первую очередь огромным набором предопределённых функций, то за JSP стоит весь конгломерат классов и технологий Java.

Но на таком простом примере вовсе не очевидно, почему нужно выбрать JSP и всё с ними связанное, в первую очередь servlets и beans. Тем не менее попытаемся рассмотреть некоторые приятные стороны JSP.

Session Management

Значения, которые сохраняются и извлекаются из объекта сессии, не могут быть примитивными типами данных (int, double) и должны быть представлены в виде своих классов-аналогов (Integer, Double).
HttpSession session=request.getSession();//get session object or create one
session.getId() //get the session ID number
Integer item = (Integer) session.getValue("item") // retrieve Integer object
session.putValue("ItemValue", itemName);//ItemValue must not be primitive

Application Management

Иногда необходимо обеспечить сервером некоторых значений переменных на уровне сайта, каждый клиент использует и манипулирует копиями этих данных. JSP использует объект ServletContext, который обеспечивает механизм, схожий с сессией (i.e. no primitive types).
getServletContext().setAttribute("Item", ItemValue);//to set an application variable
Integer i=(Integer)getServletContext().getAttribute("ItemName");//get item

JSP-Specific Language

Директивы JSP "говорят" серверу делать что-либо, когда они преобразуются из JSP в сервлет; директивы предваряются символом @. Некоторые важные директивы JSP перечислены ниже, для более полного знакомства естественно придется почитать что-то ещё.
    include - включение статического или динамического файла (Server Side Include)
<%@ include file="hello.jsp" %>
    import - итоговый сервлет будт импортировать данный пакет

<%@ import = "java.util.*" %>

    extends - сервлет будет расширять (наследовать) указанный класс (это superclass)
<%@ extends = "java.util.Dictionary" %>

    implements - сервлет будет имплементировать интерфейс
<%@ implements = "java.util.Enumeration" %>

    content_type - устанавливает тип ответа, генерируемого сервлетом
<%@ content_type = "text/plain" %>

или

 <%@ content_type = "text/html" %>

Известно, что задачи в этом сложном мире бывают не только простые или даже очень простые. Если поддаться соблазну делать всё средствами скриптлетов (динамических вставок Java кода среди статического HTML), и рассматривать внешние классы как мощную библиотеку функций, очень легко сделать из динамической страницы объёмного монстра, тяжёлого в отладке и с огромными трудностями при дальнейших модификациях и расширении.

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

Есть два варианта include:

  • Статическое включение, при этом обрабатываются JSP-элементы во включаемом файле, если они есть и попадают в результирующий сгенерированый Java-код, фактически серлет:
    <%@ include file="includeheader.jsp"%>
    
    или так
    <%@ include file="includeheader.html"%>
    
    то есть включаемый файл вовсе не обязан быть JSP страницей.

  • Динамическое включение, при этом контент включаемого файла обрабатывается независимо, фактически ему передается управление на момент выполнения:
    <jsp:include page="topic.html" flush=true />
    
Что интересно, динамически включенный контент может кэшироваться независимо, что в некоторых случаях даёт существенный выигрыш на сложных многокомпонентных страницах. Но возможность include тем не менее, наверное, самое примитивное из многогранных возможностей JSP.

Практически каждый, начав делать web-приложение, сталкивается с необходимостью предоставить пользователю удобное средство для ввода информации, и тут, как правило, возникают большие проблемы, чем просто с предоставлением информации в виде сгенерёных HTML-страниц. Необходимо обеспечить достаточную интеллектуальность ввода, кроме того, при ошибках ввода не терять ранее введённое и передавать требуемую общую информацию от страницы к странице. В Net.Data, например, я не нашёл способа делать это иначе, чем использовать hidden-поля в формах ввода, хранение же информации с временем жизни "session" вырастает в сложную задачу; как можно выкрутиться с решением этой задачи в PHP, я не в курсе. Что же касается JSP/servlets -- есть стандартное средство JavaBeans (в данном контексте не будем останавливаться на таком более мощном развитии данной концепции, как EJB) -- это полноценные классы Java с некоторыми дополнительными правилами программирования.

Это очень мощное средство, но оно требует некоторой ломки стереотипов. JavaBeans -- это компоненты Java, которые могут выполнять хорошо определённые задачи и включать в себя объекты данных. JavaBeans следуют структурной объектной модели: Bean имеет public constructor, который не имеет аргументов, и его свойства устанавливаются с помощью управляющего сервлета с использованием интроспекции (introspection/reflection).

Включение некоторого бина в "страницу" JSP делается например так:


<jsp:useBean id="formHandler" class="VagonCardFormBean" scope="request" >
   <jsp:setProperty name="formHandler" property="*" />
</jsp:useBean>

...

<tr><td>Дополнение</td>
    <td><input type=text name=description value="<%= 
formHandler.getDescription()%>"></td>
    <td><%=formHandler.getErrorMsg("description")%></td></tr>
<tr><td>Владелец</td>
    <td><%= formHandler.getOwnerName()%> | <%= formHandler.getOwnerName()%></td>
    <td><%=formHandler.getErrorMsg("owner")%></td></tr>
<tr><td>===></td><td><input type=submit value=Ввод></td><td></td></tr>
или вот ещё один
   <jsp:useBean id="Cindy" class="Coffee" />
   <jsp:setProperty name="Cindy" property="Flavor" Value="RaspberryMocha"/>
    I like <%= Cindy.getFlavor() %> coffee.

    //The Coffee Bean:
Public class Coffee
{  private String m_flavor;

   public Coffee()
   { m_flavor = "Regular"; }

   public void setFlavor(String flavor)
   {  m_flavor = flavor; }

   public String getFlavor()
   {  return m_flavor;  }
}

Некоторые пояснения к этой выжимке: scope="request" означает, что время жизни бина -- request, property="*" означает, что данный бин принимает с помощью своих методов все параметры, переданные в запросе на данную страницу. Эти методаы имеют простое правило именования: если параметр формы -- lastName, то метод, принимающий данные, будет иметь имя setLastName, а отдающий данные -- getLastName.

К сожалению, достаточно трудно продемонстрировать всю мощь использования бинов в простом приложении. Впрочем, данная статья и не ставит своей целью дать всю глубину, задача заинтересовать.

Генеральная линия, которая прослеживается во множестве публикаций последнего времени -- разделение работы дизайнера и работы программиста, обеспечивающего написание собственно работы с базой данных и бизнес-логику web-приложения. Большая часть этого может быть вынесена именно на уровень бинов. К сожалению, трудоемкость написания, по крайней мере на начальном этапе, у связки JSP-servlets-beans выглядит большей, чем у Net.Data и PHP (впрочем, с последним я знаком на уровне чуть большем "Hello World!"). Но даже использование бинов не освобождает совсем от минимального использования Java на странице. Чтобы дойти до логического конца и оставить дизайнеру только правильную расстановку тегов на странице, в JSP ввели возможность написания библиотек тегов (custom JSP tag libraries).

Использование библиотек тегов позволяет, во первых, ещё повысить повторное использование кода, во вторых, снизить сложность написания прриложения, и, в третьих, ещё больше помочь в разделении труда. К сожалению, последнее в нашей действительности ещё не приобрело должного веса при выборе средства разработки. В заключение приведу небольшой пример использования пользовательских тегов, например, запрос к базе с выводом результата в виде таблицы может выглядеть вот так:

<%@ taglib uri="xsql.tld" prefix="xsql" %>

...

<xsql:connect id="tConn" url="jdbc:db2:sample" name="user" password="password" />
<table border=1>
 <tr><th>что-то</td><th>нечто</td><th>описание</td></tr>
 <xsql:select req="select Ref, TName, Comment from vcRefList;" conn="tConn">
   <tr><td>"$1$"</td><td>"$2$"</td><td>"$3$"</td></tr>
 </xsql:select>
</table>
<xsql:disconnect conn="tConn" />
но это вовсе не значит, что он должен так выглядеть ;-)

На самом деле тема слишком обширна, чтобы быть охваченой без белых пятен в столь коротком изложении.

Serge Popov

Warning: mysql_connect() [function.mysql-connect]: Can't connect to local MySQL server through socket '/tmp/mysql.sock' (2) in /pub/home/javaport/javaportal/books/show2b.php on line 11

Warning: mysql_db_query() [function.mysql-db-query]: Can't connect to local MySQL server through socket '/tmp/mysql.sock' (2) in /pub/home/javaport/javaportal/books/show2b.php on line 19

Warning: mysql_db_query() [function.mysql-db-query]: A link to the server could not be established in /pub/home/javaport/javaportal/books/show2b.php on line 19

Warning: mysql_fetch_array(): supplied argument is not a valid MySQL result resource in /pub/home/javaport/javaportal/books/show2b.php on line 30
Узнай о чем ты на самом деле сейчас думаешь тут.


[an error occurred while processing this directive]



Warning: mysql_connect() [function.mysql-connect]: Can't connect to local MySQL server through socket '/tmp/mysql.sock' (2) in /pub/home/javaport/javaportal/news/worldnews.php on line 91

Warning: mysql_db_query() [function.mysql-db-query]: Can't connect to local MySQL server through socket '/tmp/mysql.sock' (2) in /pub/home/javaport/javaportal/news/worldnews.php on line 93

Warning: mysql_db_query() [function.mysql-db-query]: A link to the server could not be established in /pub/home/javaport/javaportal/news/worldnews.php on line 93

Warning: mysql_fetch_array(): supplied argument is not a valid MySQL result resource in /pub/home/javaport/javaportal/news/worldnews.php on line 95