]> wagnertech.de Git - kivitendo-erp.git/commitdiff
Steuerzonen überarbeitet - Prüfung und Löschen
authorG. Richardson <information@kivitendo-premium.de>
Thu, 30 Jul 2015 04:36:03 +0000 (06:36 +0200)
committerG. Richardson <information@kivitendo-premium.de>
Thu, 30 Jul 2015 10:43:54 +0000 (12:43 +0200)
Nicht benutzte Steuerzonen können jetzt gelöscht werden, sowie deren
Kontenzuordnungen geändert werden (wie bei Buchungsgruppen). Siehe
Feature #70.

Schlägt die Speicherung neuer Steuerzonen fehl, weil z.B. die
Buchungsgruppenkonten fehlen, gibt es nun einen Rollback und eine
ordentliche Fehlermeldung, siehe Fehler #68.

SL/Controller/Taxzones.pm
SL/DB/TaxZone.pm
locale/de/all
templates/webpages/taxzones/form.html

index 6f5adf7f15adf09fa92ab9fc8e5d5d7f88ccf42d..60b820d4f705af8e576cdd098f9e2c413f9454e1 100644 (file)
@@ -4,8 +4,6 @@ use strict;
 
 use parent qw(SL::Controller::Base);
 
-#use List::Util qw(first);
-
 use SL::DB::TaxZone;
 use SL::Helper::Flash;
 use SL::Locale::String;
@@ -18,7 +16,7 @@ use Rose::Object::MakeMethods::Generic (
 );
 
 __PACKAGE__->run_before('check_auth');
-__PACKAGE__->run_before('load_config', only => [ qw(edit update) ]); #destroy
+__PACKAGE__->run_before('load_config', only => [ qw(edit update delete) ]);
 
 #
 # actions
@@ -29,7 +27,6 @@ sub action_list {
 
   my $taxzones = SL::DB::Manager::TaxZone->get_all_sorted();
 
-  $::form->header;
   $self->render('taxzones/list',
                 title    => t8('List of tax zones'),
                 TAXZONES => $taxzones);
@@ -69,6 +66,24 @@ sub action_update {
   $self->create_or_update;
 }
 
+sub action_delete {
+  my ($self) = @_;
+
+  # allow deletion of unused tax zones. Will fail, due to database
+  # constraints, if tax zone is used anywhere
+
+  my $db = $self->{config}->db;
+  $db->do_transaction(sub {
+        my $taxzone_charts = SL::DB::Manager::TaxzoneChart->get_all(where => [ taxzone_id => $self->config->id ]);
+        foreach my $taxzonechart ( @{$taxzone_charts} ) { $taxzonechart->delete };
+        $self->config->delete();
+        flash_later('info',  $::locale->text('The tax zone has been deleted.'));
+  }) || flash_later('error', $::locale->text('The tax zone is in use and cannot be deleted.'));
+
+  $self->redirect_to(action => 'list');
+
+}
+
 sub action_reorder {
   my ($self) = @_;
 
@@ -100,35 +115,54 @@ sub create_or_update {
   my $is_new = !$self->config->id;
 
   my $params = delete($::form->{config}) || { };
+
   delete $params->{id};
 
-  $self->config->assign_attributes(%{ $params });
+  my @errors;
+
+  my $db = $self->config->db;
+  $db->do_transaction( sub {
+
+    # always allow editing of description and obsolete
+    $self->config->assign_attributes( %{$params} ) ;
+
+    push(@errors, $self->config->validate); # check for description
+
+    if (@errors) {
+      die @errors . "\n";
+    };
 
-  my @errors = $self->config->validate;
+    $self->config->save;
 
-  if (@errors) {
-    flash('error', @errors);
-    $self->show_form(title => $is_new ? t8('Add taxzone') : t8('Edit taxzone'));
-    return;
-  }
+    if ( $is_new or $self->config->orphaned ) {
+      # Save taxzone_charts
+      my $buchungsgruppen = SL::DB::Manager::Buchungsgruppe->get_all_sorted();
 
-  $self->config->save;
-  $self->config->obsolete($::form->{"obsolete"});
+      foreach my $bg (@{ $buchungsgruppen }) {
+        my $income_accno_id  = $::form->{"income_accno_id_"  . $bg->id};
+        my $expense_accno_id = $::form->{"expense_accno_id_" . $bg->id};
 
-  #Save taxzone_charts for new taxzones:
-  if ($is_new) {
-    my $buchungsgruppen = SL::DB::Manager::Buchungsgruppe->get_all_sorted();
+        my ($income_accno, $expense_accno);
+        $income_accno  = SL::DB::Manager::Chart->find_by( id => $income_accno_id )  if $income_accno_id;
+        $expense_accno = SL::DB::Manager::Chart->find_by( id => $expense_accno_id ) if $expense_accno_id;
 
-    foreach my $bg (@{ $buchungsgruppen }) {
-      my $taxzone_chart = SL::DB::Manager::TaxzoneChart->find_by_or_create(buchungsgruppen_id => $bg->id, taxzone_id => $self->config->id);
+        push(@errors, t8('Buchungsgruppe #1 needs a valid income account' , $bg->description)) unless $income_accno;
+        push(@errors, t8('Buchungsgruppe #1 needs a valid expense account', $bg->description)) unless $expense_accno;
 
-      $taxzone_chart->taxzone_id($self->config->id);
-      $taxzone_chart->buchungsgruppen_id($bg->id);
-      $taxzone_chart->income_accno_id($::form->{"income_accno_id_" . $bg->id});
-      $taxzone_chart->expense_accno_id($::form->{"expense_accno_id_" . $bg->id});
-      $taxzone_chart->save;
+        my $taxzone_chart = SL::DB::Manager::TaxzoneChart->find_by_or_create(buchungsgruppen_id => $bg->id, taxzone_id => $self->config->id);
+        # if taxzonechart doesn't exist an empty new TaxzoneChart object is
+        # created by find_by_or_create, so we have to assign buchungsgruppe and
+        # taxzone again for the new case to work
+        $taxzone_chart->taxzone_id($self->config->id);
+        $taxzone_chart->buchungsgruppen_id($bg->id);
+        $taxzone_chart->income_accno_id($income_accno->id);
+        $taxzone_chart->expense_accno_id($expense_accno->id);
+        $taxzone_chart->save;
+      }
     }
-  }
+  } ) || die @errors ? join("\n", @errors) . "\n" : $db->error . "\n";
+         # die with rollback of taxzone save if saving of any of the taxzone_charts fails
+         # only show the $db->error if we haven't already identified the likely error ourselves
 
   flash_later('info', $is_new ? t8('The taxzone has been created.') : t8('The taxzone has been saved.'));
   $self->redirect_to(action => 'list');
index ad96ee259960f419f5694ecb72587dc276e412f8..6545d08545d91a7d83241401af3913d054603f90 100644 (file)
@@ -23,4 +23,18 @@ sub validate {
   return @errors;
 }
 
+sub orphaned {
+  my ($self) = @_;
+  die 'not an accessor' if @_ > 1;
+
+  my @classes = qw(Customer Vendor Invoice Order DeliveryOrder PurchaseInvoice);
+  foreach my $class ( @classes ) {
+    my $module = 'SL::DB::' . $class;
+    eval "require $module";
+    my $manager = 'SL::DB::Manager::' . $class;
+    return 0 if $manager->get_all_count( query  => [ taxzone_id => $self->id ] );
+  };
+  return 1;
+}
+
 1;
index 2c0905f52a1fa706b63aac014535eb9cdfc59c06..50018d8a7a4159f71040832633fac280715b6ad9 100755 (executable)
@@ -416,6 +416,8 @@ $self->{texts} = {
   'Break up the update and contact a service provider.' => 'Diese Option bricht das Update ab. Bitte kontaktieren Sie Ihren Administrator oder beauftragen einen Dienstleister.',
   'Buchungsdatum'               => 'Buchungsdatum',
   'Buchungsgruppe'              => 'Buchungsgruppe',
+  'Buchungsgruppe #1 needs a valid expense account' => 'Buchungsgruppe #1 braucht ein gültiges Aufwandskonto',
+  'Buchungsgruppe #1 needs a valid income account' => 'Buchungsgruppe #1 braucht ein gültiges Erfolgskonto',
   'Buchungsgruppe (database ID)' => 'Buchungsgruppe (Datenbank-ID)',
   'Buchungsgruppe (name)'       => 'Buchungsgruppe (Name)',
   'Buchungsgruppen'             => 'Buchungsgruppen',
@@ -2807,6 +2809,8 @@ $self->{texts} = {
   'The task server is not running.' => 'Der Task-Server läuft nicht.',
   'The task server was started successfully.' => 'Der Task-Server wurde erfolgreich gestartet.',
   'The task server was stopped successfully.' => 'Der Task-Server wurde erfolgreich beendet.',
+  'The tax zone has been deleted.' => 'Die Steuerzone wurde gelöscht.',
+  'The tax zone is in use and cannot be deleted.' => 'Die Steuerzone wird benutzt und kann nicht gelöscht werden',
   'The taxzone has been created.' => 'Die Steuerzone wurde erstellt.',
   'The taxzone has been saved.' => 'Die Steuerzone wurde gespeichert.',
   'The third way is to download the module from the above mentioned URL and to install the module manually following the installations instructions contained in the source archive.' => 'Die dritte Variante besteht darin, das Paket von der oben genannten URL herunterzuladen und es manuell zu installieren. Beachten Sie dabei die im Paket enthaltenen Installationsanweisungen.',
index bce8371f470a72c7bda64eb7624095cf8bbf0d32..b12739962742821d2e73a3de11ca2255ab4a96d8 100644 (file)
 [%- FOREACH bg = BUCHUNGSGRUPPEN %]
   <tr>
     <th align="right">[% 'Revenue' | $T8 %] [% HTML.escape(bg.description) %]</th>
-    [%- IF SELF.config.id %]
-    <td>[% CHARTLIST.${bg.id}.income_accno %] -- [% CHARTLIST.${bg.id}.income_accno_description %]</td>
-    [%- ELSE %]
+    [%- IF NOT SELF.config.id %]
     <td>[% L.chart_picker('income_accno_id_' _ bg.id, SELF.defaults.income_accno_id, choose=1, type='IC_income,IC_sale', style=style) %]</td>
+    [%- ELSIF SELF.config.id AND SELF.config.orphaned %]
+    <td>[% L.chart_picker('income_accno_id_' _ bg.id, CHARTLIST.${bg.id}.income_accno_id, choose=1, type='IC_income,IC_sale', style=style) %]</td>
+    [%- ELSE %]
+    <td>[% CHARTLIST.${bg.id}.income_accno %] -- [% CHARTLIST.${bg.id}.income_accno_description %]</td>
     [%- END %]
   </tr>
   <tr>
     <th align="right">[% 'Expense' | $T8 %] [% HTML.escape(bg.description) %]</th>
-    [%- IF SELF.config.id %]
-    <td>[% CHARTLIST.${bg.id}.expense_accno %] -- [% CHARTLIST.${bg.id}.expense_accno_description %]</td>
-    [%- ELSE %]
+    [%- IF NOT SELF.config.id %]
     <td>[% L.chart_picker('expense_accno_id_' _ bg.id, SELF.defaults.expense_accno_id, choose=1, type='IC_expense,IC_cogs', style=style) %]</td>
+    [%- ELSIF SELF.config.id AND SELF.config.orphaned %]
+    <td>[% L.chart_picker('expense_accno_id_' _ bg.id, CHARTLIST.${bg.id}.expense_accno_id, choose=1, type='IC_expense,IC_cogs', style=style) %]</td>
+    [%- ELSE %]
+    <td>[% CHARTLIST.${bg.id}.expense_accno %] -- [% CHARTLIST.${bg.id}.expense_accno_description %]</td>
     [%- END %]
   </tr>
 [%- END %]
@@ -34,6 +38,9 @@
  <p>
   [% L.hidden_tag("action", "Taxzones/dispatch") %]
   [% L.submit_tag("action_" _  (SELF.config.id ? "update" : "create"), LxERP.t8('Save'), onclick="return check_prerequisites();") %]
+  [%- IF SELF.config.id AND SELF.config.orphaned %]
+    [% L.submit_tag("action_delete", LxERP.t8('Delete'), confirm=LxERP.t8('Are you sure?')) %]
+  [%- END %]
   <a href="[% SELF.url_for(action='list') %]">[%- LxERP.t8("Cancel") %]</a>
  </p>