Лабораторная работа №8 Обеспечение безопасности ASP.NET 2.0 1. Цель работы Целью работы является теоретическое ознакомление со средствами обеспечения безопасности ASP.NET 2.0. Освоение практических навыков в создании форм аутентификации, конфигурирования сайта для использования аутентификации Forms, а также для поддержки членства и ролей. 2. Состав рабочего места 2.1. Оборудование: IBM-совместимый персональный компьютер (ПК). 2.2. Программное обеспечение: операционная система Windows, интегрированная оболочка среда разработки Visual Studio. Рисунок ниже показывает образец приложения, которое будет создано в результате выполнения лабораторной работы. 3. Краткие теоретические сведения Аутентификация форм Методы аутентификации Windows и Passport редко применяются в реальных Webприложениях. Аутентификация Windows основана на использовании учетных записей Windows и списков контроля доступа NTFS, поэтому для ее применения необходимо, чтобы пользователи подключались к приложению с компьютеров, на которых установлена Windows. Для приложений интранет и некоторых интернет-сценариев этот метод удобен и эффективен. Однако он не подходит для типичного Web-приложения, пользователи которого не имеют учетных записей Windows из его домена. Неприменим в таких приложениях и метод Passport, хотя по другой причине. Сертификаты не бесплатны, кроме того, требуются основательные меры защиты сервера, которые дорого обходятся и нужны далеко не каждому сайту. Поэтому метод Passport применяется главным образом в системах электронной коммерции в группах сайтов, имеющих общих пользователей. Каков же оптимальный механизм аутентификации пользователей Web-приложений? Опыт показывает, что лучше всего поместить поверх каждой страницы, не предназначенной для общего доступа, некоторый более или менее стандартный код и при попытке анонимного подключения к сайту перенаправлять с его помощью пользователя на страницу входа. Эта страница предложит пользователю ввести свое имя и пароль, выполнит аутентификацию и, в случае успеха, перенаправит пользователя на ту страницу, которую он запросил. Такой метод называется аутентификацией форм (то есть аутентификацией с помощью формы). Код его реализации отнюдь не сложен, но, конечно, писать его снова и снова — не вдохновляющая перспектива. К счастью, этого и не требуется, поскольку в ASP.NET существует встроенная инфраструктура для реализации такой схемы входа. Аутентификация Forms является прекрасным (и, пожалуй, единственным) решением, позволяющим получить имя и пароль пользователя и обработать их внутри приложения, например, проверить по базе данных учетных записей пользователей. Главное отличие этого метода заключается в том, что все происходит под строгим контролем приложения. Для того чтобы настроить приложение для применения аутентификации Forms, нужно внести изменения в его корневой файл web.config: <system.web> <authentication mode="Forms"> <forms loginUrl="login.aspx"/> </authentication> <authorization> <deny users="?" /> </authorization> </system.web> В разделе <authentication> задается URL созданной вами формы ввода. ASP.NET выводит эту форму только для тех пользователей, которым явно запрещен доступ в разделе <authorization>. Символ ? представляет любого анонимного, неаутентифицированного пользователя. Заметьте, что под анонимными пользователями здесь понимаются не анонимные пользователи IIS, а просто те, которые не были аутентифицированы с использованием вашей формы ввода. Все заданные в элементах <deny> пользователи перенаправляются на страницу ввода, где им предлагается ввести свои учетные данные. Поток выполнения при аутентификации форм Аутентификацией форм управляет HTTP-модуль, реализующий класс FormsAuthenticationModule. Его поведение определяется установками, которые задаются в файле web.config. Когда браузер пытается обратиться к защищенному ресурсу, модуль FormsAuthenticationModule включается в игру и пытается найти аутентификационный билет клиента. В ASP.NET 1.x этим билетом является просто cookie с определенным конфигурируемым именем. В ASP.NET 2.0 билетом может служить значение, включенное в состав URL (аутентификация форм без применения cookie). Если допустимый cookie не найден, модуль перенаправляет запрос странице входа, поместив в строку запроса информацию об исходной запрошенной странице. После этого выводится созданная разработчиком страница входа, которая содержит, как минимум, текстовые поля для ввода имени и пароля пользователя и кнопку для их отправки серверу. Обработчик щелчка этой кнопки проверяет введенные учетные данные, применяя пользовательский алгоритм, зависящий от конкретного приложения. Если пользователь аутентифицирован, код страницы входа перенаправляет браузер по исходному URL, который содержится в строке запроса указанной страницы: http://YourApp/login.aspx?ReturnUrl=original.aspx Но теперь к запросу ресурса присоединяется аутентификационный билет. Когда браузер отправляет серверу повторный запрос этого ресурса, модуль HTTP извлекает билет и разрешает выполнение запроса. Давайте рассмотрим процесс аутентификации форм на конкретном примере. Перед его выполнением откройте файл web.config демонстрационного приложения и удалите символы комментария, которые блокируют фрагмент разметки, включающей аутентификацию форм — тем самым вы запретите анонимный доступ к страницам приложения. Далее в качестве пользователя введите в адресной строке браузера URL страницы LoginProcess\welcome.aspx, входящей в состав демонстрационного приложения, и щелкните кнопку перехода. Поскольку страницы этого приложения не разрешается открывать анонимно, модуль FormsAuthenticationModule перенаправит вас на страницу входа. Ввод учетных данных пользователя Структура страницы входа обычно всегда одна и та же: два текстовых поля, кнопка и, возможно, некоторый поясняющий текст. Однако ничто не мешает вам сделать эту страницу сколь угодно сложной. Пользователь вводит свои учетные данные (для которых обычно учитывается регистр) и щелкает кнопку входа. При возврате формы на сервере выполняется следующий код: void LogonUser(object sender, EventArgse) { string user = userName.Text; string pswd = password.Text; // Пользовательская аутентификация bool bAuthenticated = AuthenticateUser(user, pswd); if (bAuthenticated) FormsAuthentication.RedirectFromLoginPage(user, false); else errorMsg.Text = "Sorry, yours seems not to be a valid account."; } Обработчик события извлекает строки, введенные в поля имени пользователя и пароля, и вызывает локальную функцию с именем AuthenticateUser. Эта функция проверяет учетные данные пользователя и возвращает значение булева типа, указывающее успешно ли аутентифицирован пользователь. Если успешно, вызывается статический метод RedirectFromLoginPage класса FormsAuthentication, информирующий браузер о том, что он может направить повторный запрос на получение страницы. Таким образом, метод RedirectFromLoginPage перенаправляет аутентифицированного пользователя по исходному запрошенному им URL. Метод имеет две перегруженные версии: public static void RedirectFromLoginPage(string, bool); public static void RedirectFromLoginPage(string, bool, string); Первым аргументом обеих версий является имя пользователя, которое должно быть записано в аутентификационный билет, а вторым — значение булева типа, которое определяет срок действия cookie, созданного для аутентификационного билета. Если этот аргумент равен false, задается обычный срок действия, определенный в атрибуте timeout (по умолчанию 30 минут). Если же этот аргумент равен true, cookie назначается срок действия 50 лет. В третьем, не обязательном, аргументе метода RedirectFromLoginPage задается путь к cookie. Аутентификация пользователя Алгоритм аутентификации, то есть код упоминавшегося выше метода AuthenticateUser, является произвольным. Например, вы можете проверять введенные пользователем имя и пароль по базе данных или использовать какой-нибудь другой источник данных. Приведенная ниже функция сравнивает имя и пароль пользователя со значениями столбцов firstname и lastname таблицы Employees базы данных Northwind SQL Server 2000: private bool AuthenticateUser(string username, string pswd) { // Здесь выполняется аутентификация string connString=".."; string cmdText = "SELECT COUNT(*) FROM employees" + "WHERE firstname=@user AND lastname=@pswd"; int found = 0; using(SqlConnection conn = new SqlConnection(connString)) { SqlCommand cmd = new .SqlCommand(cmdText, conn); cmd.Parameters.Add("@user",SqlDbType.VarChar, 10).Value = username; cmd.Pa ramete rs.Add("@pswd",SqlDbType.VarChar, 20).Value = pswd; conn.Open(); found = (int)cmd.ExecuteScalar(); conn.Close(); } return (found > 0); } Запрос возвращает количество строк таблицы, удовлетворяющих заданному критерию. Обратите внимание на использование в SQL-команде типизированных параметров фиксированного размера — это линия защиты против возможного внедрения злоумышленником вредоносного SQL-кода. Также заметьте, что приведенный код не гарантирует использования сильных паролей, поскольку в нем выполняется самое обычное сравнение с использованием оператора а не сравнение с учетом регистра, которое может быть, например, таким: SELECT СASТ(*) FROM employees WHERE -.. CAST(RTRIM(firstname) AS VarBinary)=CAST(RTRIM(@user) AS VarBinary) -AND CAST(RTRIM(lastname) AS VarBinary)=CAST(RTRIM(@pswd) AS VarBinary) В этой команде оператор CAST служит для получения двоичного представления значения, а оператор RTRIM удаляет завершающие пробелы. Вот исходный код страница демонстрационного приложения, открываемая после успешной аутентификации пользователя: <%@ Page Language="C#" CodeFile="Welcome.aspx.cs" Inherits="Welcome" %> <html><body> Класс FormsAuthentication Класс FormsAuthentication имеет ряд статических членов, предназначенных для манипулирования аутентификационными билетами и выполнения базовых аутентификационных операций. В частности, для перенаправления аутентифицированного пользователя обратно на запрошенную им страницу используется метод RedirectFrom-LoginPage, а для удаления аутентификационного билета пользователя — метод SignOut. Остальные методы и свойства служат для манипулирования билетом и связанным с ним cookie. Свойства класса FormsAuthentication Многие из свойств класса FormsAuthentication связаны с именованием и использованием cookie или возвращают значения конфигурационных атрибутов из раздела <forms>. В ASP.NET 2.0 в состав класса FormsAuthentication было добавлено несколько новых свойств. Все перечисленные в таблице ниже свойства являются статическими. Свойство CookieDomain CookieMode CookiesSupported Описание Возвращает домен, заданный для аутентификационного билета. Это свойство эквивалентно атрибуту domain раздела <forms> конфигурационного файла. Указывает, реализована ли аутентификация форм с поддержкой cookie. Возвращает значение true, если текущий запрос поддерживает cookie. Возвращает URL страницы, к которой нужно вернуться после успешной аутентификации запроса. Соответствует атрибуту defaultUrl раздела <forms>. EnableCrossAppRedire Указывает, разрешено ли перенаправлять пользователя к другому Web-приложению. cts Возвращает заданное в конфигурационном FormsCookieName файле имя cookie, используемое в текущем приложении; по умолчанию имеет значение ASPXAUTH. Возвращает заданный в конфигурационном FormsCookiePath файле путь к файлу cookie, используемый в текущем приложении; по умолчанию имеет значение "/", представляющее корневую папку. Возвращает заданный в конфигурационном LoginUrl файле или используемый по умолчанию URL страницы входа. Соответствует атрибуту loginUrl раздела <forms>. Указывает, обязательно ли передавать cookie RequireSSL через HTTPS-coединение. Указывает, включен ли режим скользящего ShdingExpiration устаревания. DefaultUrl Табл.1. Свойства класса FormsAuthentication. Конфигурирование аутентификации форм Хотя суть аутентификации Forms исключительно проста, для настройки аутентификационного механизма предлагается множество параметров. Эти параметры задаются в подразделе ><forms> раздела <authentication>. Большая их часть связана с хранением аутентификационных билетов в cookie-файлах. Раздел <forms> Аутентификация Forms производится согласно установкам, заданным в подразделе <forms> раздела <authentication> конфигурационного файла. Синтаксис этого подраздела таков: <forms name="cookie" loginUrl="url" protection="All|None|Encryption|Validation" timeout="30" requireSSL="true|false" slidingExpiration="true|false" paths="/" enableCrossAppsRedirects="true|false" cookieless="UseCookies|UseLIri|AutoDetect|UseDeviceProf ile" defaultUrl="url" domain="string"> </forms> Атрибуты раздела <forms> Атрибут cooheless Описание Указывает, должны ли для хранения аутентификационных билетов использоваться cookie и в каких именно случаях. Допустимыми значениями являются UseCookies, UseUri, AutoDetect и UseDeviceProfile. defaultUrl Определяет используемый по умолчанию URL, по которому следует перенаправить пользователя после аутентификации; по умолчанию имеет значение default.aspx. domain Определяет имя домена, который будет задаваться для аутентификационных cookie (я расскажу об этом подробнее). В ASP.NET 1л данный атрибут не поддерживается enableCrossAppRedire Указывает, может ли пользователь быть cts аутентифицирован внешним приложением, когда cookie не используются. Если поддержка cookie включена, данная установка игнорируется и аутентификация внешним приложением всегда возможна. В ASP.NET 1л данный атрибут не поддерживается loginUrl Определяет URL страницы входа, на которую пользователь будет перенаправлен при отсутствии действительного аутентификационного билета name Определяет имя аутентификационного Cookie path Определяет путь, связываемый с аутентификационным cookie; по умолчанию имеет значение "/", представляющее путь к корневой папке приложения (такой cookie действителен для всех страниц приложения). Заметьте, что некоторые браузеры чувствительны к регистру и не будут отправлять обратно cookie, если при указании пути вы используете символы не того регистра protection Определяет, как приложение должно защищать аутентификационные Cookie. Допустимые значения: All (по умолчанию), Validation, None requireSSL Указывает, обязательно ли передавать Cookie только через SSL-соединение; по умолчанию имеет значение false. Когда этот атрибуту установлен в true, ASP.NET задает свойство Secure аутентификационного cookie так, чтобы браузер (поддерживающий такую функцию) не возвращал Cookie, если подключение не является защищенным. slidingExpiration timeout Указывает, включен ли режим скользящего устаревания. По умолчанию данный атрибут имеет значение false, то есть cookie устаревает спустя заданное время после создания. Интервал определяется атрибутом timeout. Задает время в минутах, спустя которое cookie станет устарев шим; по умолчанию имеет значение 30 Табл.2.Атрибуты раздела <forms>. Атрибут defaultUrl позволяет задать имя страницы, открываемой по умолчанию после успешной аутентификации запроса. В ASP.NET 1.x этот URL, default.aspx, жестко закодирован и его нельзя изменить, но в ASP.NET 2.0 данный параметр стал конфигурируемым. Но для чего он нужен, если URL указанной страницы включается в строку запроса (в параметре ReturnUrl)? Если пользователь перенаправляется к странице входа аутентификационным модулем, переменная ReturnUrl всегда правильно установлена и значение атрибута попросту игнорируется. Однако если ваша страница содержит ссылку на страницу входа или переход к странице входа осуществляется программно (скажем, после выхода пользователя из приложения), за установку значения переменной ReturnUrl отвечаете вы сами. Если она оказывается неустановленной, используется атрибут defaultUrl. API управления членством и ролями Используемые совместно с классом FormsAuthentication новые классы Membership и Roles составляют полный арсенал необходимых разработчикам ASP.NET средств защиты. Класс Membership предоставляет методы для управления учетными записями пользователей, в частности для добавления учетных записей новых пользователей, а также для удаления и редактирования существующих записей. Класс Roles служит связующим звеном между пользователями и их ролями. Что означает выражение «управление членством пользователей»? Да просто то, что класс Membership знает, как создать новую учетную запись пользователя и как изменить его пароль. Как создается учетная запись пользователя? Обычно она добавляется в определенное хранилище данных. Кто в таком случае решает, какое хранилище использовать и как выполнять запись информации нового пользователя? Это решает разработчик приложения, для чего в его распоряжение предоставлен новый API членства. API управления членством и ролями не привязывает вас к фиксированному хранилищу данных и фиксированной их схеме. Как раз наоборот: он дает вам в этом отношении полную свободу. Данный API основан на модели провайдеров и делегирует выполнение всех основных своих функций выбранным вами провайдерам. Управление членством Центральным компонентом API членства ASP.NET является класс Membership, скрывающий от вас детали извлечения и сравнения информации о пользователях. В его состав входит несколько методов, в том числе позволяющих получить уникальный идентификатор каждого подключенного пользователя. Он может вызываться и другими сервисами ASP.NET, в частности сервисами персонализации, а также использоваться для включения и отключения тех или иных функций с учетом роли пользователя. Среди членов класса Membership имеются также методы для создания, обновления и удаления учетных записей пользователей, но нет методов для управления ролями и программного определения возможностей и ограничений пользователя. Такие методы включены в состав класса Roles. По умолчанию класс Membership работает с провайдером, который сохраняет информацию о пользователях в базе данных SQL Express в стандартном формате. Если вы пожелаете работать с пользовательским хранилищем данных, вам достаточно будет создать собственный провайдер и подключить его к приложению. Свойство Provider возвращает ссылку на используемый провайдер членства (он задается в конфигурационном файле). В состав ASP.NET 2.0 входит пара предопределенных провайдеров, работающих с MDF-файлами SQL Server Express и с Active Directory. Но существует множество других провайдеров от Microsoft и сторонних производителей. Список доступных провайдеров можно получить с помощью свойства Providers. Все свойства класса Membership являются статическими и доступными только для чтения, а реализация их очень проста. Каждому из них соответствует член текущего провайдера: public static int PasswordAttemptWindow { get { Membership.Initialize(); return Membership.Provider.PasswordAttemptWindow; } } Метод Initialize обеспечивает правильную инициализацию внутренней структуры класса Membership и наличие ссылки на провайдер. Класс Membership обладает богатой функциональностью, например, он может определить, сколько пользователей в данный момент подключено к приложению (свойство UserIsOnlineTimeWindow). Пользователь считается подключенным, если он взаимодействует с приложением и паузы в его работе не превышают интервала, заданного в свойстве OnlineTimeWindow интервала (по умолчанию 15 минут). Управление учетными записями пользователей и паролями Класс Membership предоставляет удобные методы для работы с учетными записями пользователей. В частности, для программного создания новой учетной записи достаточно вызвать метод CreateUser. Membership.CreateUser(userName, pswd); Удаление учетной записи пользователя выполняется с помощью метода DeleteUser. Membership.DeleteUser(userName); Для получения информации об определенном пользователе используется метод GetUser. Он принимает имя пользователя и возвращает объект MembershipUser. MembershipUser user = Membership.GetUser( "DinoE"); Получив объект MembershipUser, вы обладаете всей необходимой информацией о пользователе и можете программно изменять его пароль и прочие сведения. Приложение обычно выполняет несколько операций над паролями: изменяет их, отправляет пользователям, сбрасывает (обычно с использованием протокола запрос-ответ). Например, следующий код изменяет пароль пользователя: MembershipUser user = Membership.GetUser("DinoE"); user.ChangePassword(user.GetPassword(), newPswd); Методу ChangePassword передается старый пароль. В некоторых случаях можно предоставить пользователю возможность просто сбросить пароль (то есть удалить старый и автоматически сгенерировать новый), вместо того чтобы его изменять. Для этого используется метод ResetPassword: MembershipUser user = Membership.GetUser("DinoE"); string newPswd = user.ResetPassword(); Вызвавшая его страница отвечает за отправку пользователю нового пароля, скажем, по электронной почте. Методы GetPassword и ResetPassword имеют по одной перегруженной версии, принимающей строковый параметр, в котором задается ответ на вопрос, предусмотренный на случай потери пароля. Провайдер членства проверяет правильность этого ответа, и если пользователь идентифицирован, генерируется новый пароль, который сообщается пользователю. Провайдер членства Модель членства ASP.NET примечательна исключительно компактным кодом использующего ее приложения, а также тем, что она абстрактна и расширяема. Если, к примеру, у вас имеется созданное ранее хранилище данных с информацией о пользователях, ее легко можно интегрировать с API членства. Для этого достаточно написать пользовательский провайдер членства — класс, наследующий MembershipProvider, который, в свою очередь, наследует класс ProviderBase: public class MyAppMembershipProvider : MembershipProvider { // Реализует все абстрактные члены класса // и при необходимости определяет пользовательскую функциональность } Класс ProviderBase Все используемые в ASP.NET 2.0 провайдеры, а не только провайдеры членства, реализуют общий набор членов, определенный в классе ProviderBase. Этот класс имеет один метод, Initialize, и одно свойство, Name. Свойство возвращает официальное имя класса провайдера. Что касается метода, то он принимает имя провайдера и коллекцию пар имязначение, содержащую установки из конфигурационного раздела провайдера, а затем инициализирует внутреннее состояние класса указанными значениями. Управление ролями Роли в ASP.NET используются для упрощения процесса создания приложений, в которых требуется авторизировать пользователей на выполнение тех или иных действий. Сама по себе роль — это просто присвоенный пользователю логический атрибут: строка, представляющая логическую роль, которую играет пользователь в контексте приложения. Одному пользователю может быть назначено несколько ролей. Эта информация присоединяется к идентификационному объекту, и код приложения может проверить ее, прежде чем выполнять критичные операции. Например, в приложении могут быть определены две роли: Admin и Guest, из которых первая наделена более широкими полномочиями. В ASP.NET функция управления ролями заключается в поддержании связей между ними и пользователями. Встроенной подсистемы поддержки ролей в ASP.NET 1.x не существует, однако к учетной записи пользователя можно присоединить информацию о его ролях, что требует написания программного кода. Реализовать это несложно, но в ASP.NET 2.0 данная задача еще более упростилась. Для включения поддержки ролей необходимо добавить в файл web.config приложения следующую строку: <roleManager enabled="true" /> С помощью ролей устанавливаются правила доступа к страницам и папкам. Например, следующий блок <authorization> определяет, что только члены роли Admin имеют доступ к страницам, на которые распространяется действие файла web.config: <configuration> <system.web> <authorization> <allow roles="Admin" /> <deny users="*" /> </authorization> </system.web> <configuration> API управления ролями Для программного определения ролей, а также для связывания с ними пользователей в ASP.NET применяется API управления ролями, представленный членами класса Roles. Когда управление ролями включено, ASP.NET создает экземпляр этого класса и добавляет его в контекст каждого запроса, то есть в объект HttpContext. Следующий код показывает, как программным способом создать роли Admin и Guest и заполнить их именами пользователей: Roles.CreateRole("Admin"); Roles.AddUsersToRole("DinoE", "Admin"); Roles.CreateRole("Guest"); string[] guests = new string[2]; guests[0] = "Joellsers"; guests[1] = "Godzilla"; Roles.AddUsersToRole(guests, "Guest") Во время выполнения страницы информация о запросившем ее пользователе и его ролях доступна через объект User контекста HTTP. Следующий код показывает, как установить, принадлежит ли пользователь к определенной роли, и включить соответствующие функции: if (User.IsInRoleC'Admin")) { // Включаем функции, специфические для данной роли } Члены класса Roles Класс Roles обладает удобным интерфейсом, позволяющим работать как с отдельными пользователями и ролями, так и с их группами. Методы этого класса описаны в таблице ниже. Метод AddUsersToRole AddUsersToRoles AddUserToRole AddUserToRoles CreateRole DeleteCookie DeleteRole FindUsersInRole GetAURoles GetRolesForUser Описание Включает группу пользователей в состав роли Включает группу пользователей в группу ролей Включает пользователя в состав роли Включает пользователя в состав группы ролей Создает новую роль Удаляет cookie, которые менеджер ролей использовал для кэширования всех данных указанной роли Удаляет роль Извлекает имена пользователей, принадлежащих к заданной роли Возвращает список всех доступных ролей Возвращает строковый массив ролей, к которым принадлежит заданный пользователь Возвращает строковый массив с именами пользователей, принадлежащих к заданной роли IsUserlnRole Определяет, принадлежит ли указанный пользователь заданной роли Remove UserFromRole Удаляет пользователя из заданной роли RemoveUserFromRoles Удаляет пользователя из группы заданных ролей RemoveUsersFromRole Удаляет пользователей из заданной роли RemoveUsersFromRoles Удаляет пользователей из группы заданных ролей RoleExists Возвращает значение true, если заданная роль существует Табл.3.Методы класса Roles. GetUsersInRole Свойства класса Roles перечислены в таблице ниже. Все они являются статическими и доступны только для чтения. Значения этих свойств соответствуют установкам из конфигурационного раздела <roleManager>. Свойство CookiePath CookieProtection Value Описание Определяет путь, ассоциированный с ролевым cookie Содержит установку шифрования ролевого cookie: All, Clear, Hashed или Encrypted Указывает, должны ли ролевые cookie передаваться через SSL-соединение Указывает, является срок действия ролевого cookie фиксированным или скользящим Возвращает срок действия ролевого cookie в минутах Создает ролевой cookie, сохраняющийся в течение сеанса Определяет домен ролевого cookie Указывает, включена ли функция управления ролями Определяет максимальное количество ролей, которое может быть сохранено для одного пользователя в cookie-файле Возвращает текущий провайдер ролей Возвращает полный список поддерживаемых провайдеров ролей Возвращает имя провайдера Возвращает значение true, если хранение данных ролей в cookie разрешено Определяет имя cookie, используемого для хранения информации о ролях CookieRequireSSL CookieSlidingExpiration CookieTimeout CreatePersistentCookie Domain Enabled MaxCackedResults Provider Providers ApplicationName CacheRolesInCookie CookieName Табл.4.Свойства класса Roles. Некоторым методам класса Roles необходима информация о ролях пользователя, поэтому ее обычно кэшируют в зашифрованных cookie. Получив очередной HTTP-запрос, ASP.NET проверяет, имеется ли в его составе ролевой cookie, и если имеется, дешифрует билет роли и присоединяет ее информацию к объекту User. По умолчанию ролевой cookie является сеансовым и становится недействительным, как только пользователь закрывает браузер. Заметьте, что cookie содержит сведения о ролях лишь того пользователя, от которого поступил запрос. Когда вы запрашиваете информацию о ролях других пользователей, она считывается провайдером ролей из источника данных. Провайдер ролей Для выполнения ввода-вывода данных о ролях пользователей менеджер ролей использует провайдерную модель. Провайдер ролей — это класс, наследующий класс RoleProvider. Его структура очень похожа на структуру класса провайдера членства. Методы класса RoleProvider перечислены ниже. Метод GetAURoles GetRolesForUser Описание Возвращает список доступных ролей Возвращает массив с именами всех ролей, к которым принадлежит текущий пользователь Возвращает массив с именами всех пользователей, которые принадлежат к заданной роли IsUserlnRole Указывает, принадлежит ли текущий пользователь к заданной роли RemoveUsersFromRole Удаляет из заданной роли группу заданных s пользователей RoleExists Указывает, существует ли заданная роль AddUsersToRoles Добавляет группу пользователей в группу ролей CreateRole Создает новую роль DeleteRole Удаляет заданную роль Возвращает имена принадлежащих к данной FindUsersInRole роли пользователей, соответствующие заданному шаблону Табл.5.Методы класса RoleProvider . GetUsersInRole Некоторые из этих методов подобны методам класса Roles и, как и в случае с членством, это не совпадение. В состав ASP.NET 2.0 входят два встроенных провайдера ролей — AspNetSqlRoleProvider (используется по умолчанию) и AspNetWindowsTokenRoleProvider. Первый сохраняет информацию о ролях в том же mdf-файле SQL Server 2005 Express, что и используемый по умолчанию провайдер членства, а второй предоставляет информацию о ролях, хранящуюся в Active Directory или том домене Windows, где аутентифицирован пользователь. Этот провайдер не позволяет добавлять и удалять роли. Пользовательские провайдеры ролей создаются как производные от класса RoleProvider и регистрируются в подразделе <providers> раздела <roleManager>. Заметьте, что этот процесс практически идентичен процессу создания пользовательских провайдеров членства. 4. Порядок выполнения работы Упражнение 1 Создание Login Page В этом упражнении вы создадите форму аутентификации, а также сможете добавить новых пользователей к порталу. Сценарий Проблема: Пользователи не должны иметь доступ к нескольким ыозможностям Web-сайта Adventure Works. Решение: 1) Создать форму аутентификации для активизации аутентификацйии форм. Использовать встроенные в ASP.NET 2.0 средства защиты при создании формы аутентификации. Откройте стартовую страничку 1. В среде Microsoft Visual Studio, в меню File, нажмите Open Web Site. 2. В последующем окне укажите путь E:\LabFiles\ Starter\language\AdWorksWebSite и нажмите Open. 2) Создайте фораму аутентификации. 1. В меню File нажмите New File. 2. Убедитесь, что в диалоговом окне установленных шаблонов Microsoft Visual Studio выбрана опция Web Form. А в окне Name, набрано Login.aspx. 3. В списке Language, выберите соответствующий язык (C#). 4. Проверьте наличие флажка в поле separate file. 5. Нажмите Add. 6. Измените название страницы на « Adventure Works – Login». Ваш код должен выглядеть следующим образом: <title>Adventure Works - Login</title> 3) Создайте элемент управления Login. 1. Из панели инструментов Toolbox добавьте на веб-форму элемент управления Panel с помощью тэга <div>. Если Toolbox не открыт, нажмите View, а затем выберите Toolbox. 2. В окне Properties, установите следующие параметры: Атрибут Значение (ID) Visible pnlLogin true 3. Из кода элемента управления Panel, удалите параметры Height и Width. Ваш код должен выглядеть следующим образом: <asp:Panel ID="pnlLogin" runat="server" Visible="true">\ 4. Из Toolbox, перетащите элемент управления Login в панель pnlLogin . В окне Properties, установите следующие параметры: Атрибут Значение (ID) DestinationPageUrl DisplayRememberMe FailureText AdvWorksLogin Default.aspx true Unable to log in. 5. В списке Object, нажмите AdvWorksLogin , а затем в списке Event, нажмите Authenticate. Ваш код должен выглядеть следующим образом: <asp:Login ID="AdvWorksLogin" runat="server" DestinationPageUrl="Default.aspx" DisplayRememberMe="true" FailureText="Unable to log in." OnAuthenticate="AdvWorksLogin_Authenticate"> </asp:Login> 6. Из панели инструментов ToolBox перетащите Button ниже элемента управления Login на панель pnlLogin. 7. В окне Properties установите следующие параметры: Атрибут Значение (ID) Text btnNewUser I am a new user... 8. В списке Object выберите btnNewUser, а затем в списке Event, выберите Click. Ваш код должен выглядеть следующим образом: <asp:Button ID="btnNewUser" runat="server" Text="I am a new user..." OnClick="btnNewUser_Click" /> 9. В обработчике событий кнопки btnNewUse, удалите слово Protected, установите значение false параметра Visible для элемента управления pnlLogin , и значение true параметра Visible для элемента управления pnlNewUser. Ваш код должен выглядеть следующим образом: void btnNewUser_Click(object sender, EventArgs e) { pnlLogin.Visible = false; pnlNewUser.Visible = true; } 10.В событии Authenticate элемента управления AdworksLogin удалите ключевое слово protected. 11.В обработчике событий элемента управления Login создайте переменную типа Boolean, которая будет сохранять результаты вызова метода Membership.ValidateUser со значениями свойств UserName и Password элемента управления Login в качестве параметров. 12.Проверьте переменную типа Boolean. Если ее значение true, вызовите метод FormsAuthentication.RedirectFromLoginPage с обьектом UserName относящимсяся к элемету управления Login, и установите значение параметра createPersistentCookiesв false. Ваш код должен выглядеть следующим образом: void AdvWorksLogin_Authenticate(object sender, AuthenticateEventArgs e) { bool authenticated = Membership.ValidateUser (AdvWorksLogin.UserName, AdvWorksLogin.Password); if (authenticated) FormsAuthentication.RedirectFromLoginPage (AdvWorksLogin.UserName, false); } 4) Создайте новую веб-форму. 1. Из панели инструментов Toolboxперетащите элемент управления Panel ниже панели pnlLogin. 2. В окне Properties, установите следующие знчения: Атрибут Значение (ID) Visible pnlNewUser false Из кода элемента управления Panel удалите параметры Height и Width. Ваш код должен выглядеть следующим образом: <asp:Panel ID="pnlNewUser" Visible="false" runat="server"> 3. Из панели инструмонтов Toolbox перетащите элемент управления Label в панель pnlNewUser, используя тэг <br>. 4. В окне Properties установите следующие значения: Атрибут Значение (ID) Text lblUsername User Name: Ваш код должен выглядеть следующим образом: <asp:Label ID="lblUsername" runat="server" Text="User Name:"> </asp:Label><br /> 5. Из Toolbox перетащите элемент управления TextBox под надпись lblUsername Label в панель pnlNewUser, и установите значение атрибута ID как txtUsername, используя тэг <br>. Ваш код должен выглядеть следующим образом: <asp:TextBox ID="txtUsername" runat="server"></asp:TextBox><br /> 6. Из Toolbox перетащите элемент управления Label и расположите его ниже txtUsername в панель pnlNewUser, используя тэг <br> . 7. В окне Properties, установите следующие значения: Attribute Value (ID) Text lblPassword Password: Ваш код должен выглядеть следующим образом: <asp:Label ID="lblPassword" runat="server" Text="Password:"> </asp:Label><br /> 8. Из Toolbox перетащите элемент управленияTextBox и расположите его ниже lblPassword панели pnlNewUser, используя тэг <br> . 9. В окне Properties, установите следующие значения: Attribute Value (ID) TextMode txtPassword Password Ваш код должен выглядеть следующим образом: <asp:TextBox ID="txtPassword" runat="server" TextMode="Password"></asp:TextBox><br /> 10.Из Toolbox перетащите элемент управления Button и расположите его ниже txtPassword в панель pnlNewUser, и установите следующие значения: Attribute Value (ID) Text btnAddUser Add 11.В списке Object, выберите btnAddUser, а затем в списке Event, выберите Click. Ваш код должен выглядеть следующим образом: <asp:Button ID="btnAddUser" runat="server" Text="Add" OnClick="btnAddUser_Click" /> </asp:Panel> 12.У обработчика события нажатия на кнопку btnAddUser удалите слово protected , вызовите метод Membership.CreateUser с передачей в качестве параметров значений свойств Text єлементов управления txtUsername и txtPassword. 13.Чтобы сохранить учетную запись пользователя в хранилище информации, используйте метод CreateUser класса Membership, и установите для UserName значение txtUsername.Text, а для Password - значение txtPassword.Text. 14.Установите значение свойства Visible элеметна управления pnlLogin равным true, а значение параметра Visible элемента управления pnlNewUser равным false. Ваш код должен выглядеть следующим образом: void btnAddUser_Click(object sender, EventArgs e) { Membership.CreateUser(txtUsername.Text, txtPassword.Text); pnlLogin.Visible = true; pnlNewUser.Visible = false; } 5) Просмотрите Login.aspx page. 1. Чтобы сохранить страницу login.aspx, нажмите File, а затем нажмите Save Login.aspx. 2. Нажмите правой кнопкой миши на любом участке страницы Login.aspx, и нажмите View in Browser. 3. Проверьте результат. 4. Закройте браузер и все открытые файлы либо проекты, но оставьте Visual Studio открытой. Упражнение 2 Конфигурирование аутентификации форм В этом упражнении вы будете задавать конфигурацию аутентификации форм для всего портала Adventure Works. Сценарий Следующим заданием в разработке портала будет правильное конфигурирование аутентификации форм, для чего необходимо: изменить атрибут authentication с Windows на Forms; конфигурировать провайдер членства. 1) Открытие исходного веб-сайта. 1. В среде Visual Studio, в меню File, нажмите Open Web Site. 2. Перейдите в \LabFiles\Starter\language\Ex2\AdWorksWebSite, а затем нажмите Open. 2) Активизация аутентификации форм. 1. В окне Solution Explorer двойным щелчком нажмите web.config. 2. В элементе authentication измените атрибут mode с Windows на Forms. 3. Добавьте элемент forms к элементу authentication и установите следующие значения атрибутов:. Атрибут Значение loginUrl login.aspx defaultUrl default.aspx Ваш код должен выглядеть следующим образом: <authentication mode="Forms"> <forms loginUrl="login.aspx" defaultUrl="default.aspx" /> </authentication> 4. Чтобы сохранить файл web.config file, нажмите File, и затем нажмите Save web.config. 3) Проверка результата. 1. В окне Solution Explorer правой кнопкой мыши нажмите Default.aspx, а затем нажмите View in Browser. 2. Проверьте результат. 3. Закройте браузер. 4. В меню File нажмите Close Project, но оставьте Visual Studio открытой для следующего упражнения. Упражнение 3 Конфигурирование Membership Сценарий В этом упражнении вы будете конфигурировать корпоративный сайт внутренней сети для поддержки возможностей членства и ролей. Финальным заданием будет интеграция информации членства и ролей в базу данных сайта Adventure Works Web. Это будет обеспечивать механизм аутентификации и авторизации всех пользователей портала Adventure Works. 1) Откройте стартовую страницу. 1. В среде Visual Studio, в меню File, нажмите Open Web Site. 2. Зайдите в папку \LabFiles\Starter\language\Ex3\AdWorksWebSite, а затем нажмите Open. 2) Конфигурция поставщика членства. 1. В окне Solution Explorer двойным щелчком нажмите web.config. 2. Добавьте элемент membership к секции system.web и установите следующие значения атрибутов: Атрибут Значение defaultProvider userIsOnlineTimeWindow NWMembership 15 Ваш код должен выглядеть следующим образом: <membership defaultProvider="NWMembership" userIsOnlineTimeWindow="15"> </membership> 3. Добавьте элемент providers к элементу membership. 4. Добавьте элемент add к элементу providers и установите следующие значения: Атрибут Значение Name connectionStringName Type NWMembership NWindConn System.Web.Security.SqlMembershipProvider requiresUniqueEmail requiresQuestionAndAnswer false false Ваш код должен выглядеть следующим образом: <membership defaultProvider="NWMembership" userIsOnlineTimeWindow="15"> <providers> <add name="NWMembership" connectionStringName="NWindConn" type="System.Web.Security.SqlMembershipProvider" requiresUniqueEmail="false" requiresQuestionAndAnswer="false" /> </providers> </membership> 5. Чтобы сохранить файл web.config, нажмите File, а затем намите Save web.config. 3) Просмотрите страницу Default.aspx. 1. В Solution Explorer, правым щелчком нажмите Default.aspx, затем нажмите View in Browser. 2. Нажмите ссылку I am a new user. 3. В блоке User Name напечатайте ваше имя. 4. В блоке Password, задайте пароль, соответствующий требованиям: Длина не меньше 8 символов. Пароль должен содержать нецифро-буквенные символы. Пароль должен содержать маленькие и большие буквы. Пароль должен содержать цифры. К примеру, Hello@123 5. Нажмите Add. 6. Войдите в систему, используя только что созданные имя пользователя и пароль. 7. Просмотрите результат. 5. В меню File, нажмите Close Project и закройте Visual Studio. 5. Содержание отчета В отчете должны быть представлены: Исходный код. Результат выполненой работы в виде скриншотов.