Лучший способ скрыть / отключить элементы графического интерфейса на основе привилегий пользователя? - PullRequest
12 голосов
/ 18 апреля 2011

Я запускаю веб-приложение со стороной клиента, реализованной в чистом ExtJS и средним уровнем в Grails.Приложение имеет авторизацию на основе ролей, где у пользователя может быть много мелкозернистых ролей, таких как SOME_FORM_READ, SOME_FORM_UPDATE, SOME_DATA_DELETE, SOME_DATA_READ и т. Д. В зависимости от ролей пользователя определенные элементы графического интерфейса пользователя должны быть отключены или скрыты, а другие -быть в режиме только для чтения.

Я провел поиск в Интернете, но не нашел ни одного шаблона проектирования, который бы конкретно решал эту проблему, поэтому я придумал свой собственный дизайн.Я уверен, что многие веб-приложения будут иметь аналогичные требования, поэтому я хотел бы опубликовать свой дизайн здесь и услышать мнение людей по этому поводу.Мой дизайн ни в коем случае не является идеальным, но я надеюсь, что его можно улучшить с помощью каждого.Хотя я работаю с ExtJS, общий дизайн должен также применяться к аналогичным средам, таким как GWT, Flex, Swing и т. Д.

Итак, вот так:

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

  1. код манипуляции с элементом графического интерфейса, например:

    panel.hide () form.setReadOnly (true)

  2. Требование разрешения элемента GUI, например:

    form.requires ('READ', 'FORM_READ_ROLE')

    adminPanel.requires ('ADMIN_ROLE')

  3. Информация о привилегиях пользователя, которая в основном представляет собой список ролей, которые имеет пользователь;

  4. Логика авторизации: определяет, какие элементыскрыть / отключить на основе привилегий пользователя;

Ядром проекта является одноэлементный файл с именем GUIPermissionManager или сокращенно GPM.Это централизованный дизайн, в котором большая часть кода находится в GPM, поэтому элементы GUI не загрязняются кодом авторизации.Вот как работает GPM:

  • Элементы GUI (для доступа к которым требуется определенное разрешение) регистрируют информацию о своих разрешениях в GPM, например:

    GPM.register (this,'DEPARTMENT_DELETE_ROLE');// кнопка удаления отдела

  • GPM ведет список регистрации разрешений графического интерфейса пользователя

  • При входе пользователя в систему GPM получает список ролейиспользование назначено

  • GPM просматривает список регистрации разрешений GUI и на основе привилегий пользователя определяет, какую часть GUI скрывать, и, в свою очередь, соответственно вызывает element.hide ()

Вопросы :

  • Элементы GUI организованы в виде древовидной иерархии, например, панель содержит панель кнопок и форму, поэтому, когдапанель скрыта, нет необходимости дополнительно проверять, нужно ли скрывать панель кнопок и форму. Проблема : как зарегистрировать и поддерживать эту иерархическую информацию в GPM?
  • В настоящее время я могу думать только о двух случаях использования элемента GUI: скрыть элемент или установить элемент только для чтения(такой как форма).Есть ли другие варианты использования?
  • В ExtJS, чтобы скрыть элемент, мы вызываем hide (), но чтобы установить форму только для чтения, нам нужно придумать собственную функцию, скажем, она называется setReadOnly (), как разрешитьGPM знает, какую функцию вызывать?Передача функции как часть регистрации?
  • Как лучше всего настроить форму только для чтения?Если я расширю компонент формы с помощью функции setReadOnly (), будет много дублирования кода, и мне придется делать это для каждой формы, для которой требуется контроль разрешений.Можно ли создать динамический преобразователь формы в GPM, чтобы, если форма была настроена только для чтения, она автоматически заменяла все редактируемые поля полями только для отображения?

Ответы [ 2 ]

6 голосов
/ 20 апреля 2011

Q1: Скрытие элементов иерархического пользовательского интерфейса. Оптимизация GPM во избежание скрытия элементов, которые уже скрыты через родительский элемент, по моему мнению, не приведет к значительному увеличению производительности. Мои причины:

  1. Вы загружаете разрешения один раз, когда пользователь входит в систему, а не все время.
  2. В зависимости от того, как он закодирован, в любом случае потребуется дополнительная обработка для определения иерархии.
  3. При надлежащем планировании вы можете избежать регистрации десятков и десятков компонентов и придерживаться всеобъемлющих контейнеров.

Если вы действительно хотите отслеживать иерархическую информацию, вы всегда можете использовать метод «содержащий», который предоставляют все компоненты контейнера для проверки, содержится ли DisplayObject где-либо в его дочернем списке (в том числе в цепочке). Это может быть вызвано каждый раз, когда компонент зарегистрирован, чтобы проверить, есть ли у него уже зарегистрированный родительский элемент.

Затем в словаре можно установить флаг, чтобы игнорировать скрытие этого компонента. Этот флаг можно сначала проверить при переборе списка зарегистрированных компонентов, чтобы определить, что следует скрыть. В словаре могут использоваться ключи, соответствующие UID зарегистрированного компонента. Кроме того, этот флаг можно использовать для игнорирования компонента, когда приходит время игнорировать другие функции GPM, например, отключение формы (так как форма никогда не будет видна в любом случае).

Q2. Вдобавок ко всему, вы можете отключить / включить компоненты, внести изменения в состояние или перехватить события и все оповещения. Это действительно слишком широкий вопрос, так как все можно сделать - действительно, до дизайнера.

Q3. Вы могли бы:

  1. Укажите параметры при регистрации ваших компонентов, например, укажите, к какому типу они относятся (контейнер для скрытия, форма для настройки только для чтения и т. Д.)
  2. Проверьте каждый компонент в том виде, как он зарегистрирован, чтобы определить, что будет с ним сделано.

По сути, вы заключаете контракт с различными компонентами, когда GPM знает об их интерфейсах и взаимодействует с ними соответствующим образом.

Q4. Вы всегда можете установить форму для отключения (enabled = false). Это предотвращает любое взаимодействие с пользователем. Некоторые скины изменятся, чтобы указать, что компоненты отключены, поэтому вы можете изменить их скины, чтобы предотвратить некоторые из этих действий отображения. В этой строке вы также можете изменить их обложки, чтобы скрыть определенные элементы, такие как граница поля TextInput, чтобы он выглядел больше как «представление», чем как отключенный ввод.

Можно было бы создать «преобразователь», который изменяет TextInputs с компонентами RichText и тому подобное. Это заняло бы приличный объем работы и, вероятно, должно быть встроено в расширенный класс Form вместо GPM. Я думаю, что различные состояния скинов для каждого типа компонентов могут быть лучшим решением, чтобы избежать создания и уничтожения компонентов просто для изменения внешнего вида формы.

1 голос
/ 18 апреля 2011

Внимание!Привилегии пользователей / авторизация должны контролироваться на стороне сервера, а не на стороне клиента, особенно для веб-приложений на основе js.Это большой риск для безопасности.Вы должны учесть это в своей структуре.

edit - какова ваша структура для управления авторизацией на стороне клиента?Это в основном будет направлять ваше управление на стороне клиента.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...