Каков наилучший механизм для реализации гранулярной безопасности (т.е. авторизации) в приложении ASP.NET MVC?

Предположим, высокоскоростному разработчику было поручено создать банковское приложение, к которому могли бы обращаться разные люди. Каждый человек хотел бы получить доступ к своей учетной записи, но не хотел бы, чтобы другие имели к ней доступ. Я хотел бы знать, как лучше всего ограничивать доступ в приложении MVC, чтобы к нему мог получить доступ только пользователь, владеющий информацией (или администратор).

Authorize Атрибут позволяет нам ограничивать по ролям. Хотя это отправная точка, похоже, что любой прошедший проверку пользователь может получить доступ к информации любого другого пользователя.

ActionFilters, кажется, предлагают возможность немного более детального контроля и, вероятно, могут быть использованы для выполнения задачи. Однако мне неясно, будут ли они рекомендуемым подходом.

Любые рекомендации или идеи приветствуются.

4 ответа

ActionFilter, вероятно, является хорошей отправной точкой, но в зависимости от вашей архитектуры вы можете подумать, достаточно ли хороша защита периметра.

Если вы, по сути, создаете однослойное приложение ASP.NET MVC (и для этого могут быть совершенно разумные причины), ActionFilter обеспечит достаточно хорошую защиту и в то же время очень простую в применении.

С другой стороны, если ваше приложение представляет собой многослойное приложение, защита в глубину является более подходящим. В этом случае вам следует рассмотреть возможность применения логики авторизации в модели предметной области или, возможно, даже на уровне доступа к данным. Это гарантирует, что если вы когда-либо разработаете другое приложение, основанное на той же доменной модели (например, веб-сервис), логика авторизации будет по-прежнему применяться.

Независимо от того, что вы делаете, я настоятельно рекомендую основывать фактическую реализацию авторизации на IPrincipal.

Если говорить более конкретно, то, о чем вы здесь спрашиваете, лучше всего смоделировано с помощью авторизации на основе ACL: установите ACL для каждого профиля пользователя, который по умолчанию предоставляет доступ только самому себе и администратору. Если / когда вам позже понадобится расширить приложение, чтобы разрешить делегированный доступ к профилям других пользователей (я не знаю, насколько это реалистично в вашем конкретном случае), вы можете просто сделать это, добавив новую запись в ACL.

В таком случае оценка доступа включает в себя получение ACL для запрошенного ресурса и проверку, включен ли текущий пользователь (IPrincipal) в этот ACL. Такая операция, скорее всего, будет включать в себя внепроцессные операции (поиск ACL в базе данных), поэтому наличие ее в качестве неявной части приложения путем ее скрытия за ActionFilter звучит так, будто потенциально может скрыть некоторые проблемы с производительностью. В таком случае я хотел бы сделать модель авторизации более понятной / видимой.

По моему мнению, если у вас одноуровневое приложение, авторизация является лучшим вариантом, а также actionfilter гораздо лучше и проще в использовании. Но если ваше приложение является многослойным, вы должны использовать список контроля доступа [ACL].

Если вы когда-нибудь захотите использовать авторизацию, вы можете взглянуть на реализации на основе XACML.

Я думаю, что вы правильно поняли, подход ActionFilter является разумным.

Я бы создал набор фильтров пользовательских действий, которые унаследованы от AuthorizeAttribute.

В дополнение к функциональности атрибута Authorize вы могли бы четко реализовать более строгую политику только для владельца.

НТН,

Дэн

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