|
|
|||||||||||||||||||||||||||||
|
Права доступа к элементам управления DelphiИсточник: aleksandr-pro
Автор: Проскуряков АлександрВ большинстве сложных приложений на основе баз данных существует понятие разграничение доступа к данным, таблицам, записям, полям, но в большинстве случаев этого не достаточно. В любом приложении существует множество других задач по мимо доступа к данным, таких как, например отчеты, к которым так же надо разграничивать доступ на уровне пользователей, да и во многом иногда проще разграничить права не на уровне базы данных, а на уровне приложения, так как это может предоставить более гибкую и простую систему настройки прав пользователей. В данном примере я опишу простой в программировании и использовании способ администрирования прав пользователей на доступ к элементам управления вашей программы. Задачи:
Способ решенияДля удобства администрирования и использования создан древовидный список см. рис.1, который при помощи правой кнопки мыши легко редактируется разработчиком и так же легко используется администратором системы. Для обеспечения функциональной свободы создан класс TrightData (см. исходники) который позволяет работать со строкой прав, описание класса см. ниже. Что бы облегчить администрирование и использование, каждый элемент дерева наделен дополнительными данными, а именно классом TrightData, который содержит в себе информацию о том, что пользователю разрешено или запрещено. Сами данные представляют собой следующий видИмяФормы(элементуправления.свойство) например: Form1(Button1.enabled) или Form1(button2.enabled,Menuitem.visible), form2(SpeedButton3.visible) Для экономии размера имя свойство заменено кодом, который вы можете менять на свое усмотрение, скажем я сделал так: Form1(button2.1,Menuitem.0), form2(SpeedButton3.0),all(SpeedButton1.5) где 0 - visible 1 - Enabled и т.д. Форма all используется для тех элементов управления, которые могут содержаться на любой форме. Каждое правило может содержать множество классов, каждый из которых содержит множество свойств. Для удобства администрирования, при компиляции с параметром {$define isadmin} доступно меню разработчика, а так же возможно мышью перетаскивать правила. Так же в модуле присутствуют функции загрузки и сохранения правил из потока Tstream, так что саму информацию о правилах можно сохранять в любом удобном для вас виде.
Для применения свойств используется функция парсер, которая выделяет из общей строки прав только то, что относиться к форме, описанной в параметре parent, и так же то, что относится ко всем формам (all) procedure ApllyRights(const parent:Twincontrol; rights:string); var s,s1:string; x,z,y:integer; len:byte; begin if rights='' then exit; s:=lowercase(parent.Name)+'('; z:=pos(s,rights); // вытаскиваем из общей строки прав только то, что относиться к текущей форме if z>0 then begin x:=length(s); y:=PosEx(')',rights,z+x); s:=''; if y>0 then s:=copy(rights,z+x,y-x-z);end else s:=''; s1:='all(';z:=pos(s1,rights); // и так же вытаскиваем то что относиться ко всем формам. if z>0 then begin x:=length(s1);y:=PosEx(')',rights,z+x); s1:=''; if y>0 then s1:=copy(rights,z+x,y-x-z);end else s1:=''; // формируем общую строку того, что применимо к данной форме rights:=s1+','+s+','; // запятая в конце обязательна. for x := parent.ComponentCount - 1 downto 0 do begin s:=lowercase(parent.Components[x].Name); len:=length(s)-3; z:=pos(s,rights); if z>0 then begin z:=PosEx('.',rights,z+len); y:=PosEx(',',rights,z+1); s1:=copy(rights,z+1,y-z-1); if (parent.Components[x].ClassName='ваш класс')and(s1='ваш код свойства') then "ваше действие" else if (parent.Components[x].ClassName='ваш класс ')and(s1='ваш код свойства ') then "ваше действие" else if s1='0' then SetOrdProp(parent.Components[x],'Visible',0) else if s1='1' then SetOrdProp(parent.Components[x],'Enabled',0) else if s1='5' then SetOrdProp(parent.Components[x],'ReadOnly',1); end; end; end; Как видно из процедуры, можно изменять не только стандартные логические свойства но и любые другие предусмотренные разработчиком. Данная функция может вызываться при загрузке или отображении формы следующим способом: Procedure TDisp1.FormShow(Sender: TObject); begin ApllyRights(self,CurrentRigths); // где self ссылка на вызываемую форму, а CurrentRigths - общая строка правил для конкретного пользователя. end; Описание класса TrightData TrightData=class(Tobject) private RightsClass:array of Record TFormName:string[50]; SubClass:array of string[50];end; // массив содержащий элементы строки прав function AddForm(const formname:string):integer; // Функция возвращает номер формы по порядку, если формы нет она создается Function AddSubClass(const formid:integer;Subclass:string):integer; // Функция возвращает номер класса по порядку в форме, если класса нет он создается procedure Clear; // очищает правило public Function FormExists(const FormName:string):integer; // проверяет создана ли форма возвращает номер формы или -1 если форма не найдена Function SubClassExist(FormId:integer;Subclass:string):integer; // проверяет создан ли класс в форме возвращает номер класса или -1 если класс не найдена constructor Create(CurrentRights:string); // создает массив правил RightsClass из строки прав. Destructor destroy; Function GetString:string; // Создает строку правил из массива правил Procedure ConcatWith(const Plus:TrightData);overload; // Складывает правила текущее с правилом Plusж Procedure ConcatWith(const s:string);overload; // Складывает правила текущее с троковым выражением правила function Equal(a,b: TrightData) : Boolean; // проверяет вхождение правила b в правило а Function IsNull:boolean; // возращает true если правило пустое. end; Данный модуль будет работоспособен в версии Delphi 6,7,2005,2007, 2009 и может быть легко использован в уже готовой программе без значительных доработок. Ссылки по теме
Файлы для загрузки
|
|