3 use Test::Deep qw(cmp_deeply);
 
   7 use_ok 'Support::TestSetup';
 
   8 use SL::DATEV qw(:CONSTANTS);
 
   9 use SL::Dev::ALL qw(:ALL);
 
  10 use List::Util qw(sum);
 
  11 use SL::DB::Buchungsgruppe;
 
  17 Support::TestSetup::login();
 
  19 my $dbh = SL::DB->client->dbh;
 
  23 my $d = SL::DB::Default->get;
 
  24 $d->update_attributes(datev_export_format => 'cp1252');
 
  26 my $ustid           = 'DE123456788';
 
  27 my $buchungsgruppe7 = SL::DB::Manager::Buchungsgruppe->find_by(description => 'Standard 7%') || die "No accounting group for 7\%";
 
  28 my $date            = DateTime->new(year => 2017, month =>  7, day => 19);
 
  29 my $department      = create_department(description => 'Kästchenweiße heiße Preise');
 
  30 my $project         = create_project(projectnumber => 2017, description => '299');
 
  31 my $bank            = SL::DB::Manager::Chart->find_by(description => 'Bank') || die 'Can\'t find chart "Bank"';
 
  32 my $customer        = new_customer(name => 'Test customer', ustid => $ustid)->save();
 
  33 my $part1 = new_part(partnumber => '19', description => 'Part 19%')->save;
 
  36   description        => 'Part 7%',
 
  37   buchungsgruppen_id => $buchungsgruppe7->id,
 
  40 my $invoice = create_sales_invoice(
 
  46   invoiceitems => [ create_invoice_item(part => $part1, qty =>  3, sellprice => 550),
 
  47                     create_invoice_item(part => $part2, qty => 10, sellprice => 50),
 
  49   department_id    => $department->id,
 
  50   globalproject_id => $project->id,
 
  51   customer_id      => $customer->id,
 
  55 # generate_datev_* doesn't care about encoding but
 
  56 # csv_buchungsexport does! all arabic will be deleted
 
  57 # and no string will be left as invnumber
 
  59 my $datev1 = SL::DATEV->new(
 
  61   trans_id   => $invoice->id,
 
  64 my $startdate = DateTime->new(year => 2017, month =>  1, day =>  1);
 
  65 my $enddate   = DateTime->new(year => 2017, month => 12, day => 31);
 
  66 my $today     = DateTime->new(year => 2017, month =>  3, day => 17);
 
  68 $datev1->from($startdate);
 
  69 $datev1->to($enddate);
 
  71 $datev1->generate_datev_data;
 
  72 $datev1->generate_datev_lines;
 
  74 # check conversion to csv
 
  75 $datev1->from($startdate);
 
  76 $datev1->to($enddate);
 
  77 my ($datev_csv, $die_message);
 
  79   $datev_csv = SL::DATEV::CSV->new(datev_lines  => $datev1->generate_datev_lines,
 
  82                                    locked       => $datev1->locked,
 
  84   my $lines_aref = $datev_csv->lines; # dies only if we assign (do stuff with the data)
 
  89 ok($die_message =~ m/Falscher Feldwert 'ݗݘݰݶ' für Feld 'belegfeld1' bei der Transaktion mit dem Umsatz von/, 'wrong_encoding');
 
  92 $invoice->invnumber('ݗݘݰݶmuh');
 
  95 my $datev3 = SL::DATEV->new(
 
  97   trans_id   => $invoice->id,
 
 100 $datev3->from($startdate);
 
 101 $datev3->to($enddate);
 
 102 $datev3->generate_datev_data;
 
 103 $datev3->generate_datev_lines;
 
 104 my ($datev_csv2, $die_message2);
 
 106   $datev_csv2 = SL::DATEV::CSV->new(datev_lines  => $datev3->generate_datev_lines,
 
 109                                     locked       => $datev3->locked,
 
 111 my $lines_aref = $datev_csv2->lines; # dies only if we assign (do stuff with the data)
 
 118 # redefine invnumber, we have mixed encodings, should still fail
 
 119 ok($die_message2 =~ m/Falscher Feldwert 'ݗݘݰݶmuh' für Feld 'belegfeld1' bei der Transaktion mit dem Umsatz von/, 'mixed_wrong_encoding');
 
 121 # check with good number
 
 122 $invoice->invnumber('meine muh');
 
 125 $invoice->pay_invoice(chart_id      => $bank->id,
 
 126                       amount        => $invoice->open_amount,
 
 127                       transdate     => $invoice->transdate->clone->add(days => 10),
 
 132 my $datev4 = SL::DATEV->new(
 
 134   trans_id   => $invoice->id,
 
 137 $datev4->from($startdate);
 
 138 $datev4->to($enddate);
 
 139 $datev4->generate_datev_data;
 
 140 $datev4->generate_datev_lines;
 
 142 my ($datev_csv4, $die_message3, $lines_aref);
 
 144   $datev_csv4 = SL::DATEV::CSV->new(datev_lines  => $datev4->generate_datev_lines,
 
 147                                     locked       => $datev4->locked,
 
 149   $lines_aref = $datev_csv4->lines; # dies only if we assign (do stuff with the data)
 
 155 ok(!($die_message3), 'no die message');
 
 156 ok(scalar @{ $datev_csv4->warnings } == 0, 'no warnings');
 
 159 note('testing invoice without deliverydate');
 
 160 my @sorted =  sort { $a->[0] cmp $b->[0] } @{ $lines_aref }; # sort by string-comparison of amount
 
 161 cmp_deeply $sorted[0],
 
 162            [ '1963,5', 'S', 'EUR', '', '', '',
 
 163              '1400', '8400', '', '1907', 'meine muh',
 
 164              '', '', 'Test customer', '', '', '', '', '', '',
 
 165              '', '', '', '', '', '', '', '', '',
 
 166              '', '', '', '', '', '', '', "K\x{e4}stchen",
 
 167              '299', '', $ustid, '', '', '',
 
 168              '', '', '', '', '', '', '', '', '',
 
 169              '', '', '', '', '', '', '', '', '',
 
 170              '', '', '', '', '', '', '', '', '',
 
 171              '', '', '', '', '', '', '', '', '',
 
 172              '', '', '', '', '', '', '', '', '',
 
 173              '', '', '', '', '', '', '', '', '',
 
 174              '', '', '', '', '', '', '', '', '',
 
 175              '', '', '', '', '', '', '', '1', '',
 
 178            'invoice without deliverydate 19% tax export ok';
 
 179 cmp_deeply $sorted[2],
 
 180            [ '535', 'S', 'EUR', '', '', '',
 
 181              '1400', '8300', '', '1907','meine muh',
 
 182              '', '', 'Test customer', '', '', '', '', '', '',
 
 183              '', '', '', '', '', '', '', '', '',
 
 184              '', '', '', '', '', '', '', "K\x{e4}stchen",
 
 185              '299', '', $ustid, '', '', '',
 
 186              '', '', '', '', '', '', '', '', '',
 
 187              '', '', '', '', '', '', '', '', '',
 
 188              '', '', '', '', '', '', '', '', '',
 
 189              '', '', '', '', '', '', '', '', '',
 
 190              '', '', '', '', '', '', '', '', '',
 
 191              '', '', '', '', '', '', '', '', '',
 
 192              '', '', '', '', '', '', '', '', '',
 
 193              '', '', '', '', '', '', '', '1', '',
 
 196            'invoice without deliverydate 16% tax export ok';
 
 197 cmp_deeply $sorted[1],
 
 198            [ '2498,5', 'S', 'EUR', '', '', '',
 
 199              '1200', '1400', '', '2907','meine muh',
 
 200              '', '', 'Test customer', '', '', '', '', '', '',
 
 201              '', '', '', '', '', '', '', '', '',
 
 202              '', '', '', '', '', '', '', "K\x{e4}stchen",
 
 203              '299', '', $ustid, '', '', '',
 
 204              '', '', '', '', '', '', '', '', '',
 
 205              '', '', '', '', '', '', '', '', '',
 
 206              '', '', '', '', '', '', '', '', '',
 
 207              '', '', '', '', '', '', '', '', '',
 
 208              '', '', '', '', '', '', '', '', '',
 
 209              '', '', '', '', '', '', '', '', '',
 
 210              '', '', '', '', '', '', '', '', '',
 
 211              '', '', '', '', '', '', '', '1', '',
 
 214            'invoice without deliverydate payment export ok';
 
 216 # create one haben buchung with GLTransaction today
 
 218 my $expense_chart = SL::DB::Manager::Chart->find_by(accno => '4660'); # Reisekosten
 
 219 my $cash_chart    = SL::DB::Manager::Chart->find_by(accno => '1000'); # Kasse
 
 221 note('testing gl transaction without deliverydate');
 
 222 my $gl_transaction = create_gl_transaction(
 
 223   reference      => "Reise März 2018",
 
 224   description    => "Reisekosten März 2018 / Ma Schmidt",
 
 230                         chart  => $expense_chart,
 
 232                         debit  => 100, # net 84.03
 
 235                         chart  => $cash_chart,
 
 242 my $datev2 = SL::DATEV->new(
 
 244   trans_id   => $gl_transaction->id,
 
 247 $datev2->from($startdate);
 
 248 $datev2->to($enddate);
 
 249 $datev2->generate_datev_data;
 
 251 my $datev_csv3  = SL::DATEV::CSV->new(datev_lines  => $datev2->generate_datev_lines,
 
 254                                       locked       => $datev2->locked,
 
 257 my @data_csv    = sort { $a->[0] cmp $b->[0] } @{ $datev_csv3->lines };
 
 258 cmp_deeply($data_csv[0],
 
 259            [ '100', 'S', 'EUR', '', '', '', '4660', '1000', 9, '1703', 'Reise März 2',
 
 260              '', '', 'Reisekosten März 2018 / Ma Schmidt', '', '', '', '', '', '', '', '',
 
 261              '', '', '', '', '', '', '', '', '', '', '', '', '',
 
 262              '', '', '', '', '', '', '', '', '', '', '',
 
 263              '', '', '', '', '', '', '', '', '', '', '', '', '',
 
 264              '', '', '', '', '', '', '', '', '', '', '', '', '',
 
 265              '', '', '', '', '', '', '', '', '', '', '', '', '',
 
 266              '', '', '', '', '', '', '', '', '', '', '', '', '',
 
 267              '', '', '', '', '', '', '', '', '', '', '', '', '',
 
 268              '', '', '1', '', '', '', '', '', '',
 
 270            'gl datev export without delivery date ok');
 
 273 note('testing same invoice, but with deliverydate');
 
 274 # 8400 and 8300 should have deliverydate in datev, payment should not
 
 275 $invoice->deliverydate(DateTime->new(year => 2017, month =>  7, day => 18));
 
 278 $datev1 = SL::DATEV->new(
 
 280   trans_id   => $invoice->id,
 
 283 $datev1->from($startdate);
 
 284 $datev1->to($enddate);
 
 285 $datev1->generate_datev_data;
 
 286 $datev1->generate_datev_lines;
 
 288 $datev_csv = SL::DATEV::CSV->new(datev_lines  => $datev1->generate_datev_lines,
 
 291                                  locked       => $datev1->locked,
 
 293 @sorted    = sort { $a->[0] cmp $b->[0] } @{ $datev_csv->lines };
 
 294 cmp_deeply $sorted[0],
 
 295            [ '1963,5', 'S', 'EUR', '', '', '',
 
 296              '1400', '8400', '', '1907', 'meine muh',
 
 297              '', '', 'Test customer', '', '', '', '', '', '',
 
 298              '', '', '', '', '', '', '', '', '',
 
 299              '', '', '', '', '', '', '', "K\x{e4}stchen",
 
 300              '299', '', $ustid, '', '', '',
 
 301              '', '', '', '', '', '', '', '', '',
 
 302              '', '', '', '', '', '', '', '', '',
 
 303              '', '', '', '', '', '', '', '', '',
 
 304              '', '', '', '', '', '', '', '', '',
 
 305              '', '', '', '', '', '', '', '', '',
 
 306              '', '', '', '', '', '', '', '', '',
 
 307              '', '', '', '', '', '', '', '', '',
 
 308              '', '', '', '', '', '', '', '1', '18072017',
 
 311            'invoice with deliverydate 19% tax export ok';
 
 313 cmp_deeply $sorted[2],
 
 314            [ '535', 'S', 'EUR', '', '', '',
 
 315              '1400', '8300', '', '1907','meine muh',
 
 316              '', '', 'Test customer', '', '', '', '', '', '',
 
 317              '', '', '', '', '', '', '', '', '',
 
 318              '', '', '', '', '', '', '', "K\x{e4}stchen",
 
 319              '299', '', $ustid, '', '', '',
 
 320              '', '', '', '', '', '', '', '', '',
 
 321              '', '', '', '', '', '', '', '', '',
 
 322              '', '', '', '', '', '', '', '', '',
 
 323              '', '', '', '', '', '', '', '', '',
 
 324              '', '', '', '', '', '', '', '', '',
 
 325              '', '', '', '', '', '', '', '', '',
 
 326              '', '', '', '', '', '', '', '', '',
 
 327              '', '', '', '', '', '', '', '1', '18072017',
 
 330            'invoice with deliverydate 16% tax export ok';
 
 332 cmp_deeply $sorted[1],
 
 333            [ '2498,5', 'S', 'EUR', '', '', '',
 
 334              '1200', '1400', '', '2907','meine muh',
 
 335              '', '', 'Test customer', '', '', '', '', '', '',
 
 336              '', '', '', '', '', '', '', '', '',
 
 337              '', '', '', '', '', '', '', "K\x{e4}stchen",
 
 338              '299', '', $ustid, '', '', '',
 
 339              '', '', '', '', '', '', '', '', '',
 
 340              '', '', '', '', '', '', '', '', '',
 
 341              '', '', '', '', '', '', '', '', '',
 
 342              '', '', '', '', '', '', '', '', '',
 
 343              '', '', '', '', '', '', '', '', '',
 
 344              '', '', '', '', '', '', '', '', '',
 
 345              '', '', '', '', '', '', '', '', '',
 
 346              '', '', '', '', '', '', '', '1', '',
 
 349            'invoice with deliverydate payment export ok';
 
 351 note('testing same gl transaction with deliverydate');
 
 352 $gl_transaction->deliverydate(DateTime->new(year => 2017, month =>  7, day => 18));
 
 353 $gl_transaction->save;
 
 355 $datev1 = SL::DATEV->new(
 
 357   trans_id   => $gl_transaction->id,
 
 360 $datev1->from($startdate);
 
 361 $datev1->to($enddate);
 
 362 $datev1->generate_datev_data;
 
 364 $datev_csv   = SL::DATEV::CSV->new(datev_lines  => $datev1->generate_datev_lines,
 
 367                                    locked       => $datev1->locked,
 
 370 @sorted      = sort { $a->[0] cmp $b->[0] } @{ $datev_csv->lines };
 
 371 cmp_deeply($sorted[0],
 
 372            [ '100', 'S', 'EUR', '', '', '', '4660', '1000', 9, '1703', 'Reise März 2',
 
 373              '', '', 'Reisekosten März 2018 / Ma Schmidt', '', '', '', '', '', '', '', '',
 
 374              '', '', '', '', '', '', '', '', '', '', '', '', '',
 
 375              '', '', '', '', '', '', '', '', '', '', '',
 
 376              '', '', '', '', '', '', '', '', '', '', '', '', '',
 
 377              '', '', '', '', '', '', '', '', '', '', '', '', '',
 
 378              '', '', '', '', '', '', '', '', '', '', '', '', '',
 
 379              '', '', '', '', '', '', '', '', '', '', '', '', '',
 
 380              '', '', '', '', '', '', '', '', '', '', '', '', '',
 
 381              '', '', '1', '18072017', '', '', '', '', '',
 
 383           'testing gl transaction with delivery date datev export ok');
 
 385 # TODO warnings are not yet tested
 
 386 # currently most of the valid_checks are senseless because of
 
 387 # the strict input_checks before. Maybe something like encoding mismatch of invnumber,
 
 388 # can be altered to just a warning (not a mandantory field!)
 
 395   SL::DB::Manager::AccTransaction->delete_all( all => 1);
 
 396   SL::DB::Manager::GLTransaction->delete_all(  all => 1);
 
 397   SL::DB::Manager::InvoiceItem->delete_all(    all => 1);
 
 398   SL::DB::Manager::Invoice->delete_all(        all => 1);
 
 399   SL::DB::Manager::Customer->delete_all(       all => 1);
 
 400   SL::DB::Manager::Part->delete_all(           all => 1);
 
 401   SL::DB::Manager::Project->delete_all(        all => 1);
 
 402   SL::DB::Manager::Department->delete_all(     all => 1);
 
 403   SL::DATEV->clean_temporary_directories;