Buenas amigos,
Después de buscar mucho sobre como manipular usuarios y permisos a nivel administrador y, al no encontrar nada al respecto, hice este pequeño programa para hacer todo eso.
Imagino que muchos ya saben como se hace pero otros quizá no sepan y están buscando hacer esto mismo.
Espero que el título del post sea lo suficientemente descriptivo para, en caso que se busque algo en relación no sea díficil encontrarlo.
El programa, como digo es muy simple y está divivido en 4 unidades.
Estoy usando lazarus y firebird y para acceder a los usuarios uso el componente fbadmin, para los privilegios componente zeos (zconnection y zquery).
La primera es el form de acceso.
Código Delphi
[-]unit principal;
{$mode objfpc}{$H+}
interface
uses
Classes, SysUtils, FBAdmin, db, FileUtil, Forms, Controls, Graphics, Dialogs,
StdCtrls, Buttons, ExtCtrls, ZConnection, ZDataset;
type
Tfconectar = class(TForm)
Bevel1: TBevel;
conectar: TBitBtn;
DataSource1: TDataSource;
epass: TEdit;
FBAdmin1: TFBAdmin;
Image1: TImage;
Label1: TLabel;
Label2: TLabel;
Label3: TLabel;
Label4: TLabel;
ZConnection1: TZConnection;
ZQuery1: TZQuery;
procedure conectarClick(Sender: TObject);
procedure epassKeyPress(Sender: TObject; var Key: char);
procedure FormActivate(Sender: TObject);
private
public
end;
var
fconectar: Tfconectar;
implementation
uses ugal;
{$R *.lfm}
procedure Tfconectar.FormActivate(Sender: TObject);
begin
epass.Text:='';
end;
procedure Tfconectar.epassKeyPress(Sender: TObject; var Key: char);
begin
if key=#13 then
conectar.SetFocus;
end;
procedure Tfconectar.conectarClick(Sender: TObject);
begin
try
fbadmin1.Host:='localhost';
fbadmin1.Port:=3050;
fbadmin1.User:='SYSDBA';
fbadmin1.Password:=epass.Text;
FBAdmin1.Protocol:=IBSPLOCAL; FBAdmin1.UseExceptions:=true;
fbadmin1.Connect;
zconnection1.HostName:=fbadmin1.Host;
zconnection1.Port:=3050;
zconnection1.User:=fbadmin1.User;
zconnection1.Password:=epass.text;
zconnection1.Database:='super_gal';
zconnection1.Connected:=true;
fconectar.Hide;
fusuario:=tfusuario.Create(self);
fusuario.ShowModal;
fusuario.Free;
fbadmin1.DisConnect;
close;
except
begin
epass.Text:='';
showmessage('Error en contraseña');
try
fbadmin1.DisConnect;
zconnection1.Disconnect;
except
end;
end;
end;
end;
end.
La segunda, en el caso que el acceso sea correcto, es la que permitirá visualizar los usuarios y manipularlos (modificar contraseñas, añadir uno nuevo y/o borrarlo).
Código Delphi
[-]unit ugal;
{$mode objfpc}{$H+}
interface
uses
Classes, SysUtils, FileUtil, Forms, Controls, Graphics, Dialogs, StdCtrls,
ExtCtrls;
type
Tfusuario = class(TForm)
anade_usuario: TButton;
modifica_usuario: TButton;
borra_usuario: TButton;
Label1: TLabel;
list_usuarios: TListBox;
procedure anade_usuarioClick(Sender: TObject);
procedure modifica_usuarioClick(Sender: TObject);
procedure borra_usuarioClick(Sender: TObject);
procedure FormActivate(Sender: TObject);
procedure cargarusuarios;
procedure revocar_privilegios;
private
GroupName,FirstName,MiddleName,LastName:string;
UserID, GroupID: longint;
users:tstringlist;
public
end;
var
fusuario: Tfusuario;
implementation
uses principal,nuevo,modifica;
{$R *.lfm}
procedure Tfusuario.FormActivate(Sender: TObject);
begin
cargarusuarios;
end;
procedure Tfusuario.anade_usuarioClick(Sender: TObject);
begin
fnuevo:=tfnuevo.Create(self);
fnuevo.ShowModal;
fnuevo.free;
cargarusuarios;
end;
procedure Tfusuario.modifica_usuarioClick(Sender: TObject);
begin
if list_usuarios.getselectedtext='' then
showmessage('No ha seleccionado usuario')
else
begin
form1:=tform1.Create(self);
form1.nombre.Caption:=list_usuarios.GetSelectedText;
form1.ShowModal;
form1.free;
end;
end;
procedure Tfusuario.borra_usuarioClick(Sender: TObject);
begin
if list_usuarios.getselectedtext='' then
showmessage('No ha seleccionado usuario')
else
try
revocar_privilegios;
fconectar.fbadmin1.DeleteUser(list_usuarios.GetSelectedText,'');
cargarusuarios;
except
end;
end;
procedure tfusuario.revocar_privilegios;
begin
fconectar.zquery1.SQL.Clear;
fconectar.ZQuery1.SQL.Text:='REVOKE ALL ON ventas FROM '+list_usuarios.GetSelectedText;
fconectar.zquery1.ExecSQL;
fconectar.zquery1.SQL.Clear;
fconectar.ZQuery1.SQL.Text:='REVOKE ALL ON ventasdetalle FROM '+list_usuarios.GetSelectedText;
fconectar.zquery1.ExecSQL;
fconectar.zquery1.SQL.Clear;
fconectar.ZQuery1.SQL.Text:='REVOKE ALL ON valoresiniciales FROM '+list_usuarios.GetSelectedText;
fconectar.zquery1.ExecSQL;
fconectar.zquery1.SQL.Clear;
fconectar.ZQuery1.SQL.Text:='REVOKE ALL ON INVENTARIOS FROM '+list_usuarios.GetSelectedText;
fconectar.zquery1.ExecSQL;
fconectar.zquery1.SQL.Clear;
fconectar.ZQuery1.SQL.Text:='REVOKE ALL ON CORTES FROM '+list_usuarios.GetSelectedText;
fconectar.zquery1.ExecSQL;
fconectar.zquery1.SQL.Clear;
fconectar.ZQuery1.SQL.Text:='REVOKE ALL ON cortesventas FROM '+list_usuarios.GetSelectedText;
fconectar.zquery1.ExecSQL;
fconectar.zquery1.SQL.Clear;
fconectar.ZQuery1.SQL.Text:='REVOKE ALL ON precios FROM '+list_usuarios.GetSelectedText;
fconectar.zquery1.ExecSQL;
fconectar.zquery1.SQL.Clear;
fconectar.ZQuery1.SQL.Text:='REVOKE ALL ON familias FROM '+list_usuarios.GetSelectedText;
fconectar.zquery1.ExecSQL;
fconectar.zquery1.SQL.Clear;
fconectar.ZQuery1.SQL.Text:='REVOKE ALL ON subfamilia FROM '+list_usuarios.GetSelectedText;
fconectar.zquery1.ExecSQL;
fconectar.zquery1.SQL.Clear;
fconectar.ZQuery1.SQL.Text:='REVOKE ALL ON proveedores FROM '+list_usuarios.GetSelectedText;
fconectar.zquery1.ExecSQL;
fconectar.zquery1.SQL.Clear;
fconectar.ZQuery1.SQL.Text:='REVOKE ALL ON formato FROM '+list_usuarios.GetSelectedText;
fconectar.zquery1.ExecSQL;
fconectar.zquery1.SQL.Clear;
fconectar.ZQuery1.SQL.Text:='REVOKE ALL ON estado FROM '+list_usuarios.GetSelectedText;
fconectar.zquery1.ExecSQL;
fconectar.zquery1.SQL.Clear;
fconectar.ZQuery1.SQL.Text:='REVOKE ALL ON compras FROM '+list_usuarios.GetSelectedText;
fconectar.zquery1.ExecSQL;
fconectar.zquery1.SQL.Clear;
fconectar.ZQuery1.SQL.Text:='REVOKE ALL ON comprasdetalle FROM '+list_usuarios.GetSelectedText;
fconectar.zquery1.ExecSQL;
fconectar.zquery1.SQL.Clear;
fconectar.ZQuery1.SQL.Text:='REVOKE ALL ON productos from'+list_usuarios.GetSelectedText;
end;
procedure tfusuario.cargarusuarios;
var
i:integer;
begin
fconectar.FBAdmin1.GetUser(fconectar.FBAdmin1.User,GroupName,FirstName,MiddleName,LastName,UserID, GroupID);
try
Users:=TStringList.Create;
list_usuarios.Clear;
if fconectar.FBAdmin1.GetUsers(Users) then
FOR I:=0 TO USERS.Count-1 DO
BEGIN
list_usuarios.Items.Add(users[i]);
END
finally
Users.Free;
end;
end;
end.
La tercera es donde podemos añadir un usuario nuevo y asignarle privilegios. Cabe destacar que esos privilegios son estandar para la aplicación que hice y que son los mismos para todos los usuarios que se añadan posteriormente. El cliente que me lo solicitó no quería complicarse la vida y lo quería muy sencillo.
Código Delphi
[-]unit nuevo;
{$mode objfpc}{$H+}
interface
uses
Classes, SysUtils, FileUtil, Forms, Controls, Graphics, Dialogs, StdCtrls,
ExtCtrls;
type
Tfnuevo = class(TForm)
Bevel1: TBevel;
Guardar: TButton;
nombre: TEdit;
pass: TEdit;
passcomparar: TEdit;
Label1: TLabel;
Label2: TLabel;
Label3: TLabel;
procedure GuardarClick(Sender: TObject);
procedure FormActivate(Sender: TObject);
procedure nombreKeyPress(Sender: TObject; var Key: char);
procedure passcompararKeyPress(Sender: TObject; var Key: char);
procedure passKeyPress(Sender: TObject; var Key: char);
procedure privilegios;
private
public
end;
var
fnuevo: Tfnuevo;
implementation
uses principal;
{$R *.lfm}
procedure Tfnuevo.GuardarClick(Sender: TObject);
begin
if pass.text=passcomparar.Text then
try
fconectar.fbadmin1.AddUser(nombre.text,pass.Text,'','','','','',0,0);
privilegios;
close
except
begin
showmessage('El usuario ya existe');
nombre.text:='';
pass.text:='';
passcomparar.Text:='';
end
end
else
begin
showmessage('Las contraseñas no coinciden');
pass.Text:='';
passcomparar.Text:='';
end;
end;
procedure tfnuevo.privilegios;
begin
fconectar.zquery1.SQL.Clear;
fconectar.ZQuery1.SQL.Text:='GRANT SELECT, INSERT, update, DELETE ON ventas TO '+nombre.Text;
fconectar.zquery1.ExecSQL;
fconectar.zquery1.SQL.Clear;
fconectar.ZQuery1.SQL.Text:='GRANT SELECT, INSERT, update, DELETE ON ventasdetalle TO '+nombre.Text;
fconectar.zquery1.ExecSQL;
fconectar.zquery1.SQL.Clear;
fconectar.ZQuery1.SQL.Text:='GRANT SELECT, INSERT, update, DELETE ON valoresiniciales TO '+nombre.Text;
fconectar.zquery1.ExecSQL;
fconectar.zquery1.SQL.Clear;
fconectar.ZQuery1.SQL.Text:='GRANT SELECT, INSERT, update, DELETE ON INVENTARIOS TO '+nombre.Text;
fconectar.zquery1.ExecSQL;
fconectar.zquery1.SQL.Clear;
fconectar.ZQuery1.SQL.Text:='GRANT SELECT, INSERT, update, DELETE ON CORTES TO '+nombre.Text;
fconectar.zquery1.ExecSQL;
fconectar.zquery1.SQL.Clear;
fconectar.ZQuery1.SQL.Text:='GRANT SELECT, INSERT, update, DELETE ON cortesventas TO '+nombre.Text;
fconectar.zquery1.ExecSQL;
fconectar.zquery1.SQL.Clear;
fconectar.ZQuery1.SQL.Text:='GRANT SELECT ON precios TO '+nombre.Text;
fconectar.zquery1.ExecSQL;
fconectar.zquery1.SQL.Clear;
fconectar.ZQuery1.SQL.Text:='GRANT SELECT ON familias TO '+nombre.Text;
fconectar.zquery1.ExecSQL;
fconectar.zquery1.SQL.Clear;
fconectar.ZQuery1.SQL.Text:='GRANT SELECT ON subfamilia TO '+nombre.Text;
fconectar.zquery1.ExecSQL;
fconectar.zquery1.SQL.Clear;
fconectar.ZQuery1.SQL.Text:='GRANT SELECT ON proveedores TO '+nombre.Text;
fconectar.zquery1.ExecSQL;
fconectar.zquery1.SQL.Clear;
fconectar.ZQuery1.SQL.Text:='GRANT SELECT ON formato TO '+nombre.Text;
fconectar.zquery1.ExecSQL;
fconectar.zquery1.SQL.Clear;
fconectar.ZQuery1.SQL.Text:='GRANT SELECT ON estado TO '+nombre.Text;
fconectar.zquery1.ExecSQL;
fconectar.zquery1.SQL.Clear;
fconectar.ZQuery1.SQL.Text:='GRANT SELECT ON compras TO '+nombre.Text;
fconectar.zquery1.ExecSQL;
fconectar.zquery1.SQL.Clear;
fconectar.ZQuery1.SQL.Text:='GRANT SELECT ON comprasdetalle TO '+nombre.Text;
fconectar.zquery1.ExecSQL;
fconectar.zquery1.SQL.Clear;
fconectar.ZQuery1.SQL.Text:='GRANT SELECT ON productos TO '+nombre.Text;
fconectar.zquery1.ExecSQL;
end;
procedure Tfnuevo.FormActivate(Sender: TObject);
begin
nombre.Text:='';
pass.Text:='';
passcomparar.Text:='';
end;
procedure Tfnuevo.nombreKeyPress(Sender: TObject; var Key: char);
begin
if key=#13 then
pass.SetFocus;
end;
procedure Tfnuevo.passcompararKeyPress(Sender: TObject; var Key: char);
begin
if key=#13 then
Guardar.SetFocus;
end;
procedure Tfnuevo.passKeyPress(Sender: TObject; var Key: char);
begin
if key=#13 then
passcomparar.SetFocus;
end;
end.
Y la cuarta es simplemente un form para poder cambiar la contraseña de un usuario.
Código Delphi
[-]unit modifica;
{$mode objfpc}{$H+}
interface
uses
Classes, SysUtils, FileUtil, Forms, Controls, Graphics, Dialogs, ExtCtrls,
StdCtrls;
type
TForm1 = class(TForm)
Bevel1: TBevel;
guardar: TButton;
Label1: TLabel;
Label2: TLabel;
Label3: TLabel;
nombre: TLabel;
pass: TEdit;
passcomparar: TEdit;
procedure guardarClick(Sender: TObject);
procedure passcompararKeyPress(Sender: TObject; var Key: char);
procedure passKeyPress(Sender: TObject; var Key: char);
private
public
end;
var
Form1: TForm1;
implementation
uses principal;
{$R *.lfm}
procedure TForm1.guardarClick(Sender: TObject);
begin
if pass.text=passcomparar.Text then
try
fconectar.fbadmin1.ModifyUser(nombre.Caption,pass.Text,'','','','','',0,0);
close
except
begin
showmessage('El usuario ya existe');
pass.text:='';
passcomparar.Text:='';
end
end
else
begin
showmessage('Las contraseñas no coinciden');
pass.Text:='';
passcomparar.Text:='';
end;
end;
procedure TForm1.passcompararKeyPress(Sender: TObject; var Key: char);
begin
if key=#13 then
guardar.SetFocus;
end;
procedure TForm1.passKeyPress(Sender: TObject; var Key: char);
begin
if key=#13 then
passcomparar.SetFocus;
end;
end.
Como veís es un programa muy simple, quizá los que saben más no lo hubieran hecho así, pero ahí está mi modesto aporte.
Espero que os sirva.