diff --git a/copri4/main/src/Mod/APIfunc.pm b/copri4/main/src/Mod/APIfunc.pm index ef6998d..e766639 100755 --- a/copri4/main/src/Mod/APIfunc.pm +++ b/copri4/main/src/Mod/APIfunc.pm @@ -930,8 +930,7 @@ sub booking_request(){ if($ct_bike->{barcode} && $ct_tariff->{barcode}){ my $ctt = {}; my $rentable_check=0; - $rentable_check = $bw->isuser_rentable($auth,$varenv); - + $rentable_check = $bw->isuser_rentable($auth,$varenv); $bw->log("booking_request isuser_rentable:",$rentable_check,""); if($rentable_check == 2){ @@ -957,7 +956,38 @@ sub booking_request(){ #if invoice exist if($ctt->{c_id}){ - + #if payment-type prepaid, then check whether balance positive + my $sum_balance = 0; + if($auth->{int03} && $auth->{int03} == 3){ + + my $dbh_primary = $dbt->dbconnect_extern($dbt->{primary}->{sharee_primary}->{database}->{dbname}); + my $adref = { + table => "contentadr", + fetch => "one", + c_id => "$auth->{c_id}", + }; + my $auth_prim = $dbt->fetch_tablerecord($dbh_primary,$adref); + + #get prepaid balance, like in users App RentalData + #collects all open (not captured) positions incl. primary-prepaid to get saldo + my ($cttpos,$operator_hash) = $self->user_rentals_history($q,$auth_prim,0,1); + foreach my $id (keys(%$cttpos)){ + if($cttpos->{$id}->{int35} && $cttpos->{$id}->{start_time} && $cttpos->{$id}->{end_time}){ + my $pricing = { total_price => 0 }; + ($pricing, my $counting) = $pri->counting_rental($varenv,$cttpos->{$id}); + $sum_balance += $pricing->{total_price}; + }else{ + my $total_price = 0; + ($total_price,my $rabatt) = $pri->price2calc($cttpos->{$id}); + #prepaid * -1 + $total_price *= -1 if($cttpos->{$id}->{template_id} && $cttpos->{$id}->{template_id} == 219); + $sum_balance += $total_price; + } + } + $bw->log("booking_request prepaid balance sum: $sum_balance, userID: $auth->{c_id} ",$sum_balance,""); + } + #Rental is only permitted if sum_balance <= 0 (in primary prepaid context positive) + if($sum_balance <= 1){ #2 = "requested" $pos_id = $dbt->insert_pos($dbh,$ctt->{c_id},$ct_bike,$ct_station,$auth,$ct_tariff,$now_dt,$bike,"2",$owner,$sig_book); $bw->log("booking_request insert_pos:",$pos_id,""); @@ -1009,6 +1039,10 @@ sub booking_request(){ $response_state="Failure 1007: booking request fails"; $response_text="Entschuldigung, es ist ein Fehler aufgetreten. Bitte kontaktieren Sie unsere hotline damit wir das Problem lösen können"; } + }else{ + $response_state="Failure 1593: rental is prohibited because of prepaid balance - $sum_balance"; + $response_text="Bitte überprüfen Sie Ihren Prepaid/Vorkasse Kontostand, aktuell: - $sum_balance €. Nur bei positiven Kontostand können wir das Mietradsystem für Sie freischalten."; + }#end if $sum_balance } }elsif($rentable_check == 1){ $response_state="Failure 1006: rental is prohibited because of user profil"; @@ -1641,6 +1675,7 @@ sub user_rentals_history(){ my $q = shift || ""; my $auth = shift; my $daily = shift || 0; + my $allop = shift || 0; my %varenv = $cf->envonline(); my $today = strftime("%Y-%m-%d",localtime(time)); @@ -1662,23 +1697,31 @@ sub user_rentals_history(){ my $month = $q->param('month'); $pref->{mtime} = ">=::(now() - interval '$month month')"; }else{ - #2021-06-18, list only postions which are not invoiced (Form Buchungsdaten) - #$pref->{close_time} = "is::null"; - $pref->{'ct.state'} = "is::null"; - $pref->{'ct.int14'} = "is::null"; + #2024-01-08 list not succesfully captured positions by also using ct.int14 >= 1 + $pref->{'ct.state'} = "is::null";# OR ct.int14 >= 1 + #$pref->{'ct.int14'} = "is::null"; } - if($varenv{dbname} eq $dbt->{primary}->{sharee_primary}->{database}->{dbname}){ + if($allop || $varenv{dbname} eq $dbt->{primary}->{sharee_primary}->{database}->{dbname}){ + #$bw->log("user_rentals_history userID: $auth->{c_id} with operators",$auth->{txt17},""); + if($auth->{txt17}){ if($auth->{txt17} =~ /\w\s\w/){ %operator_hash = map { $_ => "$dbt->{operator}{$_}->{operatorApp}" } split(/\s+/,$auth->{txt17}); }else{ $operator_hash{$auth->{txt17}} = "$dbt->{operator}{$auth->{txt17}}->{operatorApp}"; } + #adding primary to get prepaid + #$operator_hash{sharee_primary} = "$dbt->{primary}{sharee_primary}->{primaryApp}"; + foreach my $sharee_operator (keys (%operator_hash)){ - my $dbh_operator = $dbt->dbconnect_extern("$sharee_operator"); - my $cttpos = $dbt->collect_post($dbh_operator,$pref); - $record_all = { %$record_all, %$cttpos }; + #$bw->log("operator_hash sharee_operator: $sharee_operator",$sharee_operator,""); + my $dbh_operator = ""; + $dbh_operator = $dbt->dbconnect_extern("$sharee_operator"); + if($dbh_operator){ + my $cttpos = $dbt->collect_post($dbh_operator,$pref); + $record_all = { %$record_all, %$cttpos }; + } } } }else{ @@ -1892,7 +1935,7 @@ sub bikes_available(){ #return list of occupied/requested bikes my $adjust_freedtime = 0; my $further_freedtime_available = 1; - my ($cttpos,$operator_hash) = $self->user_rentals_history($q,$auth,1); + my ($cttpos,$operator_hash) = $self->user_rentals_history($q,$auth,1,0); foreach my $id (sort { lc($cttpos->{$b}->{itime}) cmp lc($cttpos->{$a}->{itime}) } keys(%$cttpos)){ $further_freedtime_available = $pri->count_freedrental("rentals by bikes_available",$varenv,$auth->{c_id},$cttpos->{$id},$adjust_freedtime); } @@ -2291,12 +2334,15 @@ sub stations_available(){ $record->{$id}->{txt06} =~ s/\s//g if($record->{$id}->{txt06}); if($record->{$id}->{txt06} && $record->{$id}->{txt06} =~ /\d+\.\d+\,\d+\.\d+/){ my $bike_count = 0; + my @bike_ids = (); foreach my $b_id (keys (%$record_bikes)){ if($record->{$id}->{int04} == $record_bikes->{$b_id}->{int04}){ + push @bike_ids,$dbt->{operator}->{$varenv->{dbname}}->{oprefix} . $record_bikes->{$b_id}->{barcode}; $bike_count++; } } $return->{$id}->{bike_count} = "$bike_count"; + $return->{$id}->{bike_ids} = [@bike_ids]; $return->{$id}->{authed} = "$authed"; $return->{$id}->{capacity} = "$record->{$id}->{int05}" || "1"; @@ -2911,7 +2957,7 @@ sub auth_verify(){ #first, save operator array which are used my %operator_hash = ();#local DB - #$bw->log("booking_request auth_verified by dbname $varenv{dbname}",$auth_primary->{c_id},""); + $bw->log("booking_request auth_verified by dbname $varenv{dbname}",$auth_primary->{c_id},""); print FILE "booking_request auth_verified by dbname $varenv{dbname} | pri $auth_primary->{c_id}\n" if($debug); if($auth_primary->{txt17} && $auth_primary->{txt17} =~ /\w\s\w/){#append DB's @@ -2940,7 +2986,7 @@ sub auth_verify(){ $update_primary->{txt26} = $q->escapeHTML($user_agent) if($user_agent); } - #check prepaid account + #first prepaid account check (not save because without rental history) if($auth_primary->{int03} == 3){ my $prepaidhash = { prepaid_total => 0 }; $prepaidhash = $pri->collect_prepaid($dbh_primary,$auth_primary) if($auth_primary->{c_id}); @@ -2948,6 +2994,7 @@ sub auth_verify(){ my $vde = $auth_primary->{int12} || 1; $update_primary->{int12} = $vde; } + $bw->log("auth_verify booking_request prepaid check",$update_primary,""); } my $rows = $dbt->update_record($dbh_primary,$update_primary,$auth_primary); diff --git a/copri4/main/src/Mod/APIjsonserver.pm b/copri4/main/src/Mod/APIjsonserver.pm index 855abfa..4a555b3 100755 --- a/copri4/main/src/Mod/APIjsonserver.pm +++ b/copri4/main/src/Mod/APIjsonserver.pm @@ -71,7 +71,7 @@ my $response = { apiserver => "$apiserver", response => "$respreq", uri_primary => "$dbt->{primary}->{sharee_primary}->{primaryApp}", - copri_version => "4.1.23.23", + copri_version => "4.1.23.24", user_id => "", authcookie => "", new_authcoo => "0", diff --git a/copri4/main/src/Mod/APIpayone.pm b/copri4/main/src/Mod/APIpayone.pm index 52ef0f9..7a12d32 100755 --- a/copri4/main/src/Mod/APIpayone.pm +++ b/copri4/main/src/Mod/APIpayone.pm @@ -21,7 +21,6 @@ use XML::Simple qw(:strict); use Lib::Config; use Mod::DBtank; use Mod::Basework; -use Mod::Shareework; use Mod::APIfunc; use Data::Dumper; use Sys::Hostname; @@ -35,7 +34,6 @@ sub handler { my $cf = new Config; my $dbt = new DBtank; my $bw = new Basework; - my $tk = new Shareework; my $apif = new APIfunc; my %varenv = $cf->envonline(); @@ -46,6 +44,8 @@ sub handler { my $user_agent = $q->user_agent(); my $dbh = ""; + $bw->log("APIpayone request:\n--> user-agent '$user_agent'",$q,""); + if(1==1){ foreach(@keywords){ if(length($_) > 40 || length($q->param($_)) > 400){ @@ -56,7 +56,6 @@ sub handler { } } - $bw->log("APIpayone request:\n--> user-agent '$user_agent'",$q,""); print $q->header( -charset => 'ISO-8859-1' ); print "TSOK"; @@ -73,10 +72,54 @@ sub handler { my $update_adr = { table => "contentadr", - pay_time => "now()", - #owner => $owner + pay_time => "now()",#just to see who changes at what time }; + + #primary payonelink prepaid transaction-status + #TODO live tests if aid matches + if($q->param('aid') eq "55218"){ + print FILE "TeilRad payonelink transaction on $dbt->{primary}->{sharee_primary}->{database}->{dbname}\n"; + + my $update_pos = { + table => "contenttranspos", + mtime => "now()", + owner_end => $owner, + }; + my $pos_id = ""; + + foreach(@keywords){ + my $val = $q->param($_); + $val = $q->escapeHTML("$val"); + print FILE "$_=$val\n"; + + #reference keeps ct_id-pos_id + if($_ eq "reference" && $val =~ /\d+-(\d+)/){ + $pos_id = $1; + }elsif($_ eq "txid"){ + $update_pos->{txt15} = $val; + }elsif($_ eq "receivable"){ + $update_pos->{int02} = $val; + } + } + + if($q->param('txaction') eq "paid"){ + $dbh = $dbt->dbconnect_extern($dbt->{primary}->{sharee_primary}->{database}->{dbname}); + my $fetch_ctpos = { + table => "contenttranspos", + fetch => "one", + c_id => $pos_id, + }; + my $ctpos = { c_id => 0 }; + $ctpos = $dbt->fetch_tablerecord($dbh,$fetch_ctpos) if($pos_id); + + $dbt->update_record($dbh,$update_pos,$ctpos) if($ctpos->{c_id}); + print FILE Dumper($update_pos) . "\n"; + } + } + #operator invoice transaction-status + else{ + my $update_ctt = { table => "contenttrans", mtime => "now()", @@ -169,13 +212,14 @@ sub handler { if(($update_adr->{int24} && $update_adr->{int24} > 0 || $ctadr->{int12} ne $update_adr->{int12}) && $ctadr->{c_id} > 0){ $dbt->update_record($dbh,$update_adr,$ctadr); #update adr also on primary - my $dbh_primary = $dbt->dbconnect($dbt->{primary}->{sharee_primary}->{database}->{dbname}); + my $dbh_primary = $dbt->dbconnect_extern($dbt->{primary}->{sharee_primary}->{database}->{dbname}); $dbt->update_record($dbh_primary,$update_adr,$ctadr); print FILE Dumper($update_adr) . "\n"; } } } - + } + close(FILE); return Apache2::Const::OK; diff --git a/copri4/main/src/Mod/APIshareeio.pm b/copri4/main/src/Mod/APIshareeio.pm index e13f58c..5038873 100755 --- a/copri4/main/src/Mod/APIshareeio.pm +++ b/copri4/main/src/Mod/APIshareeio.pm @@ -3,7 +3,7 @@ package Mod::APIshareeio; # SPDX-License-Identifier: AGPL-3.0-or-later # Copyright (c) Rainer Gümpelein, TeilRad GmbH # -#use lib qw(/var/www/copri-bike/shareeapp-sx/src); +#use lib qw(/var/www/copri-bike/shareeapp-primary/src); # use warnings; use strict; @@ -22,6 +22,7 @@ use Mod::DBtank; use Mod::Basework; use Mod::Shareework; use Mod::APIfunc; +use Mod::Pricing; use Data::Dumper; sub handler { @@ -58,6 +59,7 @@ sub handler { open(FILE,">>$varenv{logdir}/APIshareeio.log") if($debug); print FILE "\n*** $now_dt user-agent: '$user_agent' to syshost: $varenv{syshost}\n" if($debug); + print FILE "headers:\n" . Dumper(\%headers) . "\n" if($debug); print FILE "<=== DUMP query\n " . Dumper($q) . "\n" if($debug); print FILE "<=== DUMP postdata:\n " . Dumper($q->param('POSTDATA')) . "\n" if($debug); @@ -78,7 +80,7 @@ sub handler { } foreach(@keywords){ - if(length($_) > 40 || length($q->param($_)) > 400){ + if(length($_) > 40 || length($q->param($_)) > 900){ $response->{response_state} = "Failure 9000: amount of characters in $_ exceeds"; $bw->log("Failure 9000: amount of characters in $_ exceeds",$q,""); my $jrout = $json->pretty->encode({shareeio => $response}); @@ -88,10 +90,154 @@ sub handler { } } - -#sig booking_update +#main +my $POSTDATA = $q->param('POSTDATA'); my $response_out = {}; -$response_out = sig_booking_update($q,\%varenv,$response,$aowner);# sig json post +eval { + my $response_in = {}; + $response_in = decode_json($POSTDATA) if($POSTDATA); + if($response_in->{data}->{rentalId}){ + $response_out = sig_booking_update($q,\%varenv,$response,$aowner);#sig json post + } + #operator invoice capture request + if($response_in->{request} eq "capture_prepaid"){ + $response = { + request => "$response_in->{request}", + response_state => "Init", + sum_paid => "0", + sum_prepaid_available => "0", + }; + $response_out = srv_capture_prepaid($q,\%varenv,$response,$response_in,$aowner); + } + #operator payment balance alias p-saldo @all request + if($response_in->{request} eq "collect_prepaid_invoices"){ + $response = { + request => "$response_in->{request}", + response_state => "Init", + }; + $response_out = srv_collect_prepaid_invoices($q,\%varenv,$response,$response_in,$aowner); + } +}; +if ($@){ + print FILE "failure! can not decode POST json, POSTDATA:\n" . Dumper($q->param('POSTDATA')) . "\n" if($debug); + #warn $@; + print FILE "warn:" . $@ . "\n" if($debug); + $response_out->{response_state} = "Failure: can not decode POST json"; +} +#end main eval + + +#sharee collect prepaid json api +sub srv_collect_prepaid_invoices { + my $q = shift; + my $varenv = shift; + my $response = shift || {}; + my $response_in = shift || {}; + my $aowner = shift || ""; + + my $dbt = new DBtank; + my $apif = new APIfunc; + my $pri = new Pricing; + my $dbh = ""; + + my $pref_ctt = { + table => "contenttrans", + fetch => "all", + keyfield => "int10",#userID + main_id => 300023, + template_id => 219,#prepaid tpl + state => "is::null", + close_time => "is::null", + }; + $response_in->{userID} if($response_in->{userID}); + + my $ctt_prepaid = { }; + $ctt_prepaid = $dbt->fetch_record($dbh,$pref_ctt); + + foreach my $id (sort { $ctt_prepaid->{$a}->{c_id} <=> $ctt_prepaid->{$b}->{c_id} } keys (%$ctt_prepaid)){ + my $ctadr = { c_id => $ctt_prepaid->{$id}->{int10} }; + my $sum_prepaid_available = 0; + $sum_prepaid_available = $pri->primary_sum_prepaid($dbh,$ctadr,$ctt_prepaid); + $response->{users_prepaid_invoices}->{$id}->{invoiceID} = "$ctt_prepaid->{$id}->{c_id}"; + $response->{users_prepaid_invoices}->{$id}->{userID} = "$ctt_prepaid->{$id}->{int10}"; + $response->{users_prepaid_invoices}->{$id}->{sum_prepaid_available} = "$sum_prepaid_available"; + } + $response->{response_state} = "Success: collect_prepaid_invoives"; + + return $response; +}#end collect_prepaid_invoices + + +#sharee capture payment json api +#host must be shareeapp-primary.copri..... +sub srv_capture_prepaid { + my $q = shift; + my $varenv = shift; + my $response = shift || {}; + my $response_in = shift || {}; + my $aowner = shift || ""; + + my $dbt = new DBtank; + my $apif = new APIfunc; + my $pri = new Pricing; + my $dbh = ""; + my $debug=1; + + if(looks_like_number($response_in->{userID}) && looks_like_number($response_in->{sum_paid})){ + my $ctadr = { c_id => $response_in->{userID} }; + my $invoice_reference = $q->escapeHTML($response_in->{invoice_reference}) || "error"; + my $pref_ctt = { + table => "contenttrans", + fetch => "one", + main_id => 300023, + template_id => 219,#prepaid tpl + int10 => "$ctadr->{c_id}", + state => "is::null", + close_time => "is::null", + }; + my $ctt_prepaid = { c_id => 0 }; + $ctt_prepaid = $dbt->fetch_record($dbh,$pref_ctt); + + if($ctt_prepaid->{c_id} > 0){ + my $sum_prepaid_available = 0; + $sum_prepaid_available = $pri->primary_sum_prepaid($dbh,$ctadr,$ctt_prepaid); + $response->{sum_prepaid_available} = "$sum_prepaid_available"; + + if($sum_prepaid_available >= $response_in->{sum_paid}){ + #pseudo part. not available in content + my $ct = { + c_id => 0, + barcode => 0, + ca_id => $ctadr->{c_id}, + ct_id => $ctt_prepaid->{c_id}, + int02 => "-$response_in->{sum_paid}", + txt01 => 'Operator prepaid capture', + int16 => 5,#fibumark for operator prepaid capture + template_id => 219, + }; + + #Gegenbuchung + my $cttpos = { c_id => 0 }; + $cttpos->{c_id} = $dbt->insert_pos($dbh,$ctt_prepaid->{c_id},$ct,"",$ctadr,"","","$invoice_reference","0",$aowner,""); + if($cttpos->{c_id}){ + $response->{sum_paid} = "$response_in->{sum_paid}"; + $response->{response_state} = "Success: Prepaid capture ID $invoice_reference"; + }else{ + $response->{response_state} = "Failure: Prepaid capture"; + } + }else{ + $response->{response_state} = "Failure: Users Prepaid-Account not funded"; + } + }else{ + $response->{response_state} = "Failure: no Prepaid-Invoice available"; + } + }else{ + $response->{response_state} = "Failure: no userID defined"; + } + + return $response; +}#end capture_prepaid + #sig json api sub sig_booking_update { diff --git a/copri4/main/src/Mod/DBtank.pm b/copri4/main/src/Mod/DBtank.pm index a3ae116..bf7e043 100755 --- a/copri4/main/src/Mod/DBtank.pm +++ b/copri4/main/src/Mod/DBtank.pm @@ -66,7 +66,6 @@ sub dbconnect_extern { #$bw->log("dbconnect_extern call with instance_type:$instance_type and copri_instance:",$dbname,""); #keep in mind, only one DB can be returned by this way - #while (my ($key, $value) = each %{ $self->{$instance_type} }) { while (my ($key, $value) = each %{ $globalconf{$instance_type} }) { if($key eq $dbname){ $bw->log("dbconnect_XX",$value->{database}->{dbname},""); @@ -686,7 +685,7 @@ sub collect_post(){ } }elsif($key =~ /ct\.close_time|ct\.state|ct\.int14/ && $value){#used to get open invoices if($key =~ /ct\.state/ && $value eq "null"){ - $ct_where .= " and ($key $op $value OR $key = '')"; + $ct_where .= " and ($key $op $value OR $key = '' OR ct.int14 >= 1)"; }else{ $ct_where .= " and $key $op $value"; } @@ -1624,7 +1623,7 @@ sub insert_contenttrans(){ $doc_name = "Prepaid Account" if($tpl_id == 219); $owner="199" if(!$owner); #keep in mind int10 will be mainly used by Prelogic and Printpreview, thats because we save it also - my $sth = $dbh->prepare("INSERT INTO contenttrans (ct_name,txt00,int10,txt02,txt01,txt03,txt06,txt07,txt08,txt10,txt11,owner,itime) VALUES('$invoice_nr','$doc_name','$ctadr->{c_id}','$ctadr->{txt02}','$ctadr->{txt01}','$ctadr->{txt03}','$ctadr->{txt06}','$ctadr->{txt07}','$ctadr->{txt08}','$ctadr->{txt10}','$ctadr->{txt11}','$owner','now()') RETURNING c_id"); + my $sth = $dbh->prepare("INSERT INTO contenttrans (ct_name,txt00,int10,int03,txt02,txt01,txt03,txt06,txt07,txt08,txt10,txt11,owner,itime) VALUES('$invoice_nr','$doc_name','$ctadr->{c_id}','$ctadr->{int03}','$ctadr->{txt02}','$ctadr->{txt01}','$ctadr->{txt03}','$ctadr->{txt06}','$ctadr->{txt07}','$ctadr->{txt08}','$ctadr->{txt10}','$ctadr->{txt11}','$owner','now()') RETURNING c_id"); my $rows = $sth->execute(); my $last_id; diff --git a/copri4/main/src/Mod/Indexsharee.pm b/copri4/main/src/Mod/Indexsharee.pm index cb93069..4235764 100755 --- a/copri4/main/src/Mod/Indexsharee.pm +++ b/copri4/main/src/Mod/Indexsharee.pm @@ -469,7 +469,11 @@ sub handler { } elsif($R::c_id && $R::ct_trans eq "remove_chk4rel"){ my $delete_key = "delete_trans"; - $feedb->{message} = "failure::Datensatz wirklich löschen. ::?ct_trans=$delete_key\&exit_box2=1\&c_id=$R::c_id ::löschen"; + if(looks_like_number($R::tpl_id4trans) && $R::tpl_id4trans == 219){ + $feedb->{message} = "failure::Datensatz löschen ist für Prepaid-Account deaktiviert. Prepaid requests oder payments müssen erhalten bleiben."; + }else{ + $feedb->{message} = "failure::Datensatz wirklich löschen. ::?ct_trans=$delete_key\&exit_box2=1\&c_id=$R::c_id ::löschen"; + } } elsif($R::c_id && $R::ct_trans eq "delete_trans"){ $feedb = $pl->delete_content($node_meta,$R::c_id); @@ -780,7 +784,7 @@ sub handler { #redirections if($users_sharee->{c_id} && ($path =~ /$varenv{mandant}\/$varenv{profile}/ || $path =~ /$varenv{mandant}\/Account/)){ - if($R::sharee_edit =~ /save_account/){ + if($R::sharee_edit && $R::sharee_edit =~ /save_account/){ $returnwww =~ s/::/=/g if($returnwww && $returnwww =~ /success::\w+/); ($api_return,$users_sharee) = $apif->auth_verify($q,$coo,""); $payable_check = $bw->isuser_rentable($users_sharee,\%varenv); @@ -807,7 +811,7 @@ sub handler { exit 0; } elsif($payable_check && $payable_check == 2){ - print redirect("$varenv{wwwhost}/$varenv{mandant}/Account/$varenv{accounting_3}?cum=2-$payable_check$session_and\&$returnwww"); + print redirect("$varenv{wwwhost}/$varenv{mandant}/Account/$varenv{accounting_2}?cum=2-$payable_check$session_and\&$returnwww"); exit 0; } }elsif($path =~ /$varenv{mandant}\/$varenv{profile}/ && $referer !~ /failure=\w/){ diff --git a/copri4/main/src/Mod/Payment.pm b/copri4/main/src/Mod/Payment.pm index f8ce038..d05b787 100755 --- a/copri4/main/src/Mod/Payment.pm +++ b/copri4/main/src/Mod/Payment.pm @@ -10,7 +10,7 @@ use strict; use warnings; use POSIX; use CGI; -use Digest::SHA qw(hmac_sha256_base64); +use Digest::SHA qw(hmac_sha256 hmac_sha256_base64); use JSON; my $json = JSON->new->allow_nonref; use LWP::UserAgent; @@ -18,15 +18,15 @@ use URI::Encode; my $uri_encode = URI::Encode->new( { encode_reserved => 1 } ); use Scalar::Util qw(looks_like_number); use Lib::Config; -use Mod::Callib; use Mod::DBtank; use Mod::Basework; +use Mod::RPCshareeio; use Data::Dumper; my $q = new CGI; my $cf = new Config; -my $cal = new Callib; my $dbt = new DBtank; +my $rpcs = new RPCshareeio; my $bw = new Basework; @@ -55,7 +55,7 @@ sub book_payment { my $now_dt = strftime "%Y-%m-%d %H:%M:%S", localtime; open(EMA, ">> $varenv->{logdir}/book_payment.log"); - print EMA "\n*** $now_dt invoice pdf print c_id4trans:$R::c_id4trans\n" . Dumper($q) . "\n"; + print EMA "\n*** $now_dt book_payment invoice c_id4trans:$R::c_id4trans\n" . Dumper($q) . "\n"; my $pref_ctt = { table => "contenttrans", @@ -65,6 +65,12 @@ sub book_payment { my $ctt = { c_id => 0 }; $ctt = $dbt->fetch_record($dbh,$pref_ctt) if($R::c_id4trans); + my $update_adr = { + table => "contentadr", + mtime => "now()", + owner => $users_dms->{u_id}, + }; + my $update_ctt = { table => "contenttrans", mtime => "now()", @@ -98,12 +104,14 @@ sub book_payment { }; my $ctadr = { c_id => 0 }; $ctadr = $dbt->fetch_tablerecord($dbh,$pref_adr) if($ctt->{int10}); + my $vde_on_fail = $ctadr->{int12} || 1;#keep last or set 1 print EMA "Used adr c_id:$ctadr->{c_id} by ctt.int10: $ctt->{int10}\n"; my $sum_paid = "null"; my $sum_operatorcredit = "null"; my $sumgeb_teil = "null"; my $sumgeb_bank = "null"; + my $sum_prepaid = "null"; my $state = $R::state || ""; $update_ctt->{state} = "$state"; $update_ctt->{int14} = 2;#set OPOS @@ -113,24 +121,27 @@ sub book_payment { $sum_paid =~ s/,/\./; $update_ctt->{int01} = $sum_paid; } - if($R::sum_operatorcredit){ $sum_operatorcredit = $R::sum_operatorcredit; $sum_operatorcredit =~ s/,/\./; $update_ctt->{int02} = $sum_operatorcredit; $update_ctt->{int14} = "null"; } - + if($R::sumgeb_bank){ + $sumgeb_bank = $R::sumgeb_bank; + $sumgeb_bank =~ s/,/\./; + $update_ctt->{int07} = $sumgeb_bank; + } if($R::sumgeb_teil){ $sumgeb_teil = $R::sumgeb_teil; $sumgeb_teil =~ s/,/\./; $update_ctt->{int08} = $sumgeb_teil; } - - if($R::sumgeb_bank){ - $sumgeb_bank = $R::sumgeb_bank; - $sumgeb_bank =~ s/,/\./; - $update_ctt->{int07} = $sumgeb_bank; + #maybe, we don't use it + if($R::sum_prepaid){ + $sum_prepaid = $R::sum_prepaid; + $sum_prepaid =~ s/,/\./; + #$update_ctt->{int09} = $sum_prepaid; } $feedb->{u_rows} = $dbt->update_record($dbh,$update_ctt,$ctt); @@ -187,6 +198,31 @@ sub book_payment { $update_ctt->{pay_time} = "now()"; $feedb->{u_rows} = $dbt->update_record($dbh,$update_ctt,$ctt); } + elsif($state eq "Prepaid" && $ctadr->{c_id}){ + + #APIshareeio APIcall + my $shareeio_json = { + request => "capture_prepaid", + userID => "$ctadr->{c_id}", + sum_paid => "$update_ctt->{int01}", + invoice_reference => "$dbt->{operator}->{$varenv->{dbname}}->{oprefix}-$ctt->{c_id}-$ctt->{ct_name}", + }; + + my $response_in = {}; + $response_in = $rpcs->request_shareeio($varenv,$dbh,$ctadr,$shareeio_json); + if($response_in->{shareeio}->{response_state} =~ /Success/i){ + $update_ctt->{int14} = "null"; + $update_ctt->{pay_time} = "now()"; + $update_adr->{int12} = "null"; + }else{ + $update_adr->{int12} = $vde_on_fail;#Vde + } + $update_ctt->{txt28} = $now_dt . " $state\n" . $response_in->{shareeio}->{response_state} . "\n\n" . $ctt->{txt28}; + $feedb->{u_rows} = $dbt->update_record($dbh,$update_ctt,$ctt); + $dbt->update_record($dbh,$update_adr,$ctadr); + my $dbh_primary = $dbt->dbconnect_extern($dbt->{primary}->{sharee_primary}->{database}->{dbname}); + $dbt->update_record($dbh_primary,$update_adr,$ctadr); + } $ctt = $dbt->fetch_record($dbh,$pref_ctt);#re-read values @@ -931,14 +967,15 @@ sub rpc { print FILE Dumper($update_adr) . "\n" if($debug); #2023-04-11 set it global by update adr also on primary #disabled, because isuser_rentable will be only used by operator rental - #my $dbh_primary = $dbt->dbconnect($dbt->{primary}->{sharee_primary}->{database}->{dbname}); - #$dbt->update_record($dbh_primary,$update_adr,$ctadr); + #2024-01-08 enabled again, also done in APIpayone after payone feedback + my $dbh_primary = $dbt->dbconnect_extern($dbt->{primary}->{sharee_primary}->{database}->{dbname}); + $dbt->update_record($dbh_primary,$update_adr,$ctadr); } $dbt->update_record($dbh,$update_ctt,$ctt) if($ctt->{c_id} > 0); close(FILE) if($debug); return $payoneret; -} +}#end rpc #SEPA PDFGenerator sub pdfmandat { @@ -1091,7 +1128,7 @@ sub payone_capture { return ($retval,$return_text); } -#Request "payone-link" +#request "payone-link" sub generate_payonelink { my $self = shift; my $varenv = shift; @@ -1100,17 +1137,18 @@ sub generate_payonelink { my $prepaid_amount = shift || 0; my $owner = shift || 0; - my $payonelink_conf = $dbt->{payonelink_conf} || {}; my $ret_json = {}; my $response_in = {}; + my $feedb = { message => "" }; my $dbh = ""; my $now_dt = strftime "%Y-%m-%d %H:%M:%S", localtime; open(FILE,">>$varenv->{logdir}/payonelink.log"); print FILE "\n*** $now_dt 'generate_payonelink' ctadr:$ctadr->{c_id}|$ctadr->{txt08}\n"; + $prepaid_amount =~ s/,/\./; my $prepaid_amount2 = 0; - $prepaid_amount2 = $1 if($prepaid_amount =~ /^(\d+)/); + $prepaid_amount2 = $1 if($prepaid_amount =~ /(\d+\.\d{2})/ || $prepaid_amount =~ /(\d+)/); if($ctadr->{c_id} && $prepaidhash->{prepaid_id} && $prepaid_amount2 >= 5){ @@ -1118,94 +1156,123 @@ sub generate_payonelink { (my $firstname,$lastname) = split(/\s+/,$ctadr->{txt01}) if($ctadr->{txt01} =~ /\w\s+\w/i); chomp($firstname); chomp($lastname); - my $city = $ctadr->{txt06}; - (my $zip, $city) = split(/\s+/,$ctadr->{txt06}) if($ctadr->{txt06} =~ /[\w\d]\s+[\w\d]/i); - chomp($zip); - chomp($city); + my $firstName = Encode::encode('utf-8', Encode::decode('iso-8859-1', $firstname)); + my $lastName = Encode::encode('utf-8', Encode::decode('iso-8859-1', $lastname)); + my $email = Encode::encode('utf-8', Encode::decode('iso-8859-1', $ctadr->{txt08})); my $currency = "EUR"; my $amount = 0; $amount = $prepaid_amount2 * 100 if($prepaid_amount2); - my $pay_request = { + my $reference = Encode::encode('utf-8', Encode::decode('iso-8859-1', $prepaidhash->{prepaid_id})); + #my $epoche = time(); + #$reference = "1_$epoche";#For tests generate always new reference! + my $description = Encode::encode('utf-8', Encode::decode('iso-8859-1', $prepaidhash->{description})); + + my $pay_json = { + currency => "$currency", intent => 'authorization', - active => 1, - paymentMethods => ['visa', 'mastercard', 'paypal', 'sofort', 'paydirekt', 'giropay', 'sepa'], - userId => "$ctadr->{c_id}", - email => "$ctadr->{txt08}", - firstName => "$firstname", - lastName => "$lastname", - country => "$ctadr->{txt10}", - language => "de_DE", - reference => "$prepaidhash->{prepaid_id}", + merchantId => "$dbt->{payonelink_conf}->{merchantId}", + accountId => "$dbt->{payonelink_conf}->{accountId}", + portalId => "$dbt->{payonelink_conf}->{portalId}", + userId => "$ctadr->{c_id}", + mode => "$dbt->{payonelink_conf}->{mode}", + notifyUrl => "$dbt->{payonelink_conf}->{notifyUrl}", + description => "Ihr vorbereiteter sharee.bike Prepaid/Vorkasse Auftrag", + paymentMethods => ['visa', 'mastercard', 'giropay', 'sepa'], + reference => "$reference", shoppingCart => [{ - type => "prepaid", + type => "goods", number => "$prepaidhash->{number}", + description => "$description", price => $amount, quantity => 1, - description => "$prepaidhash->{description}", vatRate => 19 - }] + }], + "billing" => { + firstName => "$firstName", + lastName => "$lastName", + email => "$email", + country => "DE" + } + }; + #paymentMethods => ['visa', 'mastercard', 'paypal', 'sofort', 'paydirekt', 'giropay', 'sepa'], + + my $datahash = "$pay_json->{merchantId}$pay_json->{accountId}$pay_json->{portalId}$pay_json->{mode}$pay_json->{reference}$amount$currency"; + + my $paytoken = hmac_sha256_base64($datahash, $dbt->{payonelink_conf}->{portalKey}); + # Fix padding of Base64 digests + while (length($paytoken) % 4) { + $paytoken .= '='; + } + print FILE "datahash: $datahash, $dbt->{payonelink_conf}->{portalKey}\n"; + print FILE "paytoken: $paytoken\n"; + + my $rest_json = encode_json(\%{ $pay_json }); + print FILE "rest_json:\n" . Dumper($rest_json) . "\n"; + ($ret_json, my $ret_status) = $self->rpcpayone_postjson("$paytoken","$rest_json"); + + my $update_pos = { + table => "contenttranspos", + ca_id => "$ctadr->{c_id}", + mtime => "now()", + owner => "$owner", }; - - my $datahash = $payonelink_conf->{merchantId} . $payonelink_conf->{accountId} . $payonelink_conf->{portalId} . $payonelink_conf->{mode} . $prepaidhash->{prepaid_id} . $amount . $currency; - - my $paytoken = hmac_sha256_base64($datahash, $payonelink_conf->{portalKey}); - - #my $whole_json = { %$payonelink_conf, %$pay_request}; - #my $rest_json = encode_json($whole_json); - my $rest_json = encode_json(\%{ $pay_request }); - - print FILE "rest_json:\n" . Dumper($rest_json) . "\n"; - - ($ret_json, my $ret_status) = $self->rpc_postjson($paytoken,$rest_json); eval { $response_in = decode_json($ret_json); print FILE "<--- payonelink response_in with status_line: $ret_status\n" . Dumper($response_in); + print FILE $response_in->{link} . "\n"; + $update_pos->{txt30} = $response_in->{link}; print FILE $ret_json . "\n"; - #expecting something like this: - #return "https://onelink.pay1.de/p/YNEVNS4N1N5JXTFLYPMQJ5PVADEEZ0UL?lang=de_DE"; }; if ($@){ print FILE "<--- failure payonelink raw response_in with status_line: $ret_status\n" . Dumper($ret_json) . "\n"; - #warn $@; print FILE "warn:" . $@ . "\n"; } - }else{ + $update_pos->{txt25} = "$prepaidhash->{response_log}\n- $ret_status"; + my $ctpos = { c_id => $prepaidhash->{number} }; + my $rows = $dbt->update_record($dbh,$update_pos,$ctpos) if($ctpos->{c_id}); + + my $cms_message_key = "email-payonelink"; + if(!$varenv->{cms}->{$cms_message_key}->{txt}){ + $feedb->{message} = "failure::Achtung, '$cms_message_key' ist nicht vorhanden. Es wurde keine eMail versandt!"; + }elsif($ctpos->{c_id}){ + system("$dbt->{copri_conf}->{basedir}/$varenv->{syshost}/src/scripts/mailTransportcms.pl '$varenv->{syshost}' 'send_payonelink' '$ctadr->{c_id}' '$ctpos->{c_id}' '' '$cms_message_key' ''"); + } + + }#end if($ctadr->{c_id} && $prepaidhash->{prepaid_id} && $prepaid_amount2 >= 5) + + else{ $ret_json = "failure:: $ctadr->{c_id} && $prepaidhash->{prepaid_id} && $prepaid_amount2 >= 5"; } close FILE; return $ret_json; -}#end Request "send_payone_link" +}#end generate_payonelink -#JSON POST to onelink -sub rpc_postjson { +#request JSON POST to onelink +sub rpcpayone_postjson { my $self = shift; my $paytoken = shift; my $rest_json = shift || ""; - my $api_file = "/var/www/copri4/shareeconf/apikeys.cfg"; - my $aconf = Config::General->new($api_file); - my %apikeyconf = $aconf->getall; - my $ua = LWP::UserAgent->new( ssl_opts => { SSL_version => 'TLSv12:!SSLv2:!SSLv3:!TLSv1:!TLSv11', } ); - $ua->agent("sharee payone jsonPOST API"); + $ua->agent("sharee payonelink POST API"); my $bytes = 100000; $ua->max_size( $bytes ); $ua->default_header( 'Authorization' => "payone-hmac-sha256 $paytoken" ); - print Dumper($ua); + #print Dumper($ua); - #local TEST - my $endpoint = "https://shareeapp-fr01.copri-bike.de/APIvelo"; - #my $endpoint = "https://onelink.pay1.de/api/v1/payment-links/"; + #local tests + #my $endpoint = "https://shareeapp-fr01.copri-bike.de/APIvelo"; + my $endpoint = "https://onelink.pay1.de/api/v1/payment-links/"; my $req = HTTP::Request->new(POST => "$endpoint"); $req->content_type('application/json'); diff --git a/copri4/main/src/Mod/Prelib.pm b/copri4/main/src/Mod/Prelib.pm index 31d82f2..25c2d74 100755 --- a/copri4/main/src/Mod/Prelib.pm +++ b/copri4/main/src/Mod/Prelib.pm @@ -3,9 +3,8 @@ package Prelib; # SPDX-License-Identifier: AGPL-3.0-or-later # Copyright (c) Rainer Gümpelein, TeilRad GmbH # -#migrate some methodes form Prelogic and Premain to here -#defined methodes are available for web-app and backend - +#this module holds some basic data management methodes +# use strict; use warnings; use POSIX; @@ -114,7 +113,7 @@ sub prepaid_request { }; $cttpos->{c_id} = $dbt->insert_pos($dbh,$ctt_prepaid->{c_id},$ct,"",$ctadr,"","","","0",$owner,""); - $dbt->update_one($dbh,{table => 'contenttranspos',c_id => $cttpos->{c_id}},"barcode = $cttpos->{c_id},ct_name = '$cttpos->{c_id}'"); + $dbt->update_one($dbh,{table => 'contenttranspos',c_id => $cttpos->{c_id}},"barcode = $cttpos->{c_id},ct_name = '$ctt_prepaid->{c_id}-$cttpos->{c_id}'"); $feedb->{prepaid_id} = $ctt_prepaid->{c_id} . "-" . $cttpos->{c_id}; } @@ -858,20 +857,6 @@ sub save_contenttranspos { }; if($ctpos->{c_id}){ $u_rows += $dbt->update_record($dbh,$update_pos,$ctpos); - #prepaid account Vde management by booking prepaid amount - if($R::tpl_id4trans && $R::tpl_id4trans == 219){ - my $update_adr = { - table => "contentadr", - owner => $owner, - mtime => "now()", - c_id => $ctpos->{ca_id}, - int12 => "0", - }; - my $ctadr = { c_id => $ctpos->{ca_id} }; - $u_rows += $dbt->update_record($dbh,$update_adr,$ctadr);#check int12=0 update - #$dbt->update_one($dbh,$update_adr,"int12=0");#Vde - $dbt->update_operatorsloop($varenv{dbname},$ctadr->{c_id},"update"); - } }else{ $feedb->{message} = "failure::Fehler 1, Änderung abgelehnt da Rechnung bereits gebucht"; } @@ -895,7 +880,27 @@ sub delete_contenttranspos { my $feedb = { d_rows => 0, message => "", }; - $feedb->{d_rows} = $dbt->delete_content($dbh,"contenttranspos",$c_id); + + #prepaid pos check + my $pref = { + table => "contenttrans", + table_pos => "contenttranspos", + fetch => "one", + template_id => "219",#prepaid tpl_id + c_id => $c_id, + int02 => ">=::1", + "ct.state" => "is::null", + }; + + my $ctpos = { c_id => 0 }; + $ctpos = $dbt->collect_post($dbh,$pref) if($c_id); + + #prefent deleting prepaid positions + if($ctpos->{c_id}){ + $feedb->{message} = "failure::Datensatz löschen ist für Prepaid-Account deaktiviert. Prepaid payments müssen erhalten bleiben."; + }else{ + $feedb->{d_rows} = $dbt->delete_content($dbh,"contenttranspos",$c_id); + } return $feedb; }#end delete_contenttranspos diff --git a/copri4/main/src/Mod/Pricing.pm b/copri4/main/src/Mod/Pricing.pm index e2ba6eb..aaf26c3 100755 --- a/copri4/main/src/Mod/Pricing.pm +++ b/copri4/main/src/Mod/Pricing.pm @@ -44,51 +44,6 @@ sub round(){ return $rounded; } -#collect prepaid -sub collect_prepaid { - my $self = shift; - my $dbh = shift; - my $ctadr = shift || {}; - - my $prepaidhash = { - prepaid_total => 0, - prepaid_id => 0, - }; - - if($ctadr->{c_id}){ - my $posref = { - table => "contenttrans", - table_pos => "contenttranspos", - fetch => "all", - keyfield => "c_id", - ca_id => "$ctadr->{c_id}", - 'ct.state' => "is::null", - 'ct.close_time' => "is::null", - }; - my $cttpos = { c_id => 0 }; - $cttpos = $dbt->collect_post($dbh,$posref); - #TODO negative counting booked operator invoices - foreach my $id (sort { $cttpos->{$b}->{c_id} <=> $cttpos->{$a}->{c_id} } keys(%$cttpos)){ - #print $cttpos->{$id}->{barcode} . ":" . $cttpos->{$id}->{int02},"
"; - - if($cttpos->{$id}->{barcode} && $cttpos->{$id}->{int02} == 0){ - $prepaidhash->{prepaid_id} = $cttpos->{$id}->{ct_id} . "-" . $cttpos->{$id}->{c_id}; - $prepaidhash->{number} = $cttpos->{$id}->{c_id}; - $prepaidhash->{description} = $cttpos->{$id}->{txt01}; - } - #if($cttpos->{$id}->{barcode} && $cttpos->{$id}->{int02} > 0){ - # $prepaidhash->{prepay_id_payed} = $cttpos->{$id}->{int02}; - #} - if($cttpos->{$id}->{int02} > 0){ - $prepaidhash->{prepaid_total} += $cttpos->{$id}->{int02}; - } - - } - } - $bw->log("Pricing prepaidhash:",$prepaidhash,""); - return $prepaidhash; -} - #for one freed rental #depends on operator, only 1 rental get freed_time @@ -381,7 +336,7 @@ sub counting_rental { $return->{rentalog}->{used_methode} = "$used_methode"; $return->{rentalog}->{counting} = $counting; - $bw->log("Pricing counting_rental return:",$return,""); + #$bw->log("Pricing counting_rental return:",$return,""); return ($return,$counting); }#end counting_rental @@ -677,5 +632,103 @@ sub operator_accounting2calc { return $oac; } +#primary collect prepaid +sub collect_prepaid { + my $self = shift; + my $dbh = shift; + my $ctadr = shift || {}; + + my $prepaidhash = { + prepaid_total => 0, + prepaid_id => 0, + }; + + if($ctadr->{c_id}){ + my $posref = { + table => "contenttrans", + table_pos => "contenttranspos", + fetch => "all", + keyfield => "c_id", + ca_id => "$ctadr->{c_id}", + 'ct.state' => "is::null", + 'ct.close_time' => "is::null", + }; + my $cttpos = { c_id => 0 }; + $cttpos = $dbt->collect_post($dbh,$posref); + foreach my $id (sort { $cttpos->{$b}->{c_id} <=> $cttpos->{$a}->{c_id} } keys(%$cttpos)){ + #print $cttpos->{$id}->{barcode} . ":" . $cttpos->{$id}->{int02},"
"; + + if($cttpos->{$id}->{barcode} && $cttpos->{$id}->{int02} == 0){ + $prepaidhash->{invoice_id} = $cttpos->{$id}->{ct_id}; + $prepaidhash->{number} = $cttpos->{$id}->{c_id}; + $prepaidhash->{prepaid_id} = $cttpos->{$id}->{ct_id} . "-" . $cttpos->{$id}->{c_id};#payone reference + $prepaidhash->{description} = $cttpos->{$id}->{txt01}; + $prepaidhash->{response_log} = $cttpos->{$id}->{txt25}; + $prepaidhash->{payone_link} = $cttpos->{$id}->{txt30}; + if($cttpos->{$id}->{txt25} =~ /(\d{4}-\d{2}-\d{2}\s\d{2}:\d{2}) mailing/){ + $prepaidhash->{mail_datetime} = $1; + $prepaidhash->{mail_datetime} = $lb->time4de($prepaidhash->{mail_datetime},"1"); + } + } + if($cttpos->{$id}->{int02} && $cttpos->{$id}->{int02} != 0){ + $prepaidhash->{prepaid_total} += $cttpos->{$id}->{int02}; + } + } + + if($prepaidhash->{invoice_id} && $ctadr->{int03} && $ctadr->{int03} == 3 && (!$ctadr->{int12} || $ctadr->{int12} != 2)){ + my $update_adr = { + table => "contentadr", + ct_name => "Prepaid-$prepaidhash->{invoice_id}", + pay_time => "now()",#just to see who changes at what time + }; + + #for int12 vde update we need also open operator invoices to get saldo balance + #int12 => "1", + + #if($prepaidhash->{prepaid_total} > 0){ + #$update_adr->{int12} = "null"; + #}else{ + # $update_adr->{int12} = "1"; + #} + $dbt->update_record($dbh,$update_adr,$ctadr); + $dbt->update_operatorsloop("",$ctadr->{c_id},"update"); + } + } + + $bw->log("Pricing prepaidhash:",$prepaidhash,""); + return $prepaidhash; +}#end collect prepaid + + +#sum of primary prepaid +sub primary_sum_prepaid { + my $self = shift; + my $dbh = shift; + my $auth = shift; + my $ctt = shift; + + my $presum = 0; + #if($ctt->{int03} && $ctt->{int03} == 3){ + #my $dbh_primary = $dbt->dbconnect_extern($dbt->{primary}->{sharee_primary}->{database}->{dbname}); + my $pref = { + table => "contenttrans", + table_pos => "contenttranspos", + fetch => "all", + keyfield => "c_id", + ca_id => "$auth->{c_id}", + 'ct.state' => "is::null", + }; + my $prepaid_pos = { c_id => 0 }; + $prepaid_pos = $dbt->collect_post($dbh,$pref) if($auth->{c_id}); + foreach my $id (sort { $prepaid_pos->{$b}->{itime} cmp $prepaid_pos->{$a}->{itime} } keys(%$prepaid_pos)){ + (my $preprice,my $rabatt) = $self->price2calc($prepaid_pos->{$id}); + $presum += $preprice; + } + $presum = $self->round($presum); + $presum = sprintf('%.2f', $presum); + #} + return $presum; +} + 1; diff --git a/copri4/main/src/Mod/RPCshareeio.pm b/copri4/main/src/Mod/RPCshareeio.pm new file mode 100644 index 0000000..68eead6 --- /dev/null +++ b/copri4/main/src/Mod/RPCshareeio.pm @@ -0,0 +1,106 @@ +package RPCshareeio; +# +# SPDX-License-Identifier: AGPL-3.0-or-later +# Copyright (c) Rainer Gümpelein, TeilRad GmbH +# +#APIshareeio APIcall +# +#use lib "/var/www/copri-bike/shareedms-primary/src"; +# +use strict; +use warnings; +use POSIX; +use CGI; +use Digest::SHA qw(hmac_sha256 hmac_sha256_base64); +use JSON; +my $json = JSON->new->allow_nonref; +use LWP::UserAgent; +use URI::Encode; +my $uri_encode = URI::Encode->new( { encode_reserved => 1 } ); +use Scalar::Util qw(looks_like_number); +use Mod::DBtank; +use Mod::Basework; +use Data::Dumper; + +my $q = new CGI; +my $dbt = new DBtank; +my $bw = new Basework; + + +sub new { + my $class = shift; + my $self = {}; + bless($self,$class); + return $self; +} + +#@all request with defined $shareeio_json +sub request_shareeio { + my $self = shift; + my $varenv = shift; + my $dbh = shift; + my $ctadr = shift || {}; + my $shareeio_json = shift || { request => ""}; + my $response_in = {}; + + my $now_dt = strftime "%Y-%m-%d %H:%M:%S", localtime; + open(EMA, ">> $varenv->{logdir}/RPCshareeio.log"); + print EMA "\n*** $now_dt RPC $shareeio_json->{request}\n"; + + if($shareeio_json->{request}){ + my $rest_json = encode_json(\%{ $shareeio_json }); + print EMA "rest_json:\n" . Dumper($rest_json) . "\n"; + + my $ret_json = {}; + ($ret_json, my $ret_status) = $self->rpcsharee_postjson($rest_json); + eval { + $response_in = decode_json($ret_json); + print EMA "<--- success shareeio response_in: $ret_status\n" . Dumper($response_in) . "\n"; + print EMA $ret_json . "\n"; + + }; + if ($@){ + print EMA "<--- failure shareeio raw response_in: $ret_status\n" . Dumper($ret_json) . "\n"; + print EMA "warn:" . $@ . "\n"; + $response_in->{shareeio}->{response_state} = "Failure: $ret_status"; + } + } + + close EMA; + return $response_in; +} + + +#request JSON POST to shareeio +sub rpcsharee_postjson { + my $self = shift; + my $rest_json = shift || ""; + + my $api_file = "/var/www/copri4/shareeconf/apikeys.cfg"; + my $aconf = Config::General->new($api_file); + my %apikeyconf = $aconf->getall; + + my $ua = LWP::UserAgent->new(); + $ua->agent("RPCshareeio POST"); + my $bytes = 100000; + $ua->max_size( $bytes ); + $ua->default_header( 'SHAREE-API-KEY' => "$apikeyconf{shareeio}->{sharee_api_key}" ); + #print Dumper($ua); + + my $req = HTTP::Request->new(POST => "$apikeyconf{shareeio}->{endpoint}"); + $req->content_type('application/json'); + $req->content($rest_json); + my $res = $ua->request($req); + + if ($res->is_success) { + #print $res->content; + #print $res->status_line, "\n"; + return ($res->content, $res->status_line); + }else { + #print $res->status_line, "\n"; + return ("", $res->status_line); + } +} + + +1; diff --git a/copri4/main/src/Mod/Shareework.pm b/copri4/main/src/Mod/Shareework.pm index 4bef9e6..7280c57 100755 --- a/copri4/main/src/Mod/Shareework.pm +++ b/copri4/main/src/Mod/Shareework.pm @@ -3,9 +3,12 @@ package Shareework; # SPDX-License-Identifier: AGPL-3.0-or-later # Copyright (c) Rainer Gümpelein, TeilRad GmbH # +#this module holds sharee app user-account management methods. +#some methods are also used by DMS Basedit +# #disable for syntax check #use lib qw(/var/www/copri-bike/shareeapp-primary/src); - +# use strict; use warnings; use POSIX; diff --git a/copri4/main/src/Tpl/Address3.pm b/copri4/main/src/Tpl/Address3.pm index f998c17..0d0f828 100755 --- a/copri4/main/src/Tpl/Address3.pm +++ b/copri4/main/src/Tpl/Address3.pm @@ -40,8 +40,6 @@ sub tpl(){ my $trin = new TransInvoices; my $lang = "de"; my %ib = $but->ibuttons(); - my $line_count1 = 0; - my $line_count2 = 0; my $dbh = ""; #selects Kunden-Faktura @@ -301,22 +299,22 @@ EOF print $q->td({-class=>'tdval4',-colspan=>'2'},$q->span({-style=>"background-color:#dcd77f;"},$q->a({-class=>"linknav",-href=>"/DMS/Kunden?node2edit=editpart\&mode=manager\&rel_id=$ctadr->{rel_id}\&tpl_id=202",-title=>"Kunden Stammdaten öffnen"}," Kunden ID $c_idadr ")), $q->span({-style=>"color:red;padding-left:10px;"}," $vde")),"\n"; } $ctt->{txt01} = $lb->newline($ctt->{txt01},"",""); - print $q->Tr(),"\n"; $line_count1++; + print $q->Tr(),"\n"; print $q->td({-class=>'tdescr4'}," "),"\n"; print $q->td({-class=>'tdval4',-colspan=>2},"$ctt->{txt01}"),"\n"; - print $q->Tr(),"\n"; $line_count1++; + print $q->Tr(),"\n"; print $q->td({-class=>'tdescr4'}," "),"\n"; print $q->td({-class=>'tdval4',-colspan=>2},"$ctt->{txt03}"),"\n"; - print $q->Tr(),"\n"; $line_count1++; + print $q->Tr(),"\n"; print $q->td({-class=>'tdescr4'}," "),"\n"; print $q->td({-class=>'tdval4',-colspan=>2},"$ctt->{txt06}"),"\n"; - print $q->Tr(),"\n"; $line_count1++; + print $q->Tr(),"\n"; print $q->td({-class=>'tdescr4'}," "),"\n"; print $q->td({-class=>'tdval4',-colspan=>2},"$ctt->{txt08}"),"\n"; print $q->Tr(),"\n"; print $q->td({-class=>'tdescr4'}," "),"\n"; print $q->td({-class=>'tdval4',-colspan=>2},"$ctt->{txt07}"),"\n"; - print $q->Tr(),"\n";$line_count1++; + print $q->Tr(),"\n"; print $q->td({-class=>'tdescr4'}," "),"\n"; print $q->td({-class=>'tdval4',-colspan=>2},"$ctt->{txt20} $int05"),"\n"; } @@ -357,19 +355,19 @@ EOF my $kind_of_payment = "fehlt"; my $p_hash = $dbt->{shareedms_conf}->{payment_state2}; foreach my $s_key (sort keys (%{ $p_hash })) { - if($ctt->{state} && $ctt->{int03}){ - $kind_of_payment = $p_hash->{$s_key} if($ctt->{int03} == $s_key); + if($ctadr->{int03}){ + $kind_of_payment = "Kunde " . $p_hash->{$s_key} if($ctadr->{int03} == $s_key); } - elsif($ctadr->{int03}){ - $kind_of_payment = $p_hash->{$s_key} if($ctadr->{int03} == $s_key); + if($ctt->{int03}){ + $kind_of_payment .= " | Faktura " . $p_hash->{$s_key} if($ctt->{int03} == $s_key); } } my $payteaser = ""; - if($ctadr->{txt28}){ + if($ctt->{int03} && $ctt->{int03} != 3 && $ctadr->{txt28}){ $payteaser = substr($ctadr->{txt28},0,50) . " ..."; } print $q->Tr(),"\n"; - print $q->td({-class=>'tdescr4'},"Payone Zahlungsart"),"\n"; + print $q->td({-class=>'tdescr4'},"Zahlungsart"),"\n"; print $q->td({-class=>'tdval4'},"$kind_of_payment"),"\n"; print $q->Tr(),"\n"; print $q->td({-class=>'tdescr4'},"Payone log Kunde"),"\n"; @@ -395,19 +393,20 @@ EOF #operator invoices else position accounting if($ctt->{template_id} == 208 || $ctt->{int10} == 2){ - $line_count2 = $trin->tpl($varenv,$node_meta,$users_dms,$ctf,$ctadr,$ctt); + $trin->tpl($varenv,$node_meta,$users_dms,$ctf,$ctadr,$ctt); }else{ - $line_count2 = $transp->tpl($varenv,$node_meta,$users_dms,$ctf,$ctadr,$ctt); + $transp->tpl($varenv,$node_meta,$users_dms,$ctf,$ctadr,$ctt); } print "\n"; ###end Edit Parts - #Text & Vorbelegungen + #Text&State Save + if($ctt->{template_id} != 219){ + my $tplf = $dbt->get_tpl($dbh,201);#tpl Kunden-Faktura my @tplf_order = split /,/,$tplf->{tpl_order}; - print $q->start_form(),"\n"; print $q->hidden(-name=>'c_id4trans', -override=>'1', -value=>"$ctt->{c_id}"); @@ -485,6 +484,7 @@ EOF } print $q->end_form,"\n"; + }#end Text & State Save print $q->end_table,"\n"; ###end Big @@ -492,7 +492,7 @@ EOF #payone-return log $ctt->{txt28} = $lb->newline($ctt->{txt28},"",""); print $q->div({-id=>'Oline'},""),"\n"; - print $q->div({-style=>'padding: 0 15px 20px 15px;font-size:0.91em;'},"payone-response log
$ctt->{txt28}"),"\n"; + print $q->div({-style=>'padding: 0 15px 20px 15px;font-size:0.91em;'},"payment-response log
$ctt->{txt28}"),"\n"; print "\n"; return; diff --git a/copri4/main/src/Tpl/BaseEdit.pm b/copri4/main/src/Tpl/BaseEdit.pm index 3f742e3..5ccf01c 100755 --- a/copri4/main/src/Tpl/BaseEdit.pm +++ b/copri4/main/src/Tpl/BaseEdit.pm @@ -209,7 +209,7 @@ sub tpl(){ $edit = "base_edit"; $save_key = "save_pos"; my $tpl_id = $node_meta->{tpl_id}; - $tpl_id = 223 if($cttpos->{template_id} && $cttpos->{template_id} =~ /224|229/); + $tpl_id = 223 if($cttpos->{template_id} && $cttpos->{template_id} =~ /224|229|219/); $tpl = $dbt->get_tpl($dbh,$tpl_id); }else{ diff --git a/copri4/main/src/Tpl/Liste3.pm b/copri4/main/src/Tpl/Liste3.pm index d57612b..20652b5 100755 --- a/copri4/main/src/Tpl/Liste3.pm +++ b/copri4/main/src/Tpl/Liste3.pm @@ -78,6 +78,7 @@ sub tpl(){ my $debug = 0; my $coo = $q->cookie(-name=>'domcookie') || ""; my $opdir_dms = "$dbt->{copri_conf}->{basedir}/$dbt->{operator}->{$varenv{dbname}}->{dir_dms}" || ""; + my $xjournal = $dbt->get_node($dbh,$dbt->{shareedms_conf}->{xjournal}); $path =~ s/\/login|\/user|\/manager|\/admin|\/$//; my $user_agent = $q->user_agent(); @@ -819,7 +820,7 @@ EOF #fee2pos if($table eq "content" && ($ct4rel->{$id}->{template_id} =~ /229/) && $R::c_id4trans){ - print $q->a({-class=>"editnav",-href=>"/$dbt->{shareedms_conf}->{parent_node}/Mietjournal?insert_contenttranspos=1\&c_id=$ct4rel->{$id}->{c_id}\&c_id4trans=$R::c_id4trans\&owner=$users_dms->{u_id}",-title=>"Gebühr hinzufügen"}, $q->span({-class=>"bi bi-clipboard2-plus", -style=>'font-size:1.5em;'})); + print $q->a({-class=>"editnav",-href=>"/$dbt->{shareedms_conf}->{parent_node}/$xjournal->{node_name}?insert_contenttranspos=1\&c_id=$ct4rel->{$id}->{c_id}\&c_id4trans=$R::c_id4trans\&owner=$users_dms->{u_id}",-title=>"Gebühr hinzufügen"}, $q->span({-class=>"bi bi-clipboard2-plus", -style=>'font-size:1.5em;'})); } if($table eq "content" && ($ct4rel->{$id}->{template_id} =~ /205|225/)){ @@ -1153,7 +1154,7 @@ EOF print $q->td({-class=>"$calement",-colspan=>2,-style=>"$set_style;"},""),"\n"; print "\n"; #print $q->div({-style=>"position:absolute;margin-left:$daymarker;border-right: solid thin #86cb00;height:1.7em;"}," "),"\n";# if("$mon" eq "$mon_today"); - my $calpath = "Mietjournal"; + my $calpath = $xjournal->{node_name}; if(1==2 && $ct4rel->{$id}->{int13} == $cttpos->{$ctid}->{int13} && $cttpos->{$ctid}->{int10} =~ /7|8/){ $calpath = "Alarmjournal"; $time_style="color:red;"; diff --git a/copri4/main/src/Tpl/SubListe.pm b/copri4/main/src/Tpl/SubListe.pm index 74cb957..69d0a03 100755 --- a/copri4/main/src/Tpl/SubListe.pm +++ b/copri4/main/src/Tpl/SubListe.pm @@ -194,7 +194,9 @@ EOF if($users_dms->{"col_sort_$searchref->{table_pos}"}){ $searchref->{scol} = $users_dms->{"col_sort_$searchref->{table_pos}"}; } - + if(!$searchref->{table_pos} && $users_dms->{"col_sort_$searchref->{table}"}){ + $searchref->{scol} = $users_dms->{"col_sort_$searchref->{table}"}; + } $searchref->{scol} = "u_id" if($node_meta->{template_id} == 198); $users_dms->{"sort_updown_$searchref->{table_pos}"} = "down" if(!$users_dms->{"sort_updown_$searchref->{table_pos}"}); @@ -350,6 +352,7 @@ EOF if($node_meta->{tpl_id} !~ /198|199/){ $val = "$val" if($key eq $users_dms->{"col_sort_$searchref->{table_pos}"}); + $val = "$val" if($key eq $users_dms->{"col_sort_$searchref->{table}"} && !$searchref->{table_pos}); print $q->th({-style=>'padding:5px 0'},$q->div({-style=>"$divstyle"},$q->a({-class=>"sortnav",-href=>"?col_sort=$key\&offset=$searchref->{offset}\&limit=$searchref->{limit}",-title=>"$val"},"$val"))),"\n" if($key ne "u_id"); }else{ print $q->th({-style=>'padding:5px 0'},$q->div({-style=>"$divstyle"},"$val")),"\n" if($key ne "u_id"); diff --git a/copri4/main/src/Tpl/TransPositionen.pm b/copri4/main/src/Tpl/TransPositionen.pm index d963534..7b12b2b 100755 --- a/copri4/main/src/Tpl/TransPositionen.pm +++ b/copri4/main/src/Tpl/TransPositionen.pm @@ -21,6 +21,7 @@ use Mod::Libenz; use Mod::DBtank; use Mod::APIfunc; use Mod::Pricing; +use Mod::RPCshareeio; sub new { my $class = shift; @@ -46,6 +47,7 @@ sub tpl(){ my $apif = new APIfunc; my $but = new Buttons; my $pri = new Pricing; + my $rpcs = new RPCshareeio; my %ib = $but->ibuttons(); my $today = strftime "%d.%m.%Y",localtime; my $now_dt = strftime "%Y-%m-%d %H:%M:%S", localtime; @@ -56,23 +58,34 @@ sub tpl(){ my $mapref = {}; my $ct_users = $dbt->users_map($dbh,$mapref);#get serviceAPP and DMS users from contentadr - my $line_count2 = 0; my $tc=0; my $txt20 = $R::txt20 || $ctt->{txt20} || "";#Leistungsdatum my $int05 = $R::int05 || $ctt->{int05} || "";#manuell my $rows = 0; my $spart_ct_name = $R::spart_ct_name || ""; my $c_idpos = $R::c_idpos || $R::pos_id || 0; - my $cttpos = { c_id => 0 }; + my $scol = "itime"; my $vibuchen_mtime = "(nicht verfügbar, siehe Internas und log)"; - my @tpl_order = ("txt01=Beschreibung","ct_name=Nummer","date_time=timerange","int03=Menge (Miet - Gratis Zeit)","int02=Preis","int07=Rabatt","int04=Gesamt"); my $tplf = $dbt->get_tpl($dbh,201);#Kunden-Faktura Firma my @tplf_order = split /,/,$tplf->{tpl_order}; + my $cttpos = { c_id => 0 }; ($cttpos,$rows) = $dbt->collect_contentpos($dbh,"contenttrans",$ctt->{content_id}); + #if operator invoice with prepaid type exist, then check whether balance positive + my $sum_prepaid = 0; + if($ctt->{int03} && $ctt->{int03} == 3 && $varenv->{dbname} ne $dbt->{primary}->{sharee_primary}->{database}->{dbname}){ + my $shareeio_json = { + request => "collect_prepaid_invoices", + userID => "$ctadr->{c_id}", + }; + + my $prepaid_invoices = $rpcs->request_shareeio($varenv,$dbh,$ctadr,$shareeio_json); + $sum_prepaid = $prepaid_invoices->{shareeio}->{users_prepaid_invoices}->{$ctadr->{c_id}}->{sum_prepaid_available}; + } + my $station_all = {}; my $pref_st = { table => "content", @@ -150,7 +163,6 @@ EOF print $q->hidden(-id=>'c_id', -name=>"c_id", -override=>'1'),"\n"; print $q->hidden(-id=>'spart_ct_name', -name=>"spart_ct_name", -override=>'1'),"\n"; - $line_count2++; print $q->Tr(); print $q->th($but->singlesubmit("select_part","*")),"\n"; foreach (@tpl_order){ @@ -167,9 +179,6 @@ EOF print $q->start_form(-name=>'transposform'),"\n"; - #Tablecontent (buttons and ct_name(primary key)) - #my $scol = "c_id";#changed to itime because of Storno resorts - my $scol = "itime"; my $sum_parts19=0; my $sumgeb_teil=0; my $sumgeb_bank=0; @@ -178,6 +187,7 @@ EOF my $i=0; my $accounting_start = ""; my $accounting_end = ""; + my $xjournal = $dbt->get_node($dbh,$dbt->{shareedms_conf}->{xjournal}); #foreach my $id (sort { $cttpos->{$b}->{$scol} <=> $cttpos->{$a}->{$scol} } keys(%$cttpos)){ foreach my $id (sort { $cttpos->{$b}->{$scol} cmp $cttpos->{$a}->{$scol} } keys(%$cttpos)){ @@ -224,13 +234,6 @@ EOF $accounting_start = "$3.$2.$1" if($cttpos->{$id}->{itime} =~ /(\d+)\-(\d+)\-(\d+)/); } } - #print "$accounting_start - $accounting_end
"; - - my @line_txt01 = split(/\n/,$cttpos->{$id}->{txt01}); - if($cttpos->{$id}->{int02} != 0){ - $line_count2++; - #$line_count2 += scalar(@line_txt01); - } #1. Spalte print $q->Tr(),"\n"; @@ -245,8 +248,7 @@ EOF }elsif(!$ctt->{close_time}){ print $q->a({-class=>"editnav3",-href=>"/DMS/Faktura?trans2edit=transpos\&c_idpos=$cttpos->{$id}->{c_id}\&c_id4trans=$ctt->{content_id}\&tpl_id4trans=$ctt->{template_id}\&owner=$users_dms->{u_id}",-title=>"Datensatz bearbeiten"}, $q->span({-class=>"bi bi-file-earmark-text", -style=>'font-size:1.7em;'})),"\n"; } - my $calpath = "Mietjournal"; - print $q->a({-class=>"linknav3",-href=>"/DMS/$calpath/?cttpos_id=$cttpos->{$id}->{c_id}",-title=>"Im $calpath anzeigen"},"

→ ID $cttpos->{$id}->{c_id}"),"\n"; + print $q->a({-class=>"linknav3",-href=>"/DMS/$xjournal->{node_name}/?cttpos_id=$cttpos->{$id}->{c_id}",-title=>"Im $xjournal->{node_name} anzeigen"},"

→ ID $cttpos->{$id}->{c_id}"),"\n"; print "\n"; #Tablecontent (parameter) @@ -484,7 +486,8 @@ EOF $sum_paid = $pri->round($sum_paid); my $sum_preauth = $sum_paid || 0; $sum_paid = sprintf('%.2f', $sum_paid); - $sum_paid =~ s/\./,/; + my $sum_paid_view = $sum_paid; + $sum_paid_view =~ s/\./,/; $sum_parts19 = sprintf('%.2f', $sum_parts19); $sum_umst19 = sprintf('%.2f', $sum_umst19); @@ -518,21 +521,21 @@ EOF print $q->Tr("\n"); print $q->td(" "); - print $q->Tr("\n"); $line_count2++; - print $q->td({-class=>'tdint'},"Nettobetrag:"); - print $q->td({-class=>'tdint',-nowrap=>"1"},"$sum_netto19 €"); + print $q->Tr("\n"); + print $q->td({-class=>'tdint'},"Nettobetrag:"); + print $q->td({-class=>'tdint',-nowrap=>"1"},"$sum_netto19 €"); - print $q->Tr("\n");$line_count2++; - #print $q->td({-class=>'tdint',-nowrap=>"1"},"$umst1619% UmSt auf $sum_netto19 €:"); - print $q->td({-class=>'tdint',-nowrap=>"1"},"19% UmSt auf $sum_netto19 €:"); - print $q->td({-class=>'tdint',-nowrap=>"1"},"$sum_umst19 €"); - my $summe = "Summe"; - print $q->Tr("\n");$line_count2++; - print $q->td({-class=>'tdsum'},"$summe:"); - print $q->td({-class=>'tdint',-nowrap=>"1"},"$sum_paid €"); + print $q->Tr("\n"); + print $q->td({-class=>'tdint',-nowrap=>"1"},"19% UmSt auf $sum_netto19 €:"); + print $q->td({-class=>'tdint',-nowrap=>"1"},"$sum_umst19 €"); + + print $q->Tr("\n"); + print $q->td({-class=>'tdsum'},"Summe:"); + print $q->td({-class=>'tdint',-nowrap=>"1"},"$sum_paid_view €"); print $q->hidden(-name=>'sum_paid', -override=>'1',-value=>"$sum_paid"); print $q->hidden(-name=>'sumgeb_teil', -override=>'1',-value=>"$sumgeb_teil") if($sumgeb_teil); print $q->hidden(-name=>'sumgeb_bank', -override=>'1',-value=>"$sumgeb_bank") if($sumgeb_bank); + #print $q->hidden(-name=>'sum_prepaid', -override=>'1',-value=>"$sum_prepaid"); print $q->end_table; print " "; @@ -574,6 +577,8 @@ EOF $kind_of_payment = $p_hash->{3} if($ctadr->{ct_name} =~ /Prepaid-\d+/); } } + #only prepaid on primary + @_paymentstate = ("Prepaid") if($varenv->{dbname} eq $dbt->{primary}->{sharee_primary}->{database}->{dbname}); if($ctt->{state} && $ctt->{int01}){ $ctt->{int01} =~ s/\./,/; @@ -585,15 +590,25 @@ EOF print $q->div({-style=>"padding:0.5em;font-size:0.81em;width:98%;text-align:right;"},"$opos Summe $ctt->{int01} € gebucht per \"$ctt->{state}\" | Payone Saldo $ctt->{int16} € | $vibuchen_mtime "),"\n"; }else{ my $fibutext = ""; - $fibutext = "(TeilRad Gebühr $ctt->{int08})" if($ctt->{int08}); $fibutext .= "(Bank Gebühr $ctt->{int07})" if($ctt->{int07}); + $fibutext .= "(TeilRad Gebühr $ctt->{int08})" if($ctt->{int08}); + #$fibutext .= "(Prepaid $ctt->{int09})" if($ctt->{int09}); print $q->div({-style=>"padding:0.5em;font-size:0.81em;width:98%;text-align:right;"},"$opos Summe $ctt->{int01} € $fibutext gebucht per \"$ctt->{state}\" | $vibuchen_mtime "),"\n"; } }else{ print $q->div({-style=>"padding:0.5em;font-size:0.81em;width:98%;text-align:right;"},"Summe ist nicht gebucht!"),"\n"; } - if(!$ctt->{close_time}){ + if($ctt->{int03} && $ctt->{int03} == 3 && (!$ctt->{state} || $ctt->{int14})){ + my $presaldo = $sum_prepaid - $sum_paid; + $presaldo = sprintf('%.2f', $presaldo); + my $precolor = "red"; + $precolor = "green" if($presaldo >= 0); + print $q->div({-style=>"padding:0.5em;font-size:0.81em;width:98%;text-align:right;"},"Es können max. $sum_prepaid € per Prepaid abgebucht werden"),"\n"; + #$sum_paid = $sum_prepaid if($sum_paid > $sum_prepaid);#It can only paid max prepaid sum + } + + if(!$ctt->{close_time} && $ctt->{template_id} != 219){ my $send_invoice_checkbox = 1; $send_invoice_checkbox = 0 if($ctt->{txt30} || $ctt->{ct_name} =~ /\d-\d/); print $q->div({-class=>'element6',-style=>'float:right;background-color:silver;'}, $q->b("$ctt->{txt00}"), @@ -674,6 +689,6 @@ EOF }; $dbt->update_one($dbh,$update_ctt,"txt20='$accounting_start - $accounting_end'"); } - return "$line_count2"; + return; } 1; diff --git a/copri4/main/src/scripts/mailTransportcms.pl b/copri4/main/src/scripts/mailTransportcms.pl index fca69b2..51d6e85 100755 --- a/copri4/main/src/scripts/mailTransportcms.pl +++ b/copri4/main/src/scripts/mailTransportcms.pl @@ -94,6 +94,11 @@ if(looks_like_number($adr_id)){ $sendmail = send_invoice($todo,$sendref,$ctadr,$ct_id,$cmstext_select,$with_pdf); } + #send_payonelink + if($todo eq "send_payonelink"){ + $sendmail = send_payonelink($todo,$sendref,$ctadr,$ct_id,$cmstext_select); + } + #send_emailack if($todo eq "send_emailack"){ $sendmail = send_emailack($todo,$sendref,$ctadr); @@ -219,6 +224,48 @@ sub send_invoice { return $sendref; }#end send_invoice +#send_payonelink +sub send_payonelink { + my $todo = shift; + my $sendref = shift; + my $ctadr = shift; + my $ctpos_id = shift; + my $cms_message_key = shift || ""; + my $lang = $ctadr->{txt11} || $ctadr->{txt10}; + + my $dbh_primary = $dbt->dbconnect_extern($dbt->{primary}->{sharee_primary}->{database}->{dbname},"iso-8859-1"); + my $pref_ctu = { + table => "contentuser", + fetch => "one", + c_id => "1",#primary hotline + }; + my $uadr = { c_id => 0 }; + $uadr = $dbt->fetch_tablerecord($dbh_primary,$pref_ctu); + + $varenv{cms} = $dbt->fetch_cms($dbh_primary,{ lang => $lang }); + + my $pref_pos = { + table => "contenttranspos", + fetch => "one", + ca_id => "$ctadr->{c_id}", + c_id => "$ctpos_id", + }; + my $record_pos = { c_id => 0 }; + $record_pos = $dbt->fetch_tablerecord($dbh_primary,$pref_pos) if($ctpos_id); + + $sendref = prepare_content($sendref,$ctadr,$uadr,$record_pos,$varenv{cms}->{$cms_message_key}->{txt}); + + my $update_pos = { + table => "contenttranspos", + c_id => "$ctpos_id", + }; + my $log_stamp = strftime "%d.%m.%Y %H:%M:%S", localtime; + my $mailing_log = $record_pos->{txt25} . "\n- $log_stamp mailing: $cms_message_key"; + $dbt->update_one($dbh_primary,$update_pos,"txt25='$mailing_log'"); + + return $sendref; +}#end send_payonelink + #send_emailack sub send_emailack { @@ -532,6 +579,8 @@ sub prepare_content { my $total_sum = ""; my $sharee_ticket = ""; my $fibu_user = ""; + my $prepaid_id = ""; + my $payone_link = ""; if(ref($ctt) eq "HASH" && $ctt->{ct_name}){ $invoice_name = "$ctt->{txt00}-$varenv{dbname}-$ctt->{ct_name}.pdf"; $sendref->{attachment} = "$invoice_name" if($with_pdf); @@ -540,12 +589,14 @@ sub prepare_content { $total_sum =~ s/\./,/; $sharee_ticket = "[$invoice_nr]"; $fibu_user = "\n$ctt->{fibu_user}\n" if($ctt->{fibu_user}); + $prepaid_id = $ctt->{ct_id} . "-" . $ctt->{c_id}; + $payone_link = $ctt->{txt30}; } my $subject = "TeilRad Mietradsystem";#default $subject = $1 if($cms_prim =~ /--subject--(.*)--subject--/); $cms_prim =~ s/--subject--$subject--subject--//; - $subject .= " $sharee_ticket" if($sharee_ticket); + $subject .= " $sharee_ticket" if($sharee_ticket && !$payone_link); $cms_prim =~ s/\n//; my $signature = <{message} =~ s/::txid::/$ctt->{txt16}/; $sendref->{message} =~ s/::email_temppassword::/\$ctadr->{txt04}\<\/b\>/g; $sendref->{message} =~ s/::email_ack_digest::/\$ctadr->{txt34}\<\/b\>/g;#send_emailack + $sendref->{message} =~ s/::prepaid_id::/\$prepaid_id\<\/b\>/g; + $sendref->{message} =~ s/::payone_link::/\$payone_link<\/a>\<\/b\>/g; $sendref->{message} =~ s/::signature::/$signature/; $sendref->{message} =~ s/\n/\
/g; diff --git a/copri4/shareeapp-operator/src/Lib/Mlogic.pm b/copri4/shareeapp-operator/src/Lib/Mlogic.pm index 9e48276..771a5e9 100755 --- a/copri4/shareeapp-operator/src/Lib/Mlogic.pm +++ b/copri4/shareeapp-operator/src/Lib/Mlogic.pm @@ -40,7 +40,7 @@ sub tpl(){ } my $bgcolor1 = $dbt->{primary}->{$varenv->{dbname}}->{bgcolor1}; - if($users_sharee->{c_id} && $R::sharee_edit ne "delete_account2" && ($users_sharee->{c_id} eq $varenv->{superu_id} || $dbt->{copri_conf}->{stage} eq "test" || $users_sharee->{txt08} eq "sigo\@sharee.bike")){ + if($users_sharee->{c_id} && (!$R::sharee_edit || $R::sharee_edit ne "delete_account2") && ($users_sharee->{c_id} eq $varenv->{superu_id} || $dbt->{copri_conf}->{stage} eq "test" || $users_sharee->{txt08} eq "sigo\@sharee.bike")){ my $coo = $q->cookie('domcookie') || $q->param('sessionid') || ""; #my $api_test = "sharee_fr01"; my $bike="FR1538"; diff --git a/copri4/shareeapp-operator/src/Tpl/PayoneLink.pm b/copri4/shareeapp-operator/src/Tpl/PayoneLink.pm index 70da085..4d1acfd 100755 --- a/copri4/shareeapp-operator/src/Tpl/PayoneLink.pm +++ b/copri4/shareeapp-operator/src/Tpl/PayoneLink.pm @@ -61,46 +61,60 @@ sub tpl(){ $feedb = $pl->prepaid_request($dbh,$ctadr,$aowner); $prepaidhash = $pri->collect_prepaid($dbh,$ctadr); } + my $ret_json = ""; print $q->start_form(),"\n"; print $q->hidden(-name=>"sessionid",-override=>1,-value=>"$R::sessionid"); print "
\n"; - print $q->div({-class=>'content_title3'},"$varenv->{cms}->{'iframe-prepay-account'}->{txt}"),"\n"; + print $q->div({-class=>'content_title3'},"$varenv->{cms}->{'iframe-prepaid-account'}->{txt}"),"\n"; if($prepaidhash->{prepaid_id}){ #print $q->hidden(-name=>"prepaid_id",-override=>1,-value=>"$prepaidhash->{prepaid_id}"); if($ctadr->{c_id} && $R::sharee_edit && $R::sharee_edit =~ /generate_payonelink/){ $ret_json = $pay->generate_payonelink($varenv,$ctadr,$prepaidhash,$R::prepaid_amount,$aowner); + $prepaidhash = $pri->collect_prepaid($dbh,$ctadr); } $prepaidhash->{prepaid_total} = sprintf('%.2f',$prepaidhash->{prepaid_total}); $prepaidhash->{prepaid_total} =~ s/\./,/; - $varenv->{cms}->{'iframe-prepay-prolog'}->{txt} =~ s/\n/
/g; - $varenv->{cms}->{'iframe-prepay-prolog'}->{txt} =~ s/::prepaid_total::/$prepaidhash->{prepaid_total} €<\/b>/g; - $varenv->{cms}->{'iframe-prepay-prolog'}->{txt} =~ s/::app_name::/$dbt->{merchant_ids}->{$varenv->{merchant_id}}->{app_name}<\/b>/g; - $varenv->{cms}->{'iframe-prepay-prolog'}->{txt} =~ s/::prepaid_id::/$prepaidhash->{prepaid_id}<\/b>/g; - print $q->div({-class=>'content2'}, "$varenv->{cms}->{'iframe-prepay-prolog'}->{txt}"),"\n"; + $varenv->{cms}->{'iframe-prepaid-prolog'}->{txt} =~ s/\n/
/g; + $varenv->{cms}->{'iframe-prepaid-prolog'}->{txt} =~ s/::prepaid_total::/$prepaidhash->{prepaid_total} €<\/b>/g; + $varenv->{cms}->{'iframe-prepaid-prolog'}->{txt} =~ s/::app_name::/$dbt->{merchant_ids}->{$varenv->{merchant_id}}->{app_name}<\/b>/g; + $varenv->{cms}->{'iframe-prepaid-prolog'}->{txt} =~ s/::prepaid_id::/$prepaidhash->{prepaid_id}<\/b>/g; + print $q->div({-class=>'content2'}, "$varenv->{cms}->{'iframe-prepaid-prolog'}->{txt}"),"\n"; + }else{ print $q->div({-class=>'content2'}, "$varenv->{cms}->{'iframe-failure-contact-hotline'}->{txt} $prepaidhash->{prepaid_id}"),"\n"; } if(!$ret_json || $ret_json =~ /failure/){ my $required="required"; - print $q->div({-class=>'content2', -style=>'color:#c83434;'}, "$varenv->{cms}->{'iframe-prepay-failure'}->{txt}"),"\n" if($ret_json =~ /failure/); + print $q->div({-class=>'content2', -style=>'color:#c83434;'}, "$varenv->{cms}->{'iframe-prepaid-failure'}->{txt}"),"\n" if($ret_json =~ /failure/); - my $label_des="$varenv->{cms}->{'iframe-prepay-input'}->{txt}"; - print $q->label({-for=>"prepaid_amount", -style=>'padding-top:1.5em;'},"$label_des"),"\n"; - print "\n"; + if($prepaidhash->{payone_link}){ + $varenv->{cms}->{'iframe-prepaid-emailinfo'}->{txt} =~ s/::mail_datetime::/$prepaidhash->{mail_datetime}/g; + $varenv->{cms}->{'iframe-prepaid-emailinfo'}->{txt} =~ s/::email::/$ctadr->{txt08}/g; + $varenv->{cms}->{'iframe-prepaid-emailinfo'}->{txt} =~ s/::payone_link::/
Test $prepaidhash->{payone_link}<\/a><\/b>/g if($users_sharee->{c_id} eq $dbt->{copri_conf}->{superu_id}); + $varenv->{cms}->{'iframe-prepaid-emailinfo'}->{txt} =~ s/::app_name::/$dbt->{merchant_ids}->{$varenv->{merchant_id}}->{app_name}<\/b>/g; + print $q->div({-class=>'content2'}, "$varenv->{cms}->{'iframe-prepaid-emailinfo'}->{txt}"),"\n"; + }else{ + my $label_des="$varenv->{cms}->{'iframe-prepaid-input'}->{txt}"; + print $q->label({-for=>"prepaid_amount", -style=>'padding-top:1.5em;'},"$label_des"),"\n"; + print "\n"; - print $q->div({-style=>'margin-top:1em;text-align:center;'},""),"\n"; + print $q->div({-style=>'margin-top:1em;text-align:center;'},""),"\n"; + } }elsif($ret_json){ - #TODO payone-link mailing - $varenv->{cms}->{'iframe-prepay-emailinfo'}->{txt} =~ s/::app_name::/$dbt->{merchant_ids}->{$varenv->{merchant_id}}->{app_name}<\/b>/g; - print $q->div({-class=>'content2', -style=>'color:#009899;'}, "$varenv->{cms}->{'iframe-prepay-emailinfo'}->{txt}"),"\n"; + #payone-link mailing will be done by $pay->generate_payonelink + $varenv->{cms}->{'iframe-prepaid-emailinfo'}->{txt} =~ s/::mail_datetime::/$prepaidhash->{mail_datetime}/g; + $varenv->{cms}->{'iframe-prepaid-emailinfo'}->{txt} =~ s/::email::/$ctadr->{txt08}/g; + $varenv->{cms}->{'iframe-prepaid-emailinfo'}->{txt} =~ s/::payone_link::/Test $prepaidhash->{payone_link}<\/a><\/b>/g if($ctadr->{c_id} eq $dbt->{copri_conf}->{superu_id}); + $varenv->{cms}->{'iframe-prepaid-emailinfo'}->{txt} =~ s/::app_name::/$dbt->{merchant_ids}->{$varenv->{merchant_id}}->{app_name}<\/b>/g; + print $q->div({-class=>'content2', -style=>'color:#009899;'}, "$varenv->{cms}->{'iframe-prepaid-emailinfo'}->{txt}"),"\n"; print $q->div({-class=>'content2'}, ""),"\n"; - print Dumper($ret_json) . "
\n"; + #print Dumper($ret_json) . "
\n"; } diff --git a/copri4/shareeapp-operator/src/Tpl/RentalData.pm b/copri4/shareeapp-operator/src/Tpl/RentalData.pm index 9cf4b4c..44b9830 100755 --- a/copri4/shareeapp-operator/src/Tpl/RentalData.pm +++ b/copri4/shareeapp-operator/src/Tpl/RentalData.pm @@ -194,6 +194,15 @@ sub tpl { }else{ #print $q->div({-class=>'content2'}, ""),"\n"; } + if($ctadr->{int03} == 3){ + my $prepaidhash = { prepaid_total => 0 }; + $prepaidhash = $pri->collect_prepaid($dbh,$ctadr); + $prepaidhash->{prepaid_total} = sprintf('%.2f',$prepaidhash->{prepaid_total}); + $prepaidhash->{prepaid_total} =~ s/\./,/; + $varenv->{cms}->{'iframe-prepaid-sum'}->{txt} =~ s/\n/
/g; + $varenv->{cms}->{'iframe-prepaid-sum'}->{txt} =~ s/::prepaid_total::/$prepaidhash->{prepaid_total} €<\/b>/g; + print $q->div({-class=>'content2'}, "$varenv->{cms}->{'iframe-prepaid-sum'}->{txt}"),"\n"; + } print $q->div({-class=>'content2'}, "$varenv->{cms}->{'iframe-invoice-note'}->{txt}"),"\n"; print $q->div({-class=>'content2'}, "$bonus_ak"),"\n" if($R::success && $R::success eq "txt15"); @@ -288,6 +297,7 @@ sub tpl { my $gesamt = 0; my $rabatt = ""; ($gesamt,$rabatt) = $pri->price2calc($cttpos->{$id}); + $gesamt *= -1 if($cttpos->{$id}->{template_id} && $cttpos->{$id}->{template_id} == 219);#prepaid $sum += $gesamt; $gesamt = $lb->round($gesamt); $gesamt = sprintf('%.2f',$gesamt); diff --git a/copri4/shareeconf/examples/global.cfg b/copri4/shareeconf/examples/global.cfg index af87dde..48dec0e 100755 --- a/copri4/shareeconf/examples/global.cfg +++ b/copri4/shareeconf/examples/global.cfg @@ -194,6 +194,7 @@ superu_id = "1234567" logdir = "/var/log/copri4" basedir = "/var/www/copri4" + test_accounts = "" @@ -288,13 +289,21 @@ faktura = "200007" invoice = "300008" invoicejournal = "300011" - mietjournal = "200012" + xjournal = "200012" alarmjournal = "200022" einstellung = "200019" serviceconfig = "300025" - payment_state = "SEPA-Lastschrift (payone)|Kreditkarte (payone)|Überweisung|Gutschrift" order_state = "|Zahlungseingang|Zahlung offen|eMail gesendet|in Arbeit|Betrugsfall" + + 1 = "SEPA-Lastschrift (payone)" + 2 = "Kreditkarte (payone)" + 3 = "Prepaid" + 4 = "Überweisung" + 5 = "Gutschrift" + 6 = "fehlgeschlagener Einzug" + 7 = "Zahlungsausfall" + 1 = "1. Zahlungserinnerung" 2 = "2. Zahlungserinnerung" @@ -309,7 +318,7 @@ style_jquery_ui = "external/jquery-ui-1.13.2/jquery-ui.min.css" js_bootstrap = "external/bootstrap-5.2.3-dist/js/bootstrap.bundle.min.js" style_bootstrap = "external/bootstrap-5.2.3-dist/css/bootstrap.min.css" - mod_active = "Waren|Faktura|Karte|Kunden|Mietjournal|Alarmjournal|Einstellung" + mod_active = "Waren|Faktura|Karte|Kunden|journal|Einstellung" modes = "login|logout|logout_sharee|user|manager|supervisor|admin|maintainer" diff --git a/copri4/shareedms-operator/src/Lib/Mlogic.pm b/copri4/shareedms-operator/src/Lib/Mlogic.pm index 20e4fde..9dd6378 100755 --- a/copri4/shareedms-operator/src/Lib/Mlogic.pm +++ b/copri4/shareedms-operator/src/Lib/Mlogic.pm @@ -186,8 +186,8 @@ sub tpl(){ # #0. menue my $aclass = "dropdown-item"; - $aclass = "nav-link" if($node->{$id}->{node_name} =~ /Mietjourna|Alarmjournal|Karte/); - $aclass = "nav-link" if($node->{$id}->{node_name} =~ /Mietjourna|Alarmjournal|Karte|App-feedback/ && $mod_active !~ /Kunden/); + $aclass = "nav-link" if($node->{$id}->{node_name} =~ /journal|Karte/); + $aclass = "nav-link" if($node->{$id}->{node_name} =~ /journal|Karte|App-feedback/ && $mod_active !~ /Kunden/); if($users_dms->{u_id} && ($users_dms->{int01} == 2 && $node_meta->{ct_table} =~ /content$/) || ($users_dms->{u_id} == $dbt->{copri_conf}->{superu_id})){ my $url = "$topath?node2edit=edit_relation\&main_id=$node->{$id}->{main_id}"; $lmenu0 = $but->event_button("$topath","$node->{$id}->{node_name}","$node->{$id}->{main_id}","$aclass $mclass","","$users_dms->{u_id}","$url");