Die Option "Zahlenformat (Eingabe)" entfernt. Wenn sowohl . als auch , als Dezimaltre...
[kivitendo-erp.git] / SL / User.pm
index 7e40414..ea95cb1 100644 (file)
@@ -34,6 +34,8 @@
 
 package User;
 
+use SL::DBUpgrade2;
+
 sub new {
   $main::lxdebug->enter_sub();
 
@@ -114,8 +116,12 @@ sub login {
   if ($self->{login}) {
 
     if ($self->{password}) {
-      $form->{password} = crypt $form->{password},
-        substr($self->{login}, 0, 2);
+      if ($form->{hashed_password}) {
+        $form->{password} = $form->{hashed_password};
+      } else {
+        $form->{password} = crypt($form->{password},
+                                  substr($self->{login}, 0, 2));
+      }
       if ($self->{password} ne $form->{password}) {
         $main::lxdebug->leave_sub();
         return -1;
@@ -158,23 +164,37 @@ sub login {
                  '$myconfig{tel}', 'user')|;
       $dbh->do($query);
     }
+
+    $self->create_schema_info_table($form, $dbh);
+
     $dbh->disconnect;
 
     $rc = 0;
 
-    if (&update_available($myconfig{"dbdriver"}, $dbversion)) {
+    my $controls =
+      parse_dbupdate_controls($form, $myconfig{"dbdriver"});
 
-      # update the tables
-      open FH, ">$userspath/nologin" or die "
-$!";
+    map({ $form->{$_} = $myconfig{$_} }
+        qw(dbname dbhost dbport dbdriver dbuser dbpasswd dbconnect));
+
+    if (update_available($myconfig{"dbdriver"}, $dbversion) ||
+        update2_available($form, $controls)) {
 
-      map { $form->{$_} = $myconfig{$_} }
-        qw(dbname dbhost dbport dbdriver dbuser dbpasswd);
+      $form->{"stylesheet"} = "lx-office-erp.css";
+      $form->{"title"} = $main::locale->text("Dataset upgrade");
+      $form->header();
+      print($form->parse_html_template("dbupgrade/header"));
 
       $form->{dbupdate} = "db$myconfig{dbname}";
       $form->{ $form->{dbupdate} } = 1;
 
-      $form->info("Upgrading Dataset $myconfig{dbname} ...");
+      if ($form->{"show_dbupdate_warning"}) {
+        print($form->parse_html_template("dbupgrade/warning"));
+        exit(0);
+      }
+
+      # update the tables
+      open(FH, ">$userspath/nologin") or die("$!");
 
       # required for Oracle
       $form->{dbdefault} = $sid;
@@ -184,11 +204,18 @@ $!";
       $SIG{QUIT} = 'IGNORE';
 
       $self->dbupdate($form);
+      $self->dbupdate2($form, $controls);
 
       # remove lock file
-      unlink "$userspath/nologin";
+      unlink("$userspath/nologin");
+
+      my $menufile =
+        $self->{"menustyle"} eq "v3" ? "menuv3.pl" :
+        $self->{"menustyle"} eq "neu" ? "menunew.pl" :
+        "menu.pl";
 
-      $form->info("... done");
+      print($form->parse_html_template("dbupgrade/footer",
+                                       { "menufile" => $menufile }));
 
       $rc = -2;
 
@@ -272,7 +299,7 @@ sub dbsources {
 
   if ($form->{dbdriver} eq 'Pg') {
 
-    $query = qq|SELECT datname FROM pg_database|;
+    $query = qq|SELECT datname FROM pg_database WHERE NOT ((datname = 'template0') OR (datname = 'template1'))|;
     $sth   = $dbh->prepare($query);
     $sth->execute || $form->dberror($query);
 
@@ -334,20 +361,33 @@ sub dbcreate {
 
   my ($self, $form) = @_;
 
+  $form->{sid} = $form->{dbdefault};
+  &dbconnect_vars($form, $form->{dbdefault});
+  my $dbh =
+    DBI->connect($form->{dbconnect}, $form->{dbuser}, $form->{dbpasswd})
+    or $form->dberror;
+
   my %dbcreate = (
     'Pg'     => qq|CREATE DATABASE "$form->{db}"|,
     'Oracle' =>
       qq|CREATE USER "$form->{db}" DEFAULT TABLESPACE USERS TEMPORARY TABLESPACE TEMP IDENTIFIED BY "$form->{db}"|
   );
 
-  $dbcreate{Pg} .= " WITH ENCODING = '$form->{encoding}'" if $form->{encoding};
+  my %dboptions = (
+    'Pg' => [],
+  );
+
+  push(@{$dboptions{"Pg"}}, "ENCODING = " . $dbh->quote($form->{"encoding"}))
+    if ($form->{"encoding"});
+  if ($form->{"dbdefault"}) {
+    my $dbdefault = $form->{"dbdefault"};
+    $dbdefault =~ s/[^a-zA-Z0-9_\-]//g;
+    push(@{$dboptions{"Pg"}}, "TEMPLATE = $dbdefault");
+  }
 
-  $form->{sid} = $form->{dbdefault};
-  &dbconnect_vars($form, $form->{dbdefault});
-  my $dbh =
-    DBI->connect($form->{dbconnect}, $form->{dbuser}, $form->{dbpasswd})
-    or $form->dberror;
   my $query = qq|$dbcreate{$form->{dbdriver}}|;
+  $query .= " WITH " . join(" ", @{$dboptions{"Pg"}}) if (@{$dboptions{"Pg"}});
+
   $dbh->do($query) || $form->dberror($query);
 
   if ($form->{dbdriver} eq 'Oracle') {
@@ -380,6 +420,9 @@ sub dbcreate {
   $filename = qq|sql/$form->{chart}-chart.sql|;
   $self->process_query($form, $dbh, $filename);
 
+  $query = "UPDATE defaults SET coa = " . $dbh->quote($form->{"chart"});
+  $dbh->do($query) || $form->dberror($query);
+
   $dbh->disconnect;
 
   $main::lxdebug->leave_sub();
@@ -401,6 +444,15 @@ sub process_perl_script {
 
   $dbh->begin_work();
 
+  my %dbup_myconfig = ();
+  map({ $dbup_myconfig{$_} = $form->{$_}; }
+      qw(dbname dbuser dbpasswd dbhost dbport dbconnect));
+
+  my $nls_file = $filename;
+  $nls_file =~ s|.*/||;
+  $nls_file =~ s|.pl$||;
+  my $dbup_locale = Locale->new($main::language, $nls_file);
+
   my $result = eval($contents);
 
   if (1 != $result) {
@@ -409,8 +461,10 @@ sub process_perl_script {
   }
 
   if (!defined($result)) {
-    $form->dberror("The database update/creation did not succeed. The file ${filename} containing the following syntax error:<br>${@}<br>" .
-                   "All changes in that file have been reverted.");
+    print($form->parse_html_template("dbupgrade/error",
+                                     { "file" => $filename,
+                                       "error" => $@ }));
+    exit(0);
   } elsif (1 != $result) {
     unlink("users/nologin") if (2 == $result);
     exit(0);
@@ -427,7 +481,7 @@ sub process_perl_script {
 sub process_query {
   $main::lxdebug->enter_sub();
 
-  my ($self, $form, $dbh, $filename, $version) = @_;
+  my ($self, $form, $dbh, $filename, $version_or_control) = @_;
 
   #  return unless (-f $filename);
 
@@ -484,8 +538,13 @@ sub process_query {
     }
   }
 
-  if ($version) {
-    $dbh->do("UPDATE defaults SET version = " . $dbh->quote($version));
+  if (ref($version_or_control) eq "HASH") {
+    $dbh->do("INSERT INTO schema_info (tag, login) VALUES (" .
+             $dbh->quote($version_or_control->{"tag"}) . ", " .
+             $dbh->quote($form->{"login"}) . ")");
+  } elsif ($version_or_control) {
+    $dbh->do("UPDATE defaults SET version = " .
+             $dbh->quote($version_or_control));
   }
   $dbh->commit();
 
@@ -693,12 +752,31 @@ sub update_available {
 
   opendir SQLDIR, "sql/${dbdriver}-upgrade" or &error("", "sql/${dbdriver}-upgrade: $!");
   my @upgradescripts =
-    grep(/$form->{dbdriver}-upgrade-\Q$cur_version\E.*\.(sql|pl)/, readdir(SQLDIR));
+    grep(/$form->{dbdriver}-upgrade-\Q$cur_version\E.*\.(sql|pl)$/, readdir(SQLDIR));
   closedir SQLDIR;
 
   return ($#upgradescripts > -1);
 }
 
+sub create_schema_info_table {
+  $main::lxdebug->enter_sub();
+
+  my ($self, $form, $dbh) = @_;
+
+  my $query = "SELECT tag FROM schema_info LIMIT 1";
+  if (!$dbh->do($query)) {
+    $query =
+      "CREATE TABLE schema_info (" .
+      "  tag text, " .
+      "  login text, " .
+      "  itime timestamp DEFAULT now(), " .
+      "  PRIMARY KEY (tag))";
+    $dbh->do($query) || $form->dberror($query);
+  }
+
+  $main::lxdebug->leave_sub();
+}
+
 sub dbupdate {
   $main::lxdebug->enter_sub();
 
@@ -768,7 +846,7 @@ sub dbupdate {
       last if ($version < $mindb);
 
       # apply upgrade
-      $main::lxdebug->message(DEBUG2, "Appliying Update $upgradescript");
+      $main::lxdebug->message(DEBUG2, "Applying Update $upgradescript");
       if ($file_type eq "sql") {
         $self->process_query($form, $dbh, "sql/" . $form->{"dbdriver"} . "-upgrade/$upgradescript", $str_maxdb);
       } else {
@@ -789,6 +867,112 @@ sub dbupdate {
   return $rc;
 }
 
+sub dbupdate2 {
+  $main::lxdebug->enter_sub();
+
+  my ($self, $form, $controls) = @_;
+
+  $form->{sid} = $form->{dbdefault};
+
+  my @upgradescripts = ();
+  my ($query, $sth, $tag);
+  my $rc = -2;
+
+  @upgradescripts = sort_dbupdate_controls($controls);
+
+  foreach my $db (split / /, $form->{dbupdate}) {
+
+    next unless $form->{$db};
+
+    # strip db from dataset
+    $db =~ s/^db//;
+    &dbconnect_vars($form, $db);
+
+    my $dbh =
+      DBI->connect($form->{dbconnect}, $form->{dbuser}, $form->{dbpasswd})
+      or $form->dberror;
+
+    map({ $_->{"applied"} = 0; } @upgradescripts);
+
+    $query = "SELECT tag FROM schema_info";
+    $sth = $dbh->prepare($query);
+    $sth->execute() || $form->dberror($query);
+    while (($tag) = $sth->fetchrow_array()) {
+      $controls->{$tag}->{"applied"} = 1 if (defined($controls->{$tag}));
+    }
+    $sth->finish();
+
+    my $all_applied = 1;
+    foreach (@upgradescripts) {
+      if (!$_->{"applied"}) {
+        $all_applied = 0;
+        last;
+      }
+    }
+
+    next if ($all_applied);
+
+    foreach my $control (@upgradescripts) {
+      next if ($control->{"applied"});
+
+      $control->{"file"} =~ /\.(sql|pl)$/;
+      my $file_type = $1;
+
+      # apply upgrade
+      $main::lxdebug->message(DEBUG2, "Applying Update $control->{file}");
+      print($form->parse_html_template("dbupgrade/upgrade_message2",
+                                       $control));
+
+      if ($file_type eq "sql") {
+        $self->process_query($form, $dbh, "sql/" . $form->{"dbdriver"} .
+                             "-upgrade2/$control->{file}", $control);
+      } else {
+        $self->process_perl_script($form, $dbh, "sql/" . $form->{"dbdriver"} .
+                                   "-upgrade2/$control->{file}", $control);
+      }
+    }
+
+    $rc = 0;
+    $dbh->disconnect;
+
+  }
+
+  $main::lxdebug->leave_sub();
+
+  return $rc;
+}
+
+sub update2_available {
+  $main::lxdebug->enter_sub();
+
+  my ($form, $controls) = @_;
+
+  map({ $_->{"applied"} = 0; } values(%{$controls}));
+
+  dbconnect_vars($form, $form->{"dbname"});
+
+  my $dbh =
+    DBI->connect($form->{dbconnect}, $form->{dbuser}, $form->{dbpasswd}) ||
+    $form->dberror;
+
+  my ($query, $tag, $sth);
+
+  $query = "SELECT tag FROM schema_info";
+  $sth = $dbh->prepare($query);
+  $sth->execute() || $form->dberror($query);
+  while (($tag) = $sth->fetchrow_array()) {
+    $controls->{$tag}->{"applied"} = 1 if (defined($controls->{$tag}));
+  }
+  $sth->finish();
+  $dbh->disconnect();
+
+  map({ $main::lxdebug->leave_sub() and return 1 if (!$_->{"applied"}) }
+      values(%{$controls}));
+
+  $main::lxdebug->leave_sub();
+  return 0;
+}
+
 sub create_config {
   $main::lxdebug->enter_sub();
 
@@ -905,9 +1089,10 @@ sub config_vars {
 
   my @conf = qw(acs address admin businessnumber charset company countrycode
     currency dateformat dbconnect dbdriver dbhost dbport dboptions
-    dbname dbuser dbpasswd email fax name numberformat in_numberformat password
+    dbname dbuser dbpasswd email fax name numberformat password
     printer role sid signature stylesheet tel templates vclimit angebote bestellungen rechnungen
-    anfragen lieferantenbestellungen einkaufsrechnungen steuernummer co_ustid duns menustyle);
+    anfragen lieferantenbestellungen einkaufsrechnungen taxnumber co_ustid duns menustyle
+    template_format default_media default_printer_id copies show_form_details);
 
   $main::lxdebug->leave_sub();