Merge branch 'features/feature-client-export-statistic' into staging

This commit is contained in:
Tiavina 2024-12-30 08:17:59 +03:00
commit 254a8f2cf4
26 changed files with 347 additions and 33 deletions

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

View File

@ -17,6 +17,7 @@ use \Datetime;
use \DatetimeImmutable;
use \IntlDateFormatter;
use \FPDF;
use OCA\Gestion\Service\ExportClientStatisticService;
use OCA\Gestion\Service\ExportThanatoStatisticService;
use Ramsey\Uuid\Uuid;
@ -40,6 +41,9 @@ class PageController extends Controller {
/** @var ExportThanatoStatisticService */
private $exportThanatoStatisticService;
/** @var \OCA\Gestion\Service\ExportClientStatisticService */
private $exportClientStatisticService;
/**
* Constructor
*/
@ -53,7 +57,8 @@ class PageController extends Controller {
Iconfig $config,
IUserSession $userSession,
IGroupManager $groupManager,
ExportThanatoStatisticService $exportThanatoStatisticService) {
ExportThanatoStatisticService $exportThanatoStatisticService,
ExportClientStatisticService $exportClientStatisticService) {
parent::__construct($AppName, $request);
@ -63,6 +68,7 @@ class PageController extends Controller {
$this->mailer = $mailer;
$this->config = $config;
$this->exportThanatoStatisticService = $exportThanatoStatisticService;
$this->exportClientStatisticService = $exportClientStatisticService;
//$this->fpdf = $fpdf;
if ($userSession->isLoggedIn()) {
@ -2578,4 +2584,42 @@ class PageController extends Controller {
catch(\OCP\Files\NotFoundException $e) { }
}
/**
* @NoAdminRequired
* @NoCSRFRequired
* @param array $clientIdsToExport
*
*/
public function exportClientStatistic($clientIdsToExport){
if(empty($clientIdsToExport)){
return "";
}
$exportData = $this->myDb->getExportClientStatData($clientIdsToExport);
if(empty($exportData)){
return "";
}
try{
$current_config = json_decode($this->myDb->getConfiguration($this->idNextcloud));
$clean_folder = html_entity_decode($current_config[0]->path).'/';
$_clean_folder = $clean_folder.'STATISTIQUES/CLIENTS/';
try {
$this->storage->newFolder($_clean_folder);
}
catch(\OCP\Files\NotPermittedException $e) {
}
$fileHeader = $this->exportClientStatisticService->getExportClientFileHeader();
$fileContent = $this->exportClientStatisticService->populateExportDataIntoFileContent($exportData,$fileHeader);
$fileName = $this->exportClientStatisticService->getFileName($clientIdsToExport);
$fileNamePath = $_clean_folder."STAT-CLIENTS-" . $fileName .'.csv';
$this->storage->newFile($fileNamePath);
$file = $this->storage->get($fileNamePath);
$file->putContent($fileContent);
return $fileNamePath;
}
catch(\OCP\Files\NotFoundException $e) { }
}
}

View File

@ -1965,16 +1965,132 @@ class Bdd {
return null;
}
/**
* @param $calendarData
* @return bool|string
*/
private function readBlob($calendarData) {
if (is_resource($calendarData)) {
return stream_get_contents($calendarData);
}
private function getProduitsDevisStatistic($devisId){
$sql = "SELECT
produit_devis.id,
produit_devis.produit_id,
produit_devis.quantite,
produit_devis.discount,
produit.prix_unitaire as produit_price
FROM ".$this->tableprefix ."produit_devis as produit_devis
LEFT JOIN ".$this->tableprefix."produit as produit on produit_devis.produit_id = produit.id
WHERE produit_devis.devis_id = ?;";
return $calendarData;
}
$produitList = $this->execSQLNoJsonReturn(
$sql,
[$devisId]);
$productsCount = count($produitList);
$productsPrice = 0;
foreach($produitList as $produit){
$productsPrice += $produit["quantite"] * $produit["produit_price"];
}
return [
"count" => $productsCount,
"total_price" => $productsPrice
];
}
private function getClientFactureStatisticPerMonth($clientId){
$currentYear = date('Y');
$monthLists = range(1,12);
$data = [] ;
foreach($monthLists as $monthValue){
if(!isset($data[$monthValue])){
$data[$monthValue] = [];
}
$sql = "SELECT
facture.id,
facture.date,
facture.date_paiement,
devis.id as devis_id,
devis.id_client as devis_client_id
FROM ".$this->tableprefix."facture as facture
LEFT JOIN ".$this->tableprefix."devis as devis on facture.id_devis = devis.id
WHERE YEAR(facture.date_paiement) = ? AND
MONTH(facture.date_paiement) = ? AND
devis.id_client = ?
ORDER BY facture.date_paiement ASC;";
$factureList = $this->execSQLNoJsonReturn(
$sql,
[$currentYear,$monthValue,$clientId]);
$defuntCount = count($factureList);
$produitsCount = 0;
$produitsPrice = 0;
foreach($factureList as $facture){
$devisProduitStat = $this->getProduitsDevisStatistic($facture["devis_id"]);
$produitsCount+= $devisProduitStat["count"];
$produitsPrice+= $devisProduitStat["total_price"];
}
$data[$monthValue] = [
"defunt_count" => $defuntCount,
"produit_count" => $produitsCount,
"total_price" => $produitsPrice,
"year" => $currentYear
];
}
return $data;
}
public function getExportClientStatData(array $clientIds){
$data = [];
foreach($clientIds as $clientId){
if(!isset($data[$clientId])){
$data[$clientId] = [];
}
//get client name
$clientName = "Default client name";
$client = $this->getClientById($clientId);
if($client != null){
$clientName = trim($client["client_nom"]) . '-' .trim($client['client_entreprise']);
}
$data[$clientId]["client_name"] = $clientName;
$data[$clientId]["client_data"] = $this->getClientFactureStatisticPerMonth($clientId);
}
return $data;
}
private function getClientById($clientId){
$sql = "SELECT
client.id,
client.nom as client_nom,
client.prenom as client_prenom,
client.entreprise as client_entreprise
FROM ".$this->tableprefix."client as client
WHERE client.id = ?;";
$clientList = $this->execSQLNoJsonReturn(
$sql,
[$clientId]);
if(!empty($clientList)){
return $clientList[0];
}
return $clientList;
}
public function getClientsByClientsID(array $clientIds){
if(empty($clientIds)){
return [];
}
$sqlConditionsPlaceholder = implode(',', array_fill(0, count($clientIds), '?'));
$sql = "SELECT
client.id,
client.nom as client_nom,
client.prenom as client_prenom,
client.entreprise as client_entreprise
FROM ".$this->tableprefix."client as client
WHERE client.id IN ($sqlConditionsPlaceholder);";
$clientList = $this->execSQLNoJsonReturn(
$sql,
$clientIds);
return $clientList;
}
}

View File

@ -0,0 +1,113 @@
<?php
declare(strict_types=1);
/**
* Calendar App
*
* @copyright 2021 Anna Larch <anna.larch@gmx.net>
*
* @author Anna Larch <anna.larch@gmx.net>
* @author Richard Steinmetz <richard@steinmetz.cloud>
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU AFFERO GENERAL PUBLIC LICENSE
* License as published by the Free Software Foundation; either
* version 3 of the License, or any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU AFFERO GENERAL PUBLIC LICENSE for more details.
*
* You should have received a copy of the GNU Affero General Public
* License along with this library. If not, see <http://www.gnu.org/licenses/>.
*
*/
namespace OCA\Gestion\Service;
use OCA\Gestion\Db\Bdd;
use Psr\Log\LoggerInterface;
class ExportClientStatisticService {
/** @var Bdd */
private $gestionBdd;
/** @var LoggerInterface */
private $logger;
public function __construct(
Bdd $gestionBdd,
LoggerInterface $logger) {
$this->logger = $logger;
$this->gestionBdd = $gestionBdd;
}
public function getFileName(array $clientIds){
$filename = "";
$clients = $this->gestionBdd->getClientsByClientsID($clientIds);
foreach($clients as $client){
$filename .= $client['client_nom'] . '-' . $client['client_entreprise'] . '--';
}
$filename = rtrim($filename, '-');
return $filename;
}
public function getExportClientFileHeader(): string{
$fileHeader =
'Client'.';'.
'Mois'.';'.
'Année'.';'.
'Nb defunts'.';'.
'Nb articles'.';'.
'Total HT'.';'.
"\n";
return $fileHeader;
}
public function populateExportDataIntoFileContent(array $exportData,string $fileContent): string{
foreach($exportData as $clientId => $clientData){
$clientName = $clientData["client_name"];
$clientStatPerMonth = $clientData["client_data"];
$totalPrice = 0;
if(!empty($clientStatPerMonth)){
foreach($clientStatPerMonth as $month => $stat){
$stat["client_name"] = $clientName;
$totalPrice+=$stat["total_price"];
$fileContent = $this->populateClientStatDataIntoFileContent($fileContent,$month,$stat);
}
$fileContent = $this->populateTotalPriceIntoFileContent($fileContent,$totalPrice);
}
}
return $fileContent;
}
private function populateTotalPriceIntoFileContent(string $fileContent,$price){
$fileContent = $fileContent.
''.';'.
''.';'.
''.';'.
''.';'.
''.';'.
utf8_decode(html_entity_decode("$price"))."\n";
return $fileContent;
}
private function populateClientStatDataIntoFileContent(string $fileContent,$month,array $statPerMonth){
$yearValue = $statPerMonth["year"];
$defuntCount = $statPerMonth["defunt_count"];
$productCount = $statPerMonth["produit_count"];
$totalPrice = $statPerMonth["total_price"];
$fileContent = $fileContent.
utf8_decode(html_entity_decode($statPerMonth['client_name'])).';'.
utf8_decode(html_entity_decode("$month")).';'.
utf8_decode(html_entity_decode("$yearValue")).';'.
utf8_decode(html_entity_decode("$defuntCount")).';'.
utf8_decode(html_entity_decode("$productCount")).';'.
utf8_decode(html_entity_decode("$totalPrice")).';'."\n";
return $fileContent;
}
}

View File

@ -428,6 +428,7 @@ $('body').on('click', '#exportThanatoData', function () {
});
if(thanatoIdsToExport.length == 0){
showError(t('gestion', "Veuillez choisir au moins une ligne de client"));
return;
}
@ -443,9 +444,44 @@ $('body').on('click', '#exportThanatoData', function () {
}).done(function (response) {
let datatable = new DataTable('.tabledt');
Thanatopracteur.loadThanatoDT(datatable);
showSuccess(t('gestion', "Statistic exported : " + response));
showSuccess(t('gestion', "Sauvegardé dans : " + response));
}).fail(function (response, code) {
showError(t('gestion', "Please select thanato to export"));
showError(t('gestion', "Erreur dans l'export de statistique thanato"));
});
});
$('body').on('click', '#exportClientStat', function () {
var oTable = $('.tabledt').dataTable();
var rowcollection = oTable.$(".clientToExport:checked", {"page": "all"});
let clientIdsToExport = [];
rowcollection.each(function(index,elem){
var checkbox_value = $(elem).val();
clientIdsToExport.push(checkbox_value);
});
if(clientIdsToExport.length == 0){
showError(t('gestion', "Veuillez choisir au moins une ligne de client"));
return;
}
let exportClientPayload = {
clientIdsToExport: clientIdsToExport
}
$.ajax({
url: baseUrl + '/client/exportClientStatistic',
type: 'POST',
contentType: 'application/json',
data: JSON.stringify(exportClientPayload)
}).done(function (response) {
let datatable = new DataTable('.tabledt');
Client.loadClientDT(datatable);
showSuccess(t('gestion', "Sauvegardé dans : " + response));
}).fail(function (response, code) {
showError(t('gestion', "Erreur dans l'export de statistique client"));
});

View File

@ -23,6 +23,7 @@ export class Client {
*/
getDTRow() {
let myrow = [
'<input class="clientToExport" data-id= '+ this.id + ' type="checkbox" name="clientToExport" value="' + this.id + '"/>',
'<div>' + this.id + '</div>',
'<div class="editable" data-table="client" data-column="entreprise" data-id="' + this.id + '">' + this.entreprise + '</div>',
'<div class="editable" data-table="client" data-column="prenom" data-id="' + this.id + '">' + this.prenom + '</div>',

View File

@ -13,9 +13,13 @@
</button>
</div>
</div>
<div class="d-flex jsutify-content-end">
<button class="btn btn-secondary" id="exportClientStat">Export client stat</button>
</div>
<table id="client" class="display tabledt" style="font-size:11px;">
<thead>
<tr>
<th><?php p($l->t('To export'));?></th>
<th><?php p($l->t('ID'));?></th>
<th><?php p($l->t('Company'));?></th>
<th><?php p($l->t('First name'));?></th>

View File

@ -14,7 +14,7 @@
</div>
</div>
<div class="d-flex jsutify-content-end">
<button class="btn btn-secondary" id="exportThanatoData">Export thanato data</button>
<button class="btn btn-secondary" id="exportThanatoData">Export thanato stat</button>
</div>
<table id="client" class="display tabledt" style="font-size:11px;">
<thead>