Обзор реализации приложения MVC.NET с пользовательским членством - PullRequest
1 голос
/ 06 апреля 2010

Хотелось бы услышать, видит ли кто-нибудь какие-либо проблемы с тем, как я реализовал безопасность в этом приложении MVC.NET на базе Oracle, или проблемы безопасности, проблемы параллелизма или проблемы масштабируемости.

Сначала я реализовал CustomOracleMembershipProvider для обработки интерфейса базы данных с хранилищем членства.

Я реализовал пользовательский принципал с именем Пользователь , который реализует IPrincipal и имеет хэш-таблицу ролей.

Я также создал отдельный класс с именем AuthCache , который имеет простой кэш для Пользователь объектов. Его цель проста - избежать повторных обращений к базе данных, в то же время отделяя кэширование от веб-слоя или слоя данных. (Так что я могу разделить кеш между MVC.NET, WCF и т. Д.)

MVC.NET stock MembershipService использует CustomOracleMembershipProvider (настроенный в web.config), и оба MembershipService и FormsService совместно используют доступ к одноэлементному AuthCache.

Мой метод AccountController.LogOn ():

1) Проверяет пользователя с помощью MembershipService. Метод Validate () , также загружает роли в контейнер User.Roles и затем кэширует пользователя в AuthCache.

2) Вход пользователя в веб-контекст с помощью FormsService. SignIn () , который обращается к AuthCache (не к базе данных) для получения пользователя, устанавливает HttpContext.Current.User к кэшированному принципалу пользователя.

В global.asax.cs реализовано Application_AuthenticateRequest () . Он расшифровывает FormsAuthenticationTicket, обращается к AuthCache с помощью ticket.Name (Имя пользователя) и устанавливает Принципала, устанавливая Context.User = пользователь из AuthCache.

Короче говоря, все эти классы совместно используют AuthCache, и для синхронизации потоков у меня есть lock () в методе кэш-хранилища. Нет блокировки в методе чтения.

Пользовательский поставщик членства не знает о кеше, MembershipService не знает ни о каком HttpContext (поэтому его можно использовать за пределами веб-приложения), а FormsService не использует никаких пользовательских методов, кроме доступа к AuthCache. установить Context.User для первоначального входа в систему, чтобы он не зависел от конкретного поставщика членства.

Главное, что я сейчас вижу, это то, что AuthCache будет совместно использовать объект User, если пользователь входит в систему из нескольких сеансов. Поэтому мне, возможно, придется изменить ключ с просто UserId на что-то другое (может быть, использовать что-то в FormsAuthenticationTicket для ключа?).

1 Ответ

3 голосов
/ 06 апреля 2010

Зачем использовать Hashtable для ролей? Простой список, вероятно, будет быстрее искать, если вы не ожидаете, что у людей будет больше, чем несколько ролей. Если вы можете заранее предсказать все роли, тогда использование перечисления битовой маски / флагов будет еще лучше.

Вам следует избегать написания собственного механизма блокировки, так как довольно легко ошибиться. Используйте новые классы System.Collections.Concurrent, или, если вам нужно свернуть свои собственные, то обязательно используйте Interlocked (поскольку все другие механизмы блокировки довольно дороги).

Кэширование должно использовать инкапсуляцию WeakReference, чтобы разрешить GCed записи и поддерживать извлечение пользовательской информации из базы данных, если запись отсутствует. Может быть, посмотрите на Velocity, если вам нужен распределенный кеш.

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

Наконец, я лично презираю весь API-интерфейс поставщика членства, потому что он использует идентификаторы GUID для идентификации, а дизайн базы данных SQL Server по умолчанию для профилей пользователей просто ужасен (он также снижает производительность). Похоже, это вас не беспокоит, так как вы сами развернули (db и реализация), но вы можете оценить, есть ли реальные преимущества, связанные с реализацией API, или это в основном кандалы, связывающие вас особыми способами. делать вещи.

...