Merge branch 'master' of git@vc.linet-services.de:public/lx-office-erp
[kivitendo-erp.git] / SL / Auth.pm
index 870ead1..7df576b 100644 (file)
@@ -54,7 +54,7 @@ sub get_user_dbh {
   my ($self, $login, %params) = @_;
   my $may_fail = delete $params{may_fail};
 
-  my %user = $self->read_user($login);
+  my %user = $self->read_user(login => $login);
   my $dbh  = SL::DBConnect->connect(
     $user{dbconnect},
     $user{dbuser},
@@ -102,6 +102,10 @@ sub _read_auth_config {
   my $self = shift;
 
   map { $self->{$_} = $::lx_office_conf{authentication}->{$_} } keys %{ $::lx_office_conf{authentication} };
+
+  # Prevent password leakage to log files when dumping Auth instances.
+  $self->{admin_password} = sub { $::lx_office_conf{authentication}->{admin_password} };
+
   $self->{DB_config}   = $::lx_office_conf{'authentication/database'};
   $self->{LDAP_config} = $::lx_office_conf{'authentication/ldap'};
 
@@ -143,7 +147,7 @@ sub authenticate_root {
   my ($self, $password) = @_;
 
   $password             = SL::Auth::Password->hash_if_unhashed(login => 'root', password => $password);
-  my $admin_password    = SL::Auth::Password->hash_if_unhashed(login => 'root', password => $self->{admin_password});
+  my $admin_password    = SL::Auth::Password->hash_if_unhashed(login => 'root', password => $self->{admin_password}->());
 
   $main::lxdebug->leave_sub();
 
@@ -244,9 +248,9 @@ sub dbdisconnect {
 sub check_tables {
   $main::lxdebug->enter_sub();
 
-  my $self    = shift;
+  my ($self, $dbh)    = @_;
 
-  my $dbh     = $self->dbconnect();
+  $dbh   ||= $self->dbconnect();
   my $query   = qq|SELECT COUNT(*) FROM pg_tables WHERE (schemaname = 'auth') AND (tablename = 'user')|;
 
   my ($count) = $dbh->selectrow_array($query);
@@ -438,15 +442,25 @@ sub read_all_users {
 sub read_user {
   $main::lxdebug->enter_sub();
 
-  my $self  = shift;
-  my $login = shift;
+  my ($self, %params) = @_;
 
   my $dbh   = $self->dbconnect();
+
+  my (@where, @values);
+  if ($params{login}) {
+    push @where,  'u.login = ?';
+    push @values, $params{login};
+  }
+  if ($params{id}) {
+    push @where,  'u.id = ?';
+    push @values, $params{id};
+  }
+  my $where = join ' AND ', '1 = 1', @where;
   my $query = qq|SELECT u.id, u.login, cfg.cfg_key, cfg.cfg_value
                  FROM auth.user_config cfg
                  LEFT JOIN auth."user" u ON (cfg.user_id = u.id)
-                 WHERE (u.login = ?)|;
-  my $sth   = prepare_execute_query($main::form, $dbh, $query, $login);
+                 WHERE $where|;
+  my $sth   = prepare_execute_query($main::form, $dbh, $query, @values);
 
   my %user_data;
 
@@ -485,23 +499,26 @@ sub delete_user {
   my $self  = shift;
   my $login = shift;
 
-  my $u_dbh = $self->get_user_dbh($login, may_fail => 1);
   my $dbh   = $self->dbconnect;
+  my $id    = $self->get_user_id($login);
+  my $user_db_exists;
 
-  $dbh->begin_work;
+  $dbh->rollback and return $::lxdebug->leave_sub if (!$id);
 
-  my $query = qq|SELECT id FROM auth."user" WHERE login = ?|;
+  my $u_dbh = $self->get_user_dbh($login, may_fail => 1);
+  $user_db_exists = $self->check_tables($u_dbh) if $u_dbh;
 
-  my ($id)  = selectrow_query($::form, $dbh, $query, $login);
+  $u_dbh->begin_work if $u_dbh && $user_db_exists;
 
-  $dbh->rollback and return $::lxdebug->leave_sub if (!$id);
+  $dbh->begin_work;
 
   do_query($::form, $dbh, qq|DELETE FROM auth.user_group WHERE user_id = ?|, $id);
   do_query($::form, $dbh, qq|DELETE FROM auth.user_config WHERE user_id = ?|, $id);
-  do_query($::form, $u_dbh, qq|UPDATE employee SET deleted = 't' WHERE login = ?|, $login) if $u_dbh;
+  do_query($::form, $dbh, qq|DELETE FROM auth.user WHERE id = ?|, $id);
+  do_query($::form, $u_dbh, qq|UPDATE employee SET deleted = 't' WHERE login = ?|, $login) if $u_dbh && $user_db_exists;
 
   $dbh->commit;
-  $u_dbh->commit if $u_dbh;
+  $u_dbh->commit if $u_dbh && $user_db_exists;
 
   $::lxdebug->leave_sub;
 }
@@ -979,6 +996,7 @@ sub all_rights_full {
     ["--others",                       $locale->text("Others")],
     ["email_bcc",                      $locale->text("May set the BCC field when sending emails")],
     ["config",                         $locale->text("Change Lx-Office installation settings (all menu entries beneath 'System')")],
+    ["admin",                          $locale->text("Administration (Used to access instance administration from user logins)")],
     );
 
   return @all_rights;
@@ -1284,6 +1302,7 @@ SL::Auth - Authentication and session handling
 =over 4
 
 =item C<set_session_value @values>
+
 =item C<set_session_value %values>
 
 Store all values of C<@values> or C<%values> in the session. Each