4. Пользователь продолжает работу с Web-приложением.
Основная задача заключается в том, чтобы сократить количество запросов к Web-серверу и не увеличивать размер Web-страниц. Ниже перечислены действия, которые выполняет компьютер при поступлении запроса.
1. От пользователя поступает запрос с некоторыми данными.
2. Имеют ли данные корректный формат? Если да, то поместить их в базу данных; в противном случае обработать возникшие исключительные ситуации.
3. Можно ли установить соединение с базой данных? Если да, то продолжить работу; в противном случае обработать возникшие исключительные ситуации.
4. Может ли база данных получить данные? Если да, то продолжить работу; в противном случае обработать возникшие исключительные ситуации.
5. Подключен ли клиент или уже нет? Если да, то послать отклик; в противном случае закрыть подключение к базе данных.
Очевидно, что Web-сервер должен выполнить множество операций, помимо обработки кода в Web-страницах. Более того, в предыдущих перечнях операций не учитывается возможность манипулирования создаваемыми объектами.
Попробуем теперь изменить код в листингах 11.1 и 11.2 для применения хранимой процедуры, предназначенной для возвращения данных Web-странице. Для этого нужно создать саму хранимую процедуру, которая, по сути, создает основу для двухуровневого приложения.
ВНИМАНИЕ!При работе с любым приложением ASP.NET для сбора данных из формы нужно использовать метод Server.HTMLEncode(Request.Form("objectName")), который позволяет предотвратить межузловые атаки на основе сценариев. Этот метод кодирует информацию в виде строкового литерала, понятного SQL Server, что позволяет исключить риск применения злоумышленных операций, например вставки команды в виде подстроки "; TRUNСАТЕ TABLE MASTER" в текстовое поле txtFileName Web-страницы и выполнения ее со стороны SQLServer.
Некоторые разработчики опасаются использовать хранимые процедуры в Web-приложениях. Эти опасения вызваны сложностями использования объектов Command и SQLCommand в технологиях ADO и ADO.NET вместе с хранимыми процедурами. Как отмечается в главе 4, "Модель ADO.NET: провайдеры данных", указание параметров в коде необходимо для "предварительной квалификации" данных за счет установки их типа. При этом SQL Server и платформа .NET избавлены от излишних затрат времени на определение типа передаваемых данных (целое число, строка и т.д.). В данном примере рассматривается хранимая процедура без параметров, код которой показан в листинге 11.4.
НА ЗАМЕТКУС помощью типов, описанных в разделе о включении учетной записи ASPNET в список учетных записей SQL Server, необходимо конфигурировать роль public с указанием разрешения EXEC на выполнение процедуры. В листинге 11.4 показан код процедуры, а в листинге 11.5 — способ ее применения.
ЛИСТИНГ 11.4. Код процедуры sp_GetCustomersOrdersCREATE PROCEDURE sp_GetCustomersOrders
SELECT tblCustomer.LastName, tblCustomer.FirstName, tblOrder.OrderDate
FROM tblOrder
INNER JOIN tblCustomer ON tblCustomer.ID = tblOrder.CustomerID
ORDER BY tblCustomer.LastName
GO
Обратите внимание, что в запросе используются только действительно нужные а не все поля таблицы tblCustomer, как показано в листинге 11.3. Вообще говоря, никогда не следует запрашивать поля таблицы, которые не будут использоваться. Это особенно важно при расширении масштаба приложения.
Рассмотрим теперь измененный код подпрограммы ShowCustomers, который показан в листинге 11.5. Обратите внимание, что в него включена еще одна строка для обработки даты, возвращенной хранимой процедурой.
Листинг 11.5. Обращение к хранимой процедуре из подпрограммы ShowCustomersPrivate Sub ShowCustomers()
' Это простой пример использования функции,
' которая извлекает данные из таблицы tblCustomer
' Инициализация объекта подключения строкой
' подключения.
Dim conn As New SqlConnection(connString)
' Затем инициализация объекта-команды строкой выполняемой команды SQL.
Dim с As New SqlCommand("exec sp_GetCustomersOrders", conn)
conn.Open()
Dim dReader As SqlDataReader = _
cmd.ExecuteReader(CommandBehavior.CloseConnection)
While dReader.Read
Response.Write(dReader.GetString(0))
Response.Write(" " & dReader.GetString(1))
Response.Write(" " & dReader.GetDateTime(2))
Response.Write("<BR>")
End While
dReader.Close()
conn.Close ()
End Sub
(Учтите, что для работы этого приложения в базу данных Novelty должна быть включена хранимая процедура sp_GetCustomersOrders, как описывается в главе 3, "Знакомство с SQL Server 2000". — Прим. ред.)
С помощью хранимых процедур, как правило, удается значительно повысить производительность работы Web-приложений с базами данных. Дело в том, что хранимые процедуры компилируются на сервере баз данных и выполняются гораздо быстрее по сравнению с динамически создаваемыми запросами. В листинге 11.1 команда SELECT должна интерпретироваться перед каждой операцией извлечения данных из базы данных SQL Server. Поэтому компилированные версии Web-страницы и хранимой процедуры выполняются гораздо быстрее. В аспекте повышения производительности эти особенности технологии ASP.NET и платформы .NET Framework являются их несомненным преимуществом.