source: trunk/Modules/Finance/Manage.php

Last change on this file was 968, checked in by chronos, 7 weeks ago
  • Modified: Improved content of email with finance account state.
  • Added: Customer IS action to generate finance email into email queue.
File size: 24.0 KB
Line 
1<?php
2
3class PageFinanceManage extends Page
4{
5 function __construct(System $System)
6 {
7 parent::__construct($System);
8 $this->Title = 'Správa financí';
9 $this->ParentClass = 'PageFinance';
10 }
11
12 function Show(): string
13 {
14 $Output = '';
15 if (!ModuleUser::Cast($this->System->GetModule('User'))->User->CheckPermission('Finance', 'Manage'))
16 return 'Nemáte oprávnění';
17
18 if (array_key_exists('Operation', $_GET)) $Operation = $_GET['Operation'];
19 else $Operation = '';
20 switch ($Operation)
21 {
22 case 'Recalculate':
23 $Output .= ModuleFinance::Cast($this->System->GetModule('Finance'))->Finance->RecalculateMemberPayment();
24 break;
25 case 'ShowMonthlyPayment':
26 $Output = $this->ShowMonthlyPayment();
27 break;
28 case 'ProcessMonthlyPayment':
29 $Output = $this->ProcessMonthlyPayment();
30 break;
31 case 'GenerateBills':
32 $Output = $this->GenerateBills();
33 break;
34 case 'RegenerateInvoice':
35 $Output = $this->GenerateInvoice('AND (Id='.$_GET['i'].')');
36 break;
37 case 'RegenerateOperation':
38 $Output = $this->GenerateOperation('AND (Id='.$_GET['i'].')');
39 break;
40 case 'SendPaymentEmail':
41 $Output = $this->SendPaymentEmail($_GET['i']);
42 break;
43 default:
44 //$Output .= '<a href="?Operation=Recalculate">Přepočet financí</a><br />';
45 $Output .= '<a href="?Operation=ShowMonthlyPayment">Měsíční vyúčtování</a><br />';
46 $Output .= '<a href="'.$this->System->Link('/finance/zivnost/').'">Živnost</a><br />';
47 $Output .= '<a href="?Operation=GenerateBills">Generovat chybějící doklady</a><br />';
48 $Output .= '<a href="'.$this->System->Link('/finance/import/').'">Import plateb</a><br />';
49 }
50 return $Output;
51 }
52
53 /* Get first day and last day of given billing period. Periods are aligned with year start/end. */
54 function GetBillingPeriod(int $Period): array
55 {
56 $Time = time();
57 $Year = date('Y', $Time);
58
59 $MonthCount = ModuleFinance::Cast($this->System->GetModule('Finance'))->Finance->BillingPeriods[$Period]['MonthCount'];
60 if ($MonthCount <= 0) return array('From' => NULL, 'To' => NULL, 'MonthCount' => 0);
61 $MonthCurrent = date('n', $Time);
62
63 /* Get start and end of aligned period */
64 $MonthFrom = floor(($MonthCurrent - 1) / $MonthCount) * $MonthCount + 1;
65 $MonthTo = $MonthFrom + $MonthCount - 1;
66
67 /* Use period from current month to end month so months before current month are cut out */
68 $MonthCount = $MonthTo - $MonthCurrent + 1;
69 $MonthFrom = $MonthCurrent;
70
71 /* Get first and last day of period */
72 $PeriodFrom = mktime(0, 0, 0, $MonthFrom, 1, $Year);
73 $PeriodTo = mktime(0, 0, 0, $MonthTo, date('t', mktime(0, 0, 0, $MonthTo, 1, $Year)), $Year);
74
75 return array('From' => $PeriodFrom, 'To' => $PeriodTo, 'MonthCount' => $MonthCount);
76 }
77
78 function ShowMonthlyPayment(): string
79 {
80 if (!ModuleUser::Cast($this->System->GetModule('User'))->User->CheckPermission('Finance', 'Manage')) return 'Nemáte oprávnění';
81 $SQL = 'SELECT `Member`.*, `MemberPayment`.`MonthlyTotal` AS `Monthly`, '.
82 '`MemberPayment`.`Cash` AS `Cash`, '.
83 '(SELECT GROUP_CONCAT(`Service`.`Name`) FROM `ServiceCustomerRel` LEFT JOIN `Service` '.
84 'ON `Service`.`Id`=`ServiceCustomerRel`.`Service` WHERE `ServiceCustomerRel`.`Customer`=`Member`.`Id` AND '.
85 '`ServiceCustomerRel`.`ChangeAction` IS NULL) AS `ServicesNextMonth`, '.
86 'UNIX_TIMESTAMP(`Member`.`BillingPeriodLastDate`) AS `LastDate`, `Subject`.`Name` AS `SubjectName`, '.
87 '`FinanceBillingPeriod`.`Name` AS `BillingPeriodName` '.
88 'FROM `MemberPayment` JOIN `Member` ON `Member`.`Id`=`MemberPayment`.`Member` JOIN `Subject` '.
89 'ON `Subject`.`Id`=`Member`.`Subject` LEFT JOIN `FinanceBillingPeriod` ON '.
90 '`FinanceBillingPeriod`.`Id`=`Member`.`BillingPeriod` WHERE (`Member`.`Blocked` = 0)'.
91 'AND (`Member`.`BillingPeriod` > 1) AND (`MemberPayment`.`MonthlyTotal` != 0)';
92
93 $DbResult = $this->Database->query('SELECT COUNT(*) FROM ('.$SQL.') AS T');
94 $DbRow = $DbResult->fetch_row();
95 $PageList = GetPageList('MonthlyPayment', $DbRow[0]);
96
97 $Output = $PageList['Output'];
98 $Output .= '<table class="WideTable" style="font-size: small;">';
99
100 $TableColumns = array(
101 array('Name' => 'SubjectName', 'Title' => 'Jméno'),
102 array('Name' => 'Monthly', 'Title' => 'Platba'),
103 array('Name' => 'Cash', 'Title' => 'Kredit'),
104 array('Name' => 'LastDate', 'Title' => 'Poslední fakturace'),
105 array('Name' => 'ServicesNextMonth', 'Title' => 'Služby'),
106 array('Name' => 'BillingPeriodName', 'Title' => 'Perioda'),
107 );
108 $Order = GetOrderTableHeader('MonthlyPayment', $TableColumns, 'SubjectName', 0);
109 $Output .= $Order['Output'];
110
111 $Query = $SQL.' '.$Order['SQL'].$PageList['SQLLimit'];
112
113 $DbResult = $this->Database->query($Query);
114 while ($Row = $DbResult->fetch_assoc())
115 {
116 $Output .= '<tr>'.
117 '<td>'.$Row['SubjectName'].'</td>'.
118 '<td>'.$Row['Monthly'].'</td>'.
119 '<td>'.$Row['Cash'].'</td>'.
120 '<td>'.date('j.n.Y', $Row['LastDate']).'</td>'.
121 '<td>'.$Row['ServicesNextMonth'].'</td>'.
122 '<td>'.$Row['BillingPeriodName'].'</td>'.
123 '</tr>';
124 }
125 $Output .= '</table>';
126 $Output .= $PageList['Output'];
127 $Output .= '<a href="?Operation=ProcessMonthlyPayment">Generovat faktury</a>';
128 return $Output;
129 }
130
131 function InsertInvoice(string $Subject, string $TimeCreation, string $TimeDue, array $Items,
132 array $Group, float $PeriodFrom, float $PeriodTo): string
133 {
134 global $LastInsertTime;
135
136 $Finance = ModuleFinance::Cast($this->System->GetModule('Finance'))->Finance;
137
138 $Year = date('Y', $TimeCreation);
139 $BillCode = ModuleDocument::Cast($this->System->GetModule('Document'))->GetNextDocumentLineNumberId($Group['DocumentLine'], $Year);
140 $SumValue = 0;
141 foreach ($Items as $Item) {
142 $SumValue = $SumValue + $Item['Price'] * $Item['Quantity'];
143 }
144 $SumValue = round($SumValue, $Finance->Rounding);
145 $this->Database->insert('FinanceInvoice', array(
146 'Subject' => $Subject, 'Time' => TimeToMysqlDateTime($TimeCreation),
147 'TimeDue' => TimeToMysqlDateTime($TimeDue), 'Value' => $SumValue * $Group['ValueSign'],
148 'BillCode' => $BillCode,
149 'PeriodFrom' => TimeToMysqlDate($PeriodFrom), 'PeriodTo' => TimeToMysqlDate($PeriodTo),
150 'Generate' => 1, 'Group' => $Group['Id']));
151 $InvoiceId = $this->Database->insert_id;
152 foreach ($Items as $Item)
153 $this->Database->insert('FinanceInvoiceItem', array('FinanceInvoice' => $InvoiceId,
154 'Description' => $Item['Description'], 'Price' => $Item['Price'],
155 'Quantity' => $Item['Quantity'], 'VAT' => $Item['VAT']));
156 //$LastInsertTime = $Time;
157 //$this->CheckAdvancesAndLiabilities($Subject);
158 return $InvoiceId;
159 }
160
161 function ProduceInvoices(): string
162 {
163 $Output = '';
164
165 // Produce accounting items
166 $DbResult = $this->Database->query('SELECT `Member`.*, `MemberPayment`.`MonthlyTotal` AS `MonthlyTotal`, '.
167 'UNIX_TIMESTAMP(`Member`.`BillingPeriodLastDate`) AS `BillingPeriodLastUnixTime`, `Subject`.`Name` AS `SubjectName`,'.
168 '`MemberPayment`.`MonthlyPlus` AS `MonthlyPlus` '.
169 'FROM `MemberPayment` JOIN `Member` ON `Member`.`Id`=`MemberPayment`.`Member` '.
170 'JOIN `Subject` ON `Subject`.`Id`=`Member`.`Subject`');
171 while ($Member = $DbResult->fetch_assoc())
172 {
173 $Output .= $Member['SubjectName'].': ';
174 $Period = $this->GetBillingPeriod($Member['BillingPeriod']);
175
176 // Check if need to produce new invoice for customer
177 if (($Period['MonthCount'] > 0) and ($Member['Blocked'] == 0) and
178 ($Period['From'] > $Member['BillingPeriodLastUnixTime']))
179 {
180 $InvoiceItems = array();
181 $MonthlyTotal = 0;
182 $DbResult2 = $this->Database->query('SELECT `Service`.* '.
183 'FROM `ServiceCustomerRel` LEFT JOIN `Service` '.
184 'ON `Service`.`Id`=`ServiceCustomerRel`.`Service` '.
185 'WHERE (`ServiceCustomerRel`.`Customer`='.
186 $Member['Id'].') AND (`ServiceCustomerRel`.`ChangeAction` IS NULL) ');
187 while ($Service = $DbResult2->fetch_assoc())
188 {
189 $InvoiceItems[] = array('Description' => $Service['Name'], 'Price' => $Service['Price'],
190 'Quantity' => $Period['MonthCount'], 'VAT' => ModuleFinance::Cast($this->System->GetModule('Finance'))->Finance->GetVATByType($Service['VAT']));
191 $MonthlyTotal += $Service['Price'];
192 }
193 $PayPerPeriod = $MonthlyTotal * $Period['MonthCount'];
194 // We can't produce negative invoice except storno invoice.
195 // TODO: In case of negative invoice it is not sufficient to reverse invoicing direction
196 // Other subject should invoice only positive items. Negative items should be somehow removed.
197 if ($MonthlyTotal >= 0)
198 {
199 $InvoiceGroupId = INVOICE_GROUP_OUT;
200 } else
201 {
202 $InvoiceGroupId = INVOICE_GROUP_IN;
203 }
204
205 // Load invoice group
206 $FinanceGroup = ModuleFinance::Cast($this->System->GetModule('Finance'))->Finance->GetFinanceGroupById($InvoiceGroupId, 'FinanceInvoiceGroup');
207 foreach ($InvoiceItems as $Index => $Item)
208 {
209 $InvoiceItems[$Index]['Price'] = $Item['Price'] * $FinanceGroup['ValueSign'];
210 }
211
212 if ($PayPerPeriod != 0)
213 {
214 $TimePeriodText = date('j.n.Y', $Period['From']).' - '.date('j.n.Y', $Period['To']);
215 $Output .= $TimePeriodText.': '.$MonthlyTotal.' * '.$Period['MonthCount'].' = '.$PayPerPeriod;
216 $this->InsertInvoice($Member['Subject'], time(), time() + 3600 * 24 * INVOICE_DUE_DAYS,
217 $InvoiceItems, $FinanceGroup, $Period['From'], $Period['To']);
218
219 $Output .= $this->SendPaymentEmail($Member['Id']);
220 }
221 // Update last billing day
222 $this->Database->update('Member', '`Id`='.$Member['Id'],
223 array('BillingPeriodLastDate' => TimeToMysqlDateTime($Period['To'])));
224 }
225 $Output .= "\n";
226 }
227 return $Output;
228 }
229
230 function TableUpdateChanges(string $Table): void
231 {
232 $Time = time();
233 $DbResult = $this->Database->select($Table, '*', '(`ChangeAction` IS NOT NULL) AND '.
234 '(`ChangeTime` <= "'.TimeToMysqlDateTime($Time).'") ORDER BY `ChangeTime` ASC');
235 while ($Service = $DbResult->fetch_assoc())
236 {
237 if ($Service['ChangeAction'] == 'add')
238 {
239 unset($Service['Id']);
240 unset($Service['ChangeReplaceId']);
241 unset($Service['ChangeAction']);
242 unset($Service['ChangeTime']);
243 $this->Database->insert($Table, $Service);
244 } else
245 if ($Service['ChangeAction'] == 'modify')
246 {
247 unset($Service['Id']);
248 unset($Service['ChangeAction']);
249 $ReplaceId = $Service['ChangeReplaceId'];
250 unset($Service['ChangeReplaceId']);
251 unset($Service['ChangeTime']);
252 $this->Database->update($Table, '`Id`='.$ReplaceId, $Service);
253 } else
254 if ($Service['ChangeAction'] == 'delete')
255 {
256 $this->Database->delete($Table, '`Id`='.$Service['ReplaceId']);
257 }
258 }
259 $this->Database->delete($Table, '(`ChangeAction` IS NOT NULL) AND (`ChangeTime` <= "'.TimeToMysqlDateTime($Time).'")');
260 }
261
262 function ProcessTableUpdates(): string
263 {
264 // Update customers
265 $Output = 'Měním zákazníky...'."\n";
266 $this->TableUpdateChanges('Member');
267
268 // Update finance charge
269 $Output = 'Měním aktuální parametry sítě...'."\n";
270 $this->TableUpdateChanges('FinanceCharge');
271
272 // Update services
273 $Output .= 'Aktualizuji služby....'."\n";
274 $this->TableUpdateChanges('Service');
275
276 // Update customer service selections
277 $Output .= 'Aktualizuji výběr služeb zákazníků....'."\n";
278 $this->TableUpdateChanges('ServiceCustomerRel');
279
280 return $Output;
281 }
282
283 function ProcessMonthlyPayment(): string
284 {
285 if (!ModuleUser::Cast($this->System->GetModule('User'))->User->CheckPermission('Finance', 'Manage')) return 'Nemáte oprávnění';
286 $Output = '';
287
288 $Output .= $this->ProcessTableUpdates();
289
290 $Finance = &ModuleFinance::Cast($this->System->GetModule('Finance'))->Finance;
291 $Finance->LoadMonthParameters(0);
292
293 // Načti poslední měsíční přehled a nastavení
294 $DbResult = $this->Database->select('FinanceMonthlyOverall', '*', '1 ORDER BY `Date` DESC LIMIT 1');
295 $Overall = $DbResult->fetch_array();
296
297 $Output .= 'Datum: '.date('j.n.Y')."\n";
298
299 $DateParts = explode('-', $Overall['Date']);
300 $MonthLast = $DateParts[1];
301 $YearLast = $DateParts[0];
302 $MonthCurrent = date('m') + 0;
303 $YearCurrent = date('Y') + 0;
304
305 $Output .= $Finance->RecalculateMemberPayment();
306
307 $DbResult = $this->Database->query('SELECT SUM(`Cash`) FROM `MemberPayment`');
308 $Row = $DbResult->fetch_row();
309 $TotalMemberCash = $Row[0];
310 $Output .= 'Stav pokladny: Členové('.round($TotalMemberCash).')'."\n";
311
312 $DbResult = $this->Database->query('SELECT SUM(`Product`.`Consumption`) AS `Consumption` FROM `StockSerialNumber` '.
313 'JOIN `Product` ON `StockSerialNumber`.`Product` = `Product`.`Id` WHERE (`StockSerialNumber`.`TimeElimination` IS NULL) ');
314 $Row = $DbResult->fetch_row();
315 $TotalConsumption = $Row[0];
316 $TotalConsumptionCost = $Finance->W2Kc($TotalConsumption);
317
318 $SpravaCelkem = $Finance->Sprava * $Finance->SpravaUsers;
319 $Output .= 'Kontrola placení (Zaplaceno-Sprava-Internet): '.$Finance->TotalPaid.'-'.$SpravaCelkem.'-'.$Finance->Internet.'='.($Finance->TotalPaid - $SpravaCelkem - $Finance->Internet)."\n";
320
321 // Zkontrolovat odečtení měsíčního poplatku
322 $Output .= 'Kontrola odečtení poplatků: Poslední měsíc-'.$MonthLast.' Aktuální měsíc-'.$MonthCurrent."\n";
323 if (($MonthCurrent != $MonthLast) or ($YearCurrent != $YearLast))
324 {
325 $Output .= 'Odečítám pravidelný poplatek...'."\n";
326 $Output .= $this->ProduceInvoices();
327
328 $Output .= 'Přidávám měsíční přehled...'."\n";
329 $DbResult = $this->Database->query('SELECT * FROM `FinanceCharge` WHERE (`ChangeAction` IS NULL) LIMIT 1');
330 $Charge = $DbResult->fetch_assoc();
331 $this->Database->insert('FinanceMonthlyOverall', array('Date' => 'NOW()',
332 'Money' => $Finance->Internet, 'kWh' => $Finance->kWh,
333 'Administration' => $Finance->Sprava, 'AdministrationTotal' => $SpravaCelkem,
334 'ConsumptionTotal' => $TotalConsumptionCost, 'TotalPaid' => $Finance->TotalPaid,
335 'BaseTariffPrice' => $Charge['BaseTariffPrice'],
336 'TopTariffPrice' => $Charge['TopTariffPrice'], 'MemberCount' => $Finance->InternetUsers));
337
338 $Finance->RecalculateMemberPayment();
339
340 // Restart traffic shaping
341 //$this->Database->update('NetworkConfiguration', 'Id = 3', array('Changed' => 1));
342 //flush();
343 //$this->GenerateBills();
344 ModuleLog::Cast($this->System->GetModule('Log'))->NewRecord('Finance', 'ProcessMonthlyPayment', $Output);
345 }
346 $Output = str_replace("\n", '<br/>', $Output);
347 return $Output;
348 }
349
350 function SendPaymentEmail(string $MemberId, string $FileId = ''): string
351 {
352 $Finance = &ModuleFinance::Cast($this->System->GetModule('Finance'))->Finance;
353 $Finance->LoadMonthParameters(0);
354
355 if (!ModuleUser::Cast($this->System->GetModule('User'))->User->CheckPermission('Finance', 'Manage')) return 'Nemáte oprávnění';
356 global $Config;
357
358 $DbResult = $this->Database->select('Member', '*', '`Id`='.$MemberId);
359 $Member = $DbResult->fetch_assoc();
360
361 $DbResult = $this->Database->select('MemberPayment', '*', '`Member`='.$MemberId);
362 $MemberPayment = $DbResult->fetch_assoc();
363
364 $DbResult = $this->Database->select('Subject', 'Name', '`Id`='.$Member['Subject']);
365 $Subject = $DbResult->fetch_assoc();
366
367 $DbResult = $this->Database->select('User', '*', '`Id`='.$Member['ResponsibleUser']);
368 $User = $DbResult->fetch_assoc();
369
370 $DbResult = $this->Database->select('Subject', '*', '`Id`='.$Config['Finance']['MainSubjectId']);
371 $MainSubject = $DbResult->fetch_assoc();
372
373 $DbResult = $this->Database->select('Company', '*', '`Id`='.$Config['Finance']['MainCompanyId']);
374 $MainCompany = $DbResult->fetch_assoc();
375
376 $Period = $this->GetBillingPeriod($Member['BillingPeriod']);
377
378 $DbResult = $this->Database->query('SELECT `FinanceBankAccount`.*, '.
379 'CONCAT(`FinanceBankAccount`.`Number`, "/", `FinanceBank`.`Code`) AS `NumberFull` FROM `FinanceBankAccount` '.
380 'JOIN `FinanceBank` ON `FinanceBank`.`Id`=`FinanceBankAccount`.`Bank` '.
381 'WHERE (`FinanceBankAccount`.`Subject`='.$Config['Finance']['MainSubjectId'].') '.
382 'AND (`FinanceBankAccount`.`Use`=1)');
383 $MainSubjectAccount = $DbResult->fetch_assoc();
384
385 if ($User['Email'] != '')
386 {
387 $Title = 'Pravidelné vyúčtování služeb '.$MainCompany['Name'];
388 $Content = 'Dobrý den,<br/><br/>'.
389 'Zasíláme vyúčtování klienta <strong>'.$Subject['Name'].'</strong> zastoupeného uživatelem <strong>'.
390 $User['Name'].'</strong> ke dni <strong>'.Core::Cast($this->System)->HumanDate(time()).'</strong>.<br/><br/>'."\n".
391 'Vaše aktuální služby: ';
392 $DbResult = $this->Database->query('SELECT GROUP_CONCAT(`Service`.`Name`) AS `Name` FROM `ServiceCustomerRel` LEFT JOIN `Service` '.
393 'ON `Service`.`Id`=`ServiceCustomerRel`.`Service` WHERE (`ServiceCustomerRel`.`Customer`='.$Member['Id'].') '.
394 'AND (`ServiceCustomerRel`.`ChangeAction` IS NULL)');
395 $Service = $DbResult->fetch_assoc();
396 $Content .= '<strong>'.$Service['Name'].'</strong><br />'."\n".
397 'Vaše platební období: <strong>'.ModuleFinance::Cast($this->System->GetModule('Finance'))->Finance->BillingPeriods[$Member['BillingPeriod']]['Name'].'</strong><br />'."\n".
398 'Pravidelná platba za období: <strong>'.($MemberPayment['MonthlyTotal'] * $Period['MonthCount']).' Kč</strong><br />'."\n".
399 'Bankovní účet: <strong>'.$MainSubjectAccount['NumberFull'].'</strong><br/>'."\n".
400 'Variabilní symbol: <strong>'.$Member['Subject'].'</strong><br/>'."\n".
401 'Stav vašeho účtu: <strong>'.($MemberPayment['Cash'] - $MemberPayment['MonthlyTotal'] * $Period['MonthCount']).' Kč</strong><br /><br />'."\n";
402 $Content .= 'Nové finanční operace:<br/>'.
403 '<table style="margin-left: auto; margin-right: auto; border-style: solid; border-width: 1px; border-collapse: collapse;">'.
404 '<tr><th style="border-style: solid; border-width: 1px; padding: 1px 5px 1px 5px; text-align: center; font-weight: bold;">Čas</th>'.
405 '<th style="border-style: solid; border-width: 1px; padding: 1px 5px 1px 5px; text-align: center; font-weight: bold;">Popis</th>'.
406 '<th style="border-style: solid; border-width: 1px; padding: 1px 5px 1px 5px; text-align: center; font-weight: bold;">Částka [Kč]</th></tr>'."\n";
407 if ($Member['PaymentEmailTime'] <> 'NULL')
408 {
409 $Where = ' WHERE (`T1`.`Time` > "'.$Member['PaymentEmailTime'].'")';
410 } else
411 {
412 $Where = '';
413 }
414 $DbResult = $this->Database->query('SELECT T1.* FROM ((SELECT `Text`, `Time`, `Value`, `File` FROM `FinanceOperation` WHERE (`Subject`='.$Member['Subject'].')) UNION ALL '.
415 '(SELECT (SELECT GROUP_CONCAT(`Description` SEPARATOR ", ") FROM `FinanceInvoiceItem` '.
416 'WHERE `FinanceInvoiceItem`.`FinanceInvoice` = `FinanceInvoice`.`Id`) AS `Text`, '.
417 '`Time`, -`Value`, `File` FROM `FinanceInvoice` WHERE (`Subject`='.$Member['Subject'].')) ORDER BY `Time` DESC) AS `T1`'.$Where);
418 while ($DbRow = $DbResult->fetch_assoc())
419 {
420 $Text = $DbRow['Text'];
421 $Content .= '<tr><td style="border-style: solid; border-width: 1px; padding: 1px 5px 1px 5px; text-align: center;">'.HumanDate($DbRow['Time']).'</td>'.
422 '<td style="border-style: solid; border-width: 1px; padding: 1px 5px 1px 5px; text-align: center;">'.$Text.'</td>'.
423 '<td style="border-style: solid; border-width: 1px; padding: 1px 5px 1px 5px; text-align: center;">'.$DbRow['Value'].'</td></tr>'."\n";
424 }
425 $Content .= '</table><br />'."\n".
426 'Pro aktuální informace, prohlížení elektronických dokladů a možnost změny údajů se prosím přihlaste na stránkách '.
427 '<a href="https://'.$Config['Web']['Host'].$Config['Web']['RootFolder'].'">https://'.
428 $Config['Web']['Host'].$Config['Web']['RootFolder'].'</a>.<br/><br/>'."\n";
429
430 $Content .= '<br/>Tento email je generován automaticky. V případě zjištění nesrovnalostí prosím napište zpět.';
431
432 $Content .= '<br/><br/>S pozdravem,<br/>'.$MainCompany['Name'].'<br/><a href="'.$MainSubject['WWW'].'">'.
433 str_replace(array('https:', '/'), '', $MainSubject['WWW']).'</a>';
434
435 ModuleEmailQueue::Cast($this->System->GetModule('EmailQueue'))->AddItem($User['Name'].' <'.$User['Email'].'>', $Title, $Content,
436 $Config['Web']['Admin'].' <'.$Config['Web']['AdminEmail'].'>');
437 $this->Database->update('Member', 'Id='.$Member['Id'], array('PaymentEmailTime' => 'NOW()'));
438 $Output = '';
439 } else $Output = 'Uživatel '.$User['Name'].' nemá email.';
440 return $Output;
441 }
442
443 function GenerateInvoice(string $Where): string
444 {
445 $DirectoryId = ModuleFinance::Cast($this->System->GetModule('Finance'))->Finance->DirectoryId;
446 $Output = '';
447 $DbResult = $this->Database->query('SELECT * FROM `FinanceInvoice` WHERE (`BillCode` <> "") '.
448 'AND (`Value` != 0) AND (`Generate` = 1)'.$Where);
449 while ($Row = $DbResult->fetch_assoc())
450 {
451 if ($Row['File'] == null)
452 {
453 $this->Database->insert('File', array('Name' => '', 'Size' => 0, 'Directory' => $DirectoryId, 'Time' => 'NOW()',
454 'Hash' => 'SHA1(CONCAT(Id,Name,Size,Time))'));
455 $FileId = $this->Database->insert_id;
456 } else $FileId = $Row['File'];
457 $FileName = 'doklad-'.$FileId.'.pdf';
458 $Bill = new BillInvoice($this->System);
459 $Bill->InvoiceId = $Row['Id'];
460 $FullFileName = ModuleFile::Cast($this->System->GetModule('File'))->File->GetDir($DirectoryId).$FileName;
461 $Bill->SaveToFile($FullFileName);
462 if (file_exists($FullFileName))
463 {
464 $this->Database->update('File', 'Id='.$FileId, array('Name' => $FileName, 'Size' => filesize($FullFileName), 'Hash' => 'SHA1(CONCAT(Id,Name,Size,Time))'));
465 $this->Database->update('FinanceInvoice', 'Id='.$Row['Id'], array('File' => $FileId));
466 $Output .= 'Faktura '.$Row['Id'].' vygenerována do souboru '.$FileName.'<br/>'."\n";
467 } else $Output .= 'Soubor "'.$FullFileName.'" se nepodařilo uložit.';
468 }
469 return $Output;
470 }
471
472 function GenerateOperation(string $Where): string
473 {
474 $DirectoryId = ModuleFinance::Cast($this->System->GetModule('Finance'))->Finance->DirectoryId;
475 $Output = '';
476 $DbResult = $this->Database->query('SELECT * FROM `FinanceOperation` WHERE (`BillCode` <> "") '.
477 'AND (`Value` != 0) AND (`Generate` = 1)'.$Where);
478 while ($Row = $DbResult->fetch_assoc())
479 {
480 if ($Row['File'] == null)
481 {
482 $DbResult2 = $this->Database->insert('File', array('Name' => '', 'Size' => 0,
483 'Directory' => $DirectoryId, 'Time' => 'NOW()', 'Hash' => 'SHA1(CONCAT(Id,Name,Size,Time))'));
484 $FileId = $this->Database->insert_id;
485 } else $FileId = $Row['File'];
486 $FileName = 'doklad2-'.$FileId.'.pdf';
487 $Bill = new BillOperation($this->System);
488 $Bill->OperationId = $Row['Id'];
489 $FullFileName = ModuleFile::Cast($this->System->GetModule('File'))->File->GetDir($DirectoryId).$FileName;
490 $Bill->SaveToFile($FullFileName);
491 if (file_exists($FullFileName))
492 {
493 $this->Database->update('File', 'Id='.$FileId, array('Name' => $FileName, 'Size' => filesize($FullFileName), 'Hash' => 'SHA1(CONCAT(Id,Name,Size,Time))'));
494 $this->Database->update('FinanceOperation', 'Id='.$Row['Id'], array('File' => $FileId));
495 $Output .= 'Doklad pro platbu '.$Row['Id'].' vygenerován do souboru '.$FileName.'<br/>'."\n";
496 } else $Output .= 'Soubor "'.$FullFileName.'" se nepodařilo uložit.';
497 }
498 return $Output;
499 }
500
501 function GenerateBills(): string
502 {
503 $Output = '';
504 // Generate PDF files for new invoices and operations
505 $Output .= $this->GenerateInvoice(' AND (`File` IS NULL)');
506 $Output .= $this->GenerateOperation(' AND (`File` IS NULL)');
507 return $Output;
508 }
509}
Note: See TracBrowser for help on using the repository browser.