<% ASP на блюдечке %>. Часть 2
ActiveX-компоненты и ASP
<!--If you build it, they will come. If you make it dynamic
(using ASP, ActiveX and this article) they'll come back more often.-->
Что же такое Active X? (Небольшое «лирическое» отступление)
А зачем, собственно, применять Active X-технологию в ASP?
Создание и подготовка базы данных
Формируем главную страницу (index.asp)
Форма загрузки (UploadForm.asp)
(Обработка формы загрузки с помощью ActiveX-компонента Upload2DBS.asp)
Загрузка файлов с помощью ASP и VBScript
А теперь давайте попробуем сами разработать ActiveX-компонент…
…с помощью Microsoft Visual Basic 6.0
… с помощью Microsoft Visual C++ 6.0
Еще несколько слов в защиту C++
Введение
В первой статье серии «<% ASP на блюдечке %>» («<% ASP на блюдечке %>. Часть 1. Построение интерфейса к базе данных», КомпьютерПресс 9 за 2000 год) мы ознакомились с ASP, а также с принципами построения с его помощью простейшего интерфейса к базе данных (газетный сайт со встроенными возможностями его пополнения новыми статьями, снабжаемыми фотографиями непосредственно с самого сайта и без программирования). Теперь я предложу читателям обогатить этот интерфейс возможностями загрузки (upload) HTML-статьи и иллюстрации к ней непосредственно с сайта (то есть с HTML-формы), ведения автоматической статистики посещений, организации показа баннеров, а также методами использования и азами разработки Активных Серверных Компонентов (Active Server Components) для ASP. Статья будет весьма полезна начинающим Web-программистам, профессионалам же достаточно беглого взгляда, чтобы понять принципы и вникнуть в детали работы активных серверных страниц — ASP.
Итак…
| |
|
Что же такое Active X? (Небольшое «лирическое» отступление)
Как вы уже догадываетесь, в настоящей статье речь пойдет о технологиях ActiveX и COM. Те, кому эти технологии и принципы их работы известны, могут пропустить настоящий параграф. Однако рекомендую все-таки освежить в памяти некоторые детали. Именно благодаря этим технологиям процесс разработки активных серверных страниц может стать гораздо проще и быстрее.Итак, что же такое COM (Component Object Model) и ActiveX? Чтобы ответить на этот вопрос, зададимся сначала другим: каким образом одна часть программного обеспечения должна получать доступ к сервисам, предоставляемым другой частью? Сегодня ответ на этот вопрос зависит от того, что представляют собой эти части. Например, приложения, скомпонованные с библиотекой, могут пользоваться ее сервисами, вызывая функции из этой библиотеки. Приложение может также использовать сервисы другого — являющегося совершенно отдельным процессом. В данном случае два локальных процесса взаимодействуют посредством некоего механизма связи, который обычно требует определения протокола между этими приложениями (набор сообщений, позволяющий одному приложению выдавать запросы, а другому соответствующим образом отвечать на них). Еще пример: приложение, использующее сервисы операционной системы. Здесь приложение обычно выполняет системные вызовы, обрабатываемые операционной системой. Наконец, приложению могут понадобиться сервисы, предоставляемые программным обеспечением, выполняемым на другой машине, доступ к которой осуществляется по сети. Получить доступ к таким сервисам можно множеством способов, таких как обмен сообщениями с удаленным приложением или вызовы удаленных процедур.
В принципе, проблема одна: первая часть программного обеспечения должна получить доступ к сервисам, предоставляемым второй частью. Но в каждом отдельном случае механизм доступа разный: вызовы локальных функций, передача сообщения средствами связи между процессами, системные вызовы (которые с точки зрения программиста выглядят практически так же, как и вызовы функций) или одна из разновидностей сетевых коммуникаций.
Каждый такой объект поддерживает один или несколько интерфейсов, состоящих из методов. Метод — это функция или процедура, которая выполняет некоторое действие и может быть вызвана программным обеспечением, использующим данный объект (клиентом объекта). Методы, составляющие каждый из интерфейсов, обычно определенным образом взаимосвязаны. Клиенты могут получить доступ к сервисам объекта COM только через вызовы методов интерфейсов объекта — у них нет непосредственного доступа к данным объекта.
| |
|
А зачем, собственно, применять Active X-технологию в ASP?
Применение встраиваемых в ASP ActiveX-компонентов значительно облегчает задачу создания сайтов. Посудите сами: ведь создание громоздких функций, выполняющих сложные вычисления, да и простых подпрограмм гораздо удобнее с помощью известных всем языков программирования, таких как Visual Basic, Delphi или C++, а сгенерированный код (.dll или .ocx) будет работать во много раз быстрее, ведь скомпилированный код модуля выполняется почти мгновенно, в то время как препроцессор ASP формирует HTML-страницу для каждого клиента гораздо дольше. Реализация этих функций средствами самого ASP во многих случаях будет нетривиальна, а в некоторых — попросту невозможна. Кроме того, многие полезные компоненты доступны со стороны так называемых третьих фирм (third-party components), которые зачастую распространяются бесплатно (или почти бесплатно).
Итак, я надеюсь, что эта статья поможет вам научиться применять «чужие» компоненты (third-party components) и разрабатывать свои.
| |
|
С чего начать?
Давайте для начала разберемся, что же от нас требуется. Во-первых, необходимо подготовить шаблон базы данных с соответствующими полями для заголовка, аннотации, рубрики, даты публикации и текста самой статьи, а также HTML-файла и иллюстрации, загружаемой как в виде текста с HTML-формы, так и в виде HTML-файла. В последнем случае полностью сохраняется формат статьи, что достаточно удобно. Кроме того, статья на сайте может быть снабжена иллюстрацией, которую тоже необходимо загрузить с формы на сервер и отображать по усмотрению пользователя на главной странице сайта. Попросту говоря, пользователь может определить статьи, которые будут отображаться на главной страничке сайта (так называемые горячие новости), а также будет ли отображаться иллюстрация (если таковая имеется) к самой последней из них. Для этого в соответствующей HTML-форме необходимо предусмотреть два регистра.Далее необходимо организовать ввод всех полей формы, включая локальные пути (на компьютере клиента) к загружаемым файлам (в нашем случае с HTML-версией статьи и с иллюстрацией), загрузить их на сервер в определенный каталог и присвоить соответствующим полям базы данных значения имен этих файлов (уже на сервере).
| |
|
Что для этого понадобится?
Для реализации вышеизложенной задачи необходим персональный компьютер с Microsoft Windows NT или Windows 2000 (можно и Workstation или Server), установленный IIS (Internet Information Server), какой-нибудь HTML-редактор (советую использовать Macromedia Dreamweaver), Microsoft Access (версии 95, 97 или 2000) и самый обычный текстовый редактор.
| |
|
Создание и подготовка базы данных
Для начала нашего первого эксперимента создадим базу данных статей, а для этого:
- запустим приложение Microsoft Access;
- любым из известных способов создадим новую базу данных (назовем ее «Articles»);
- в созданной базе данных создадим таблицу с именем, например, «Articles»;
- пользуясь инструментом «Конструктор», определим поля нашей таблицы и типы принимаемых ими значений:
- заполним таблицу несколькими статьями в соответствии с созданными полями;
- сохраним базу данных в файле «ArticlesDB.mdb»
Далее необходимо прописать нашу базу данных в соответствующем разделе источников данных систем. Для этого:
- запустим программу-конфигуратор источников данных (Data Sources ODBC) — Start->Settings->Control Panel->Administrative Tools->Data Sources ODBC;
- перейдем во вкладку «System DSN» и создадим новый источник данных, нажав на «Add…»;
- в появившемся списке драйверов выберем драйвер баз данных Microsoft Access — «Microsoft Access Driver (*.mdb)» и нажмем на «Finish»;
- в строке «Data Source Name» зададим имя нашей базы данных, например «Articles» (это то имя, по которому мы в дальнейшем будем обращаться к ней);
- нажмем на «Select…», выберем подготовленный нами файл «ArticlesDB.mdb» и нажмем «OK».
Появляется строка в списке источников данных в вашей системе:
| |
|
Применение ActiveX в ASP
Мировая компьютерная сеть «кишит» и платными, и бесплатными ActiveX-компонентами. Последний параграф настоящей статьи — попытка перечислить наиболее популярные. Для загрузки файла с HTML-формы советую использовать компонент AspUpload 2.0 Copyright (c) 1998-2000 Persist Software, Inc. (http://www.persits.com). Компонент платный, но временную одномесячную версию вы сможете найти на нашем CD-ROM.
| |
|
Формируем главную страницу (index.asp)
…
<!- Определяем таблицу ->
<table BORDER=0 CELLSPACING=0 CELLPADDING=0 WIDTH="710">
<tr>
<td WIDTH="232"><img SRC="Images\Banner.jpg" height=60 width=232></td>
<td WIDTH="10"></td>
<td WIDTH="468"></td>
</tr>
<tr>
<td BGCOLOR="#000000"><b><font color="#FFFFFF"> Today is:
<!- Отобразим дату ->
<%
D = Date()
D = FormatDateTime(D,2)
Response.Write D
%>
</font></b></td>
<td> </td>
<td></td>
</tr>
<!- Линки на основные страницы ->
<tr>
<td BGCOLOR="#FFCC99" valign = top>
<a href="http://localhost/List.asp" class="antiLine">
<b> Show Articles List</b></a><br>
<a href="http://localhost/Search/SearchForm.asp" class="antiLine">
<b>Search for an article</b></a><br>
<a href="http://localhost/Upload/UploadForm.asp" class="antiLine">
<b>Upload an article</b></a><br>
<a href="http://localhost/Signin.asp" class="antiLine">
<b>Signing In</b></a><br>
</td>
<td></td>
<td>
<%
‘ Подключимся к таблице Articles базы данных Articles и откроем ее
Set db = Server.CreateObject("ADODB.Connection")
db.Open "Articles"
‘ Сформируем SQL запрос и выполним его
sSQL = "SELECT * FROM Articles Where IsTopNew = '1' Order by ID DESC"
Set rs = db.Execute(sSQL)
Display = 0
‘ В цикле будем считывать значения полей и добавлять их в таблицу
Do While NOT Rs.EOF
MainImage = rs.Fields("IFile1").value ‘Имя файла с иллюстрацией к текущей статье
ShouldDisplay = rs.Fields("IsDImage").value
‘Переменная, определяющая, должна ли иллюстрация отображаться
If NOT rs.EOF and Display = 0 and MainImage <> "No" and ShouldDisplay = "1" Then
Display = 1 ‘ Если да, то сгенерировать соответствующий тэг с именем иллюстрации
Response.Write "<img SRC=" & "Articles\" & MainImage & " height=300 width=468>"
End If
Rs.MoveNext
Loop
%>
</td>
</tr>
<%
Set rs = db.Execute(sSQL)
Cnt = 0
Do While NOT Rs.EOF
%>
<tr>
<td BGCOLOR="#FFCC99"> </td>
<td></td>
<td>
<%
If rs.Fields("Article").value <> "No Text" Then ‘Если поле текста статьи не равно "No Text"
Link = "<a href= http://localhost/ArtTempl.asp?id=" & rs.Fields("ID").value & ">" & rs.Fields("Title").value & "</a>"
Else ‘В противном случае сгенерировать линк на HTML-файл со статьей
Link = "<a href= http://localhost/Articles/" & rs.Fields("TextFile").value & ">" & rs.Fields("Title").value & "</a>"
End If
Response.Write Link & "<br>"
‘ Добавляем автора статьи
Response.Write "<i>By " & rs.Fields("Author").value & "</i><br>"
‘ Добавляем аннотацию к статье
ANN = rs.Fields("Annotation").value
If ANN <> "NA" Then
Response.Write ANN
End If
%>
<hr NOSHADE WIDTH="100%">
</td>
</tr>
<%
Rs.MoveNext
Cnt = Cnt + 1
Loop
db.Close
Set db = Nothing
%>
</table>
…
Следует обратить особое внимание на формирование переменной «Link». В первом случае, когда значение поля «Article» не равно «No Text», ссылка на статью формируется из файла шаблона ArtTempl.asp, которому идентификатор текущей статьи передается в качестве параметра
Link ="<a href= http://localhost/ArtTempl.asp?id="&rs.Fields("ID").value&">"&rs.Fields("Title").value &"</a>"
(дальнейшая обработка в теле файла шаблона подробно обсуждалась в первой части настоящей статьи).
В противном случае ссылка на статью формируется из имени файла (которое содержится в переменной TextFile) с ее HTML-версией, который уже подгружен на сервер и располагается в каталоге «Articles».
Link ="<a href= http://localhost/Articles/" &rs.Fields("TextFile").value &">"& rs.Fields("Title").value &"</a>"
| |
|
Загружаем файл с HTML-формы
Форма загрузки (UploadForm.asp)
Для начала необходимо создать соответствующую форму. Предполагается, что читатель знаком с азами построения форм (для этих целей советую воспользоваться Macromedia Dreamweaverом), тем не менее я обращу внимание на пару тэгов формы загрузки файлов (полная версия формы загрузки прилагается к данной статье).
Хочется обратить особое внимание на обработку «радиокнопки», определяющей тип статьи («горячая» — «не горячая») и флажок показа иллюстрации на главной странице. Если читатель знаком с первой статьей, то он, вероятно, вспомнит, что в целях обучения вся обработка формы (проверка корректности ввода полей и первоначальная обработка введенных значений) велась на ASP. Приведенный ниже пример иллюстрирует то, как это на самом деле следует делать с помощью какого-либо языка описания сценариев (в нашем случае JavaScript).
В нашем случае мы будем определять состояние флажка показа иллюстрации с помощью небольшого скрипта на JavaScript и «спрятанного» (hidden) поля. Последнее будет принимать значение, соответствующее состоянию флажка.
< script >
function preprocess ()
{
message = 2;
if (mainform.DI.checked) message = 1;
else message = 2;
mainform.details.value = message;
}
</script>
Как видно, значение поля «details» будет равно 1, если флажок поля «DI» был установлен, и 2 — в противном случае. Вызов самого скрипта удобнее всего выполнять по событию «onsubmit», которое обрабатывается по нажатию на кнопку «Submit», и вплоть до передачи управления скрипту-реакции. Таким образом, на этапе ввода можно осуществлять инициализацию внутренних полей и переменных формы, причем непосредственно на стороне клиента (как известно, языки описания скриптов JavaScript и VBScript именно для этого и предназначены). В нашем случае фрагмент формы будет выглядеть следующим образом:
… <form name="mainform" method="post" enctype="multipart/form-data" action="http://localhost/Upload/Upload2DBS.asp" onsubmit="preprocess();"> … <input type="radio" name="IsTopNewSelector" value="0" checked> <b> Ordinary type Article <input type="radio" name="IsTopNewSelector" value="1"> Top New type Article</b> … <b>Display image on Home page <input type="checkbox" name="DI" value="0"> <input type="hidden" name="details"> <i>(only for Top News type articles) </i></b> … </form> …
Соответственно радиокнопка «IsTopNewSelector» будет возвращать значение «0» для обычной и значение «1» для «горячей» статьи.
| |
|
Обработка формы загрузки с помощью ActiveX-компонента Upload2DBS.asp
Работать с ActiveX-компонентами в ASP достаточно просто. Например, загрузка файлов при помощи компонента «ASPUpload» производится всего двумя строчками кода:
<%
Set Upload = Server.CreateObject("Persits.Upload.1") ‘Создаем переменную — указатель на интерфейс Upload
Count = Upload.Save ("c:\InetPub\wwwroot\Articles") ‘ Вызываем функцию Save этого интерфейса
‘ И присваиваем переменной Count число подгруженных файлов
%>
Фактически после отработки этих двух строк все файлы, которые были указаны в полях формы, загружаются на сервер — в данном случае в каталог "c:\InetPub\wwwroot\Articles".
Далее необходимо произвести обработку остальных полей формы и добавить запись в базу данных:
…
<%
I = 0
FileI = "No"
Set FI = Upload.Files("IFile1") ‘ Определяем указатель на погруженный файл
If Not FI Is Nothing Then ‘ И если он не пуст
FileI = FI.Path ‘ То читаем полный путь к подгруженному файлу
strPosition = Instr(25,FileI,"\") ‘ Вырезаем из полного пути собственно имя файла
intStringLen=strPosition-1
strLeft = Left(FileI,intStringLen)
strRight = Right(FileI,(Len(FileI)-Len(strLeft)-1))
FileI = strRight ‘ И присваиваем его переменной FileI
End If
…
Аналогичные действия должны быть выполнены и с файлом HTML (если таковой был указан)
…
Set TF = Upload.Files("TextFile")
If Not TF Is Nothing Then
FileT = TF.Path
strPosition = Instr(25,FileT,"\")
intStringLen=strPosition-1
strLeft = Left(FileT,intStringLen)
strRight = Right(FileT,(Len(FileT)-Len(strLeft)-1))
FileT = strRight ‘ И присваиваем его переменной FileТ
End If
ErrA = 0 ‘ Заводим четыре флажка для обработки ошибок ввода полей
ErrT = 0
ErrP = 0
ErrC = 0
‘ Получаем значение флажка показа иллюстрации
DI = Upload.Form("DETAILS")
If DI = 1 Then
IsDisplayImage = "1"
End If
If DI = 2 Then
IsDisplayImage = "0"
End If
‘ Получаем значение поля автора статьи
AUT = Upload.Form("Author")
If AUT = "" Then ErrA = 1 End If
AUT = FormatStr(AUT)
‘ Получаем значение поля заголовка статьи
TIT = Upload.Form("Title")
If TIT = "" Then ErrT = 1 End If
TIT = FormatStr(TIT)
‘ Получаем значение поля текста самой статьи
ART = Upload.Form("Article")
If ART = "" Then
ART = "No Text" ‘ Если оно пусто, присваиваем переменной константу "No Text"
If File1 = "No" Then
ErrC = 1
End If
End If
‘ Форматируем текст самой статьи для его последующего показа в формате HTML ART = FormatStr(ART)
‘ Получаем значение селектора рубрик SBJ = Upload.Form("Subject")
IsTopNew = Upload.Form("IsTopNewSelector")
ANN = Upload.Form("Annotation")
ANN = FormatStr(ANN)
If ANN = "" Then
ANN = "NA"
End If
‘ Получаем значение поля пароля доступа к базе данных Password = Upload.Form("Password")
If Password = DBP Then
If ErrA = 0 and ErrT = 0 Then
‘ Открываем базу данных и записываем в нее значения
Set db = Server.CreateObject("ADODB.Connection")
db.Open "DSN=Articles;UID=sa;PWD=;"
sSQL = "insert into
Articles(Author,Title,Article,Subject,TextFile,IFile1,Published,IsTopNew,Annotation,IsDImage)values('" & AUT &
"', '" & TIT & "','" & ART & "','" & SBJ & "','" & FileT & "','" & FileI & "','" & TIM &"','" & IsTopNew &"','" &
ANN & "','" & IsDisplayImage &"')"
Set rs = db.Execute(sSQL)
db.Close
Set db = Nothing
End If
Else
ErrP = 1
End If
%>
…
| |
|








