AuthorizeAttribute MVC - ограничить доступ к пользовательскому контенту

Поэтому я прочитал о том, как плохо реализованы ваши собственные процедуры авторизации!

http://www.nashcoding.com/2011/02/05/using-the-forms-authentication-membership-provider-on-appharbor/

И я испугался, потому что я реализовывал свои действия как таковые (например, предотвращение доступа к данным учетной записи, если аутентифицированный пользователь не вошел в систему)

public ActionResult DisplayAccount(int someid){
    Account a = context.Accounts.Single(a => a.id == someid);

    // currentUserId() returns userid from FormsAuthentication
    if (!a.owner == currentUserId()){
        /* Not Authorised! */
    }
}

Что, очевидно, означает, что он сломается, если ASP решит кэшировать мое действие (поэтому действие даже не будет выполнено).

Так что теперь я изучаю использование AuthorizeAttribute, чтобы сделать то, что мне нужно, что

  • запретить доступ к действию, если он не прошел проверку подлинности
  • проверить, имеет ли аутентифицированный пользователь доступ к полученному ресурсу

Однако всякий раз, когда я думаю об этом, я не могу думать о том, как реализовать 2-й пункт. Роли не работают, потому что это на уровне сайта, но внутри приложения пользователи также имеют роли (например, владелец, модератор, участник, пользователь и т. Д.), И они имеют эти роли только в своих соответствующих частях приложения (например, владелец темы, автор вики, модератор форума и т. д.)

Я столкнулся с несколькими примерами переопределения AuthorizeCore. Я могу себе представить создание нескольких подклассов AuthorizeAttribute для каждого имеющегося у меня ресурса (к счастью, не многих), но означает ли это, что мне приходится запрашивать базу данных каждый раз, когда я нажимаю на это действие, чтобы гарантировать, что зарегистрированный пользователь должен получить доступ к этим данным, а затем запросить базу данных в моем действии, чтобы получить модель, вместо того, чтобы делать это в моем запросе?

Так что мои вопросы

  • я слишком беспокоюсь о кешировании? Произойдет ли что-либо из следующего
    • веб-сайт кэширует данные пользователя A, которые отображаются на экране пользователя B?
    • веб-сайт кэширует версию страницы администратора (с элементами управления редактированием), а обычный пользователь видит кэшированную версию?
  • Использование AuthorizeAttribute само собой разумеющееся, но как мне добиться того, что мне нужно сделать в пункте 2, не обращаясь к базе данных перед действием? Или каков наилучший способ добиться этого в любом случае.
  • Или я использую только AuthorizeAttribute, чтобы определить, вошел ли пользователь в систему, и выполнить другую логику проверки в моих действиях?

Во всяком случае, я надеюсь, что этот пост не идет по каким-либо старым путям (я не мог найти ничего по этому, что я нашел окончательным)


Изменить: Я думаю, если я не включаю кэширование, эта проблема не возникнет, это правильно?


Изменить: сейчас я собираюсь использовать vanilla AuthorizeAttribute, затем проверять доступ к уровню ресурсов в моих действиях, а затем убедиться, что я не использую кэширование для любых аутентифицированных действий. Надеюсь, получит больше ответов на это в течение недели.

1 ответ

Я использовал следующий подход в недавнем проекте, создавая DataRightsAttribute, который использовал перечисление для каждого поддерживаемого типа модели. Он работает, сначала извлекая идентификатор из данных маршрута, formcollection или строки запроса. Затем он запросил тип модели, определенный в enum, и провел соответствующую проверку, чтобы проверить, авторизован ли текущий пользователь к нему.

Использование было так:

[DataRights(ModelType.Customer)]

Он использовался вместе с AuthorizeAttribute (который мы переопределили) и никогда не замечал никаких проблем с кэшированием.

Другие вопросы по тегам