瀏覽代碼

Refactoring services #885

refactoring
Guillaume 1 年之前
父節點
當前提交
eacb1fc180
共有 21 個文件被更改,包括 575 次插入465 次删除
  1. +16
    -15
      common/logic/Distribution/Distribution/DistributionBuilder.php
  2. +7
    -0
      common/logic/Distribution/Distribution/DistributionRepository.php
  3. +13
    -21
      common/logic/Distribution/PointSaleDistribution/PointSaleDistributionBuilder.php
  4. +7
    -0
      common/logic/Distribution/PointSaleDistribution/PointSaleDistributionRepository.php
  5. +51
    -83
      common/logic/Document/DeliveryNote/DeliveryNote.php
  6. +3
    -3
      common/logic/Document/DeliveryNote/DeliveryNoteContainer.php
  7. +44
    -42
      common/logic/Document/DeliveryNote/DeliveryNoteSearch.php
  8. +25
    -0
      common/logic/Document/DeliveryNote/DeliveryNoteSolver.php
  9. +8
    -133
      common/logic/Document/Document/Document.php
  10. +8
    -0
      common/logic/Document/Document/DocumentInterface.php
  11. +108
    -0
      common/logic/Document/Document/DocumentSolver.php
  12. +0
    -21
      common/logic/Order/Order/Order.php
  13. +16
    -0
      common/logic/Order/Order/OrderRepository.php
  14. +32
    -0
      common/logic/Order/ProductOrder/ProductOrderBuilder.php
  15. +13
    -1
      common/logic/PointSale/PointSale/PointSaleRepository.php
  16. +0
    -52
      common/logic/Product/Product/Product.php
  17. +49
    -1
      common/logic/Product/Product/ProductSolver.php
  18. +0
    -91
      common/logic/Product/ProductPrice/ProductPrice.php
  19. +113
    -0
      common/logic/Product/ProductPrice/ProductPriceSolver.php
  20. +2
    -1
      composer.json
  21. +60
    -1
      composer.lock

+ 16
- 15
common/logic/Distribution/Distribution/DistributionBuilder.php 查看文件

@@ -12,12 +12,14 @@ use common\logic\Distribution\ProductDistribution\ProductDistributionBuilder;
use common\logic\Distribution\ProductDistribution\ProductDistributionRepository;
use common\logic\Order\Order\Order;
use common\logic\Order\Order\OrderRepository;
use common\logic\Order\ProductOrder\ProductOrderBuilder;
use common\logic\PointSale\PointSale\PointSale;
use common\logic\Producer\Producer\Producer;
use common\logic\Product\Product\Product;
use common\logic\Product\Product\ProductRepository;
use common\logic\Subscription\Subscription\Subscription;
use common\logic\User\UserProducer\UserProducer;
use common\logic\User\UserProducer\UserProducerRepository;

class DistributionBuilder extends BaseService implements BuilderInterface
{
@@ -29,6 +31,8 @@ class DistributionBuilder extends BaseService implements BuilderInterface
protected ProductDistributionRepository $productDistributionRepository;
protected ProductDistributionBuilder $productDistributionBuilder;
protected OrderRepository $orderRepository;
protected UserProducerRepository $userProducerRepository;
protected ProductOrderBuilder $productOrderBuilder;

public function __construct()
{
@@ -39,6 +43,8 @@ class DistributionBuilder extends BaseService implements BuilderInterface
$this->productRepository = $this->loadService(ProductRepository::class);
$this->productDistributionRepository = $this->loadService(ProductDistributionRepository::class);
$this->orderRepository = $this->loadService(OrderRepository::class);
$this->userProducerRepository = $this->loadService(UserProducerRepository::class);
$this->productOrderBuilder = $this->loadService(ProductOrderBuilder::class);
}

public function instanciate(Producer $producer, string $date, bool $delivery = true): Distribution
@@ -157,26 +163,21 @@ class DistributionBuilder extends BaseService implements BuilderInterface
foreach ($ordersArray as $order) {
foreach ($order->productOrder as $productOrder) {
if ($productOrder->id_product == $product->id) {
$productOrder->price = $product->price;

$user = false;
$userProducer = false;
$user = null;
$userProducer = null;
if (isset($order->user) && $order->user) {
$user = $order->user;
$userProducer = UserProducer::searchOne([
'id_user' => $user->id,
'id_producer' => $order->distribution->id_producer
]);
$userProducer = $this->userProducerRepository->getOne($user, $distribution->producer);
}

$productOrder->price = $product->getPrice([
'user' => $user,
'user_producer' => $userProducer,
'point_sale' => $order->pointSale,
'quantity' => $productOrder->quantity
]);

$productOrder->save();
$this->productOrderBuilder->updatePrice(
$productOrder,
$user,
$userProducer,
$order->pointSale,
$productOrder->quantity
);
}
}
}

+ 7
- 0
common/logic/Distribution/Distribution/DistributionRepository.php 查看文件

@@ -19,6 +19,13 @@ class DistributionRepository extends BaseService implements RepositoryInterface
];
}

public function getOneById($id): ?Distribution
{
return Distribution::searchOne([
'id' => $id
]);
}

public function getOne(Producer $producer, string $date)
{
$paramsDistribution = [

+ 13
- 21
common/logic/Distribution/PointSaleDistribution/PointSaleDistributionBuilder.php 查看文件

@@ -6,15 +6,21 @@ use common\helpers\GlobalParam;
use common\logic\BaseService;
use common\logic\BuilderInterface;
use common\logic\Distribution\Distribution\Distribution;
use common\logic\Distribution\Distribution\DistributionRepository;
use common\logic\PointSale\PointSale\PointSale;
use common\logic\PointSale\PointSale\PointSaleRepository;

class PointSaleDistributionBuilder extends BaseService implements BuilderInterface
{
protected PointSaleDistributionRepository $pointSaleDistributionRepository;
protected PointSaleRepository $pointSaleRepository;
protected DistributionRepository $distributionRepository;

public function __construct()
{
$this->pointSaleDistributionRepository = $this->loadService(PointSaleDistributionRepository::class);
$this->pointSaleRepository = $this->loadService(PointSaleRepository::class);
$this->distributionRepository = $this->loadService(DistributionRepository::class);
}

/**
@@ -45,7 +51,7 @@ class PointSaleDistributionBuilder extends BaseService implements BuilderInterfa
{
$pointSaleDistribution = $this->pointSaleDistributionRepository->getOne($distribution, $pointSale);

if(!$pointSaleDistribution) {
if (!$pointSaleDistribution) {
$pointSaleDistribution = $this->create($distribution, $pointSale);
}

@@ -58,30 +64,16 @@ class PointSaleDistributionBuilder extends BaseService implements BuilderInterfa
// setAll
public function createAll(Distribution $distribution, bool $delivery): void
{
$arrPointsSale = PointSale::find()
->with(['pointSaleDistribution' => function($q) use ($distribution) {
$q->where(['id_distribution' => $distribution->id]);
}])
->where([
'id_producer' => GlobalParam::getCurrentProducerId(),
])
->all();

foreach ($arrPointsSale as $pointSale) {
if(!$pointSale->pointSaleDistribution) {
$pointSaleArray = $this->pointSaleRepository->getByDistribution($distribution);
foreach ($pointSaleArray as $pointSale) {
if (!$pointSale->pointSaleDistribution) {
$this->create($distribution, $pointSale);
}
}

$distribution = Distribution::findOne($distribution->id);
if ($distribution) {

$arrPointsSaleDistribution = PointSaleDistribution::searchAll([
'id_distribution' => $distribution->id
]) ;
foreach ($arrPointsSaleDistribution as $pointSaleDistribution) {
$this->initDelivery($pointSaleDistribution, $delivery);
}
$pointSaleDistributionArray = $this->pointSaleDistributionRepository->getByDistribution($distribution);
foreach ($pointSaleDistributionArray as $pointSaleDistribution) {
$this->initDelivery($pointSaleDistribution, $delivery);
}
}


+ 7
- 0
common/logic/Distribution/PointSaleDistribution/PointSaleDistributionRepository.php 查看文件

@@ -26,6 +26,13 @@ class PointSaleDistributionRepository extends BaseService implements RepositoryI
]);
}

public function getByDistribution(Distribution $distribution)
{
return PointSaleDistribution::searchAll([
'id_distribution' => $distribution->id
]) ;
}

public function countByDistribution(Distribution $distribution): int
{
return PointSaleDistribution::searchCount([

+ 51
- 83
common/logic/Document/DeliveryNote/DeliveryNote.php 查看文件

@@ -1,40 +1,40 @@
<?php

/**
Copyright distrib (2018)
contact@opendistrib.net
Ce logiciel est un programme informatique servant à aider les producteurs
à distribuer leur production en circuits courts.
Ce logiciel est régi par la licence CeCILL soumise au droit français et
respectant les principes de diffusion des logiciels libres. Vous pouvez
utiliser, modifier et/ou redistribuer ce programme sous les conditions
de la licence CeCILL telle que diffusée par le CEA, le CNRS et l'INRIA
sur le site "http://www.cecill.info".
En contrepartie de l'accessibilité au code source et des droits de copie,
de modification et de redistribution accordés par cette licence, il n'est
offert aux utilisateurs qu'une garantie limitée. Pour les mêmes raisons,
seule une responsabilité restreinte pèse sur l'auteur du programme, le
titulaire des droits patrimoniaux et les concédants successifs.
A cet égard l'attention de l'utilisateur est attirée sur les risques
associés au chargement, à l'utilisation, à la modification et/ou au
développement et à la reproduction du logiciel par l'utilisateur étant
donné sa spécificité de logiciel libre, qui peut le rendre complexe à
manipuler et qui le réserve donc à des développeurs et des professionnels
avertis possédant des connaissances informatiques approfondies. Les
utilisateurs sont donc invités à charger et tester l'adéquation du
logiciel à leurs besoins dans des conditions permettant d'assurer la
sécurité de leurs systèmes et ou de leurs données et, plus généralement,
à l'utiliser et l'exploiter dans les mêmes conditions de sécurité.
Le fait que vous puissiez accéder à cet en-tête signifie que vous avez
pris connaissance de la licence CeCILL, et que vous en avez accepté les
termes.
*/
/**
* Copyright distrib (2018)
*
* contact@opendistrib.net
*
* Ce logiciel est un programme informatique servant à aider les producteurs
* à distribuer leur production en circuits courts.
*
* Ce logiciel est régi par la licence CeCILL soumise au droit français et
* respectant les principes de diffusion des logiciels libres. Vous pouvez
* utiliser, modifier et/ou redistribuer ce programme sous les conditions
* de la licence CeCILL telle que diffusée par le CEA, le CNRS et l'INRIA
* sur le site "http://www.cecill.info".
*
* En contrepartie de l'accessibilité au code source et des droits de copie,
* de modification et de redistribution accordés par cette licence, il n'est
* offert aux utilisateurs qu'une garantie limitée. Pour les mêmes raisons,
* seule une responsabilité restreinte pèse sur l'auteur du programme, le
* titulaire des droits patrimoniaux et les concédants successifs.
*
* A cet égard l'attention de l'utilisateur est attirée sur les risques
* associés au chargement, à l'utilisation, à la modification et/ou au
* développement et à la reproduction du logiciel par l'utilisateur étant
* donné sa spécificité de logiciel libre, qui peut le rendre complexe à
* manipuler et qui le réserve donc à des développeurs et des professionnels
* avertis possédant des connaissances informatiques approfondies. Les
* utilisateurs sont donc invités à charger et tester l'adéquation du
* logiciel à leurs besoins dans des conditions permettant d'assurer la
* sécurité de leurs systèmes et ou de leurs données et, plus généralement,
* à l'utiliser et l'exploiter dans les mêmes conditions de sécurité.
*
* Le fait que vous puissiez accéder à cet en-tête signifie que vous avez
* pris connaissance de la licence CeCILL, et que vous en avez accepté les
* termes.
*/

namespace common\logic\Document\DeliveryNote;

@@ -42,52 +42,20 @@ use common\logic\Document\Document\Document;

class DeliveryNote extends Document
{
/**
* @inheritdoc
*/
public static function tableName()
{
return 'delivery_note';
}

/*
* Relations
*/

public function getOrders()
{
return $this->relationOrders('id_delivery_note') ;
}

public function getInvoiceId()
{
if($this->orders && count($this->orders) > 0) {
foreach($this->orders as $order) {
if($order->id_invoice) {
return $order->id_invoice;
}
}
}

return false;
}

public function isInvoiced()
{
return (bool) $this->getInvoiceId();
}

public function getInvoice()
{
$invoice = null;
$idInvoice = $this->getInvoiceId();

if($idInvoice) {
$invoice = Invoice::searchOne([
'id' => $idInvoice
]);
}

return $invoice;
}
/**
* @inheritdoc
*/
public static function tableName()
{
return 'delivery_note';
}

/*
* Relations
*/

public function getOrders()
{
return $this->relationOrders('id_delivery_note');
}
}

+ 3
- 3
common/logic/Document/DeliveryNote/DeliveryNoteContainer.php 查看文件

@@ -14,14 +14,14 @@ class DeliveryNoteContainer implements ContainerInterface
public function getServices(): array
{
return [
DeliveryNoteFactory::class,
DeliveryNoteBuilder::class,
DeliveryNoteSolver::class,
];
}

public function getFactory(): DeliveryNoteFactory
public function getFactory(): DeliveryNoteBuilder
{
return new DeliveryNoteFactory();
return new DeliveryNoteBuilder();
}

public function getSolver(): DeliveryNoteSolver

+ 44
- 42
common/logic/Document/DeliveryNote/DeliveryNoteSearch.php 查看文件

@@ -39,59 +39,61 @@
namespace common\logic\Document\DeliveryNote;

use common\helpers\GlobalParam;
use common\logic\PointSale\PointSale\DeliveryNoteRepository;
use yii\data\ActiveDataProvider;

class DeliveryNoteSearch extends DeliveryNote
{
public $id_point_sale ;
public $date_distribution ;
public $id_point_sale;
public $date_distribution;

public function rules()
{
return [
[[], 'safe'],
[['comment', 'address', 'status', 'date_distribution'], 'string'],
[['id_user', 'id_point_sale'], 'integer'],
[['name', 'reference'], 'string', 'max' => 255],
];
}

public function search($params)
{
$optionsSearch = self::defaultOptionsSearch();
public function rules()
{
return [
[[], 'safe'],
[['comment', 'address', 'status', 'date_distribution'], 'string'],
[['id_user', 'id_point_sale'], 'integer'],
[['name', 'reference'], 'string', 'max' => 255],
];
}

$query = DeliveryNote::find()
->with($optionsSearch['with'])
->joinWith($optionsSearch['join_with'])
->where(['delivery_note.id_producer' => GlobalParam::getCurrentProducerId()])
->orderBy('delivery_note.status ASC, delivery_note.reference DESC')
->groupBy('delivery_note.id');
public function search($params)
{
$deliveryNoteRepository = new DeliveryNoteRepository();
$optionsSearch = $deliveryNoteRepository->defaultOptionsSearch();

$dataProvider = new ActiveDataProvider([
'query' => $query,
'sort' => ['attributes' => ['name', 'reference', 'date']],
'pagination' => [
'pageSize' => 20,
],
]);
$query = DeliveryNote::find()
->with($optionsSearch['with'])
->joinWith($optionsSearch['join_with'])
->where(['delivery_note.id_producer' => GlobalParam::getCurrentProducerId()])
->orderBy('delivery_note.status ASC, delivery_note.reference DESC')
->groupBy('delivery_note.id');

$this->load($params);
if (!$this->validate()) {
return $dataProvider;
}
$dataProvider = new ActiveDataProvider([
'query' => $query,
'sort' => ['attributes' => ['name', 'reference', 'date']],
'pagination' => [
'pageSize' => 20,
],
]);

$query->andFilterWhere(['like', 'delivery_note.name', $this->name]);
$query->andFilterWhere(['like', 'delivery_note.reference', $this->reference]);
$query->andFilterWhere(['like', 'delivery_note.status', $this->status]);
$this->load($params);
if (!$this->validate()) {
return $dataProvider;
}

if($this->id_point_sale) {
$query->andWhere(['order.id_point_sale' => $this->id_point_sale]);
}
$query->andFilterWhere(['like', 'delivery_note.name', $this->name]);
$query->andFilterWhere(['like', 'delivery_note.reference', $this->reference]);
$query->andFilterWhere(['like', 'delivery_note.status', $this->status]);

if($this->date_distribution && strlen($this->date_distribution)) {
$query->andFilterWhere(['like', 'distribution.date', date('Y-m-d',strtotime(str_replace('/','-',$this->date_distribution)))]);
}
if ($this->id_point_sale) {
$query->andWhere(['order.id_point_sale' => $this->id_point_sale]);
}

return $dataProvider;
if ($this->date_distribution && strlen($this->date_distribution)) {
$query->andFilterWhere(['like', 'distribution.date', date('Y-m-d', strtotime(str_replace('/', '-', $this->date_distribution)))]);
}

return $dataProvider;
}
}

+ 25
- 0
common/logic/Document/DeliveryNote/DeliveryNoteSolver.php 查看文件

@@ -3,9 +3,34 @@
namespace common\logic\Document\DeliveryNote;

use common\logic\BaseService;
use common\logic\Document\Invoice\Invoice;
use common\logic\SolverInterface;

class DeliveryNoteSolver extends BaseService implements SolverInterface
{
public function getInvoiceId(DeliveryNote $deliveryNote): ?int
{
if($deliveryNote->orders && count($deliveryNote->orders) > 0) {
foreach($deliveryNote->orders as $order) {
if($order->id_invoice) {
return $order->id_invoice;
}
}
}

return null;
}

public function isInvoiced(DeliveryNote $deliveryNote): bool
{
return (bool) $this->getInvoiceId($deliveryNote);
}

public function getInvoice(DeliveryNote $deliveryNote): ?Invoice
{
$idInvoice = (int) $this->getInvoiceId($deliveryNote);
return Invoice::searchOne([
'id' => $idInvoice
]);
}
}

+ 8
- 133
common/logic/Document/Document/Document.php 查看文件

@@ -40,11 +40,14 @@ namespace common\logic\Document\Document;

use common\components\ActiveRecordCommon;
use common\helpers\GlobalParam;
use common\logic\Order\Order\Order;
use common\logic\Order\Order\OrderRepository;
use common\logic\Producer\Producer\Producer;
use common\logic\User\User\User;
use kartik\mpdf\Pdf;
use yii\base\ErrorException;

class Document extends ActiveRecordCommon
class Document extends ActiveRecordCommon implements DocumentInterface
{
const STATUS_DRAFT = 'draft';
const STATUS_VALID = 'valid';
@@ -100,7 +103,7 @@ class Document extends ActiveRecordCommon

public function getUser()
{
return $this->hasOne( User::className(), ['id' => 'id_user']);
return $this->hasOne(User::class, ['id' => 'id_user']);
}

public function getProducer()
@@ -110,9 +113,10 @@ class Document extends ActiveRecordCommon

public function relationOrders($fieldIdDocument)
{
$defaultOptionsSearch = Order::defaultOptionsSearch();
$orderRepository = new OrderRepository();
$defaultOptionsSearch = $orderRepository->defaultOptionsSearch();

return $this->hasMany(Order::className(), [$fieldIdDocument => 'id'])
return $this->hasMany(Order::class, [$fieldIdDocument => 'id'])
->with($defaultOptionsSearch['with'])
->joinWith($defaultOptionsSearch['join_with'])
->orderBy('distribution.date ASC');
@@ -122,136 +126,7 @@ class Document extends ActiveRecordCommon
* Méthodes
*/

public function getAmount($type = Order::AMOUNT_TOTAL, $format = false)
{
return $this->_getAmountGeneric($type, false, $format);
}

public function getAmountWithTax($type = Order::AMOUNT_TOTAL, $format = false)
{
return $this->_getAmountGeneric($type, true, $format);
}

protected function _getAmountGeneric($type = Order::AMOUNT_TOTAL, $withTax = true, $format = false)
{
$amount = 0;
$totalVat = 0;
$ordersArray = $this->orders;

// Méthode de calcul via les commandes liées
/*foreach ($ordersArray as $order) {
$order->init($this->tax_calculation_method);
$amount += $order->getAmount($type);
$totalVat += $order->getTotalVat($type);
}*/

// Méthode de calcul via getProductOrders()
foreach($this->getProductsOrders() as $productOrderArray) {
foreach($productOrderArray as $productOrder) {
$priceLine = $productOrder->getPriceByTypeTotal($type) * $productOrder->quantity;
$amount += $priceLine;
$totalVat += Price::getVat($priceLine, $productOrder->taxRate->value, $this->tax_calculation_method);
}
}

if ($this->isTaxCalculationMethodRoundingOfTheSum()) {
$totalVat = Price::round($totalVat);
}

if ($withTax) {
$amount += $totalVat;
}

if ($format) {
return Price::format($amount);
} else {
return $amount;
}
}

public function getTotalVatArray($typeTotal)
{
$totalVatArray = [];

// Méthode de calcul via les commandes liées
/*$ordersArray = $this->orders;
foreach ($ordersArray as $order) {
$order->init($this->tax_calculation_method);
$fieldNameVat = $order->getFieldNameAmount($typeTotal, 'vat');
foreach ($order->$fieldNameVat as $idTaxRate => $vat) {
if (!isset($totalVatArray[$idTaxRate])) {
$totalVatArray[$idTaxRate] = 0;
}
$totalVatArray[$idTaxRate] += $vat;
}
}*/

// Méthode de calcul via getProductOrders()
foreach($this->getProductsOrders() as $productOrderArray) {
foreach ($productOrderArray as $productOrder) {

$idTaxRate = $productOrder->taxRate->id;
if (!isset($totalVatArray[$idTaxRate])) {
$totalVatArray[$idTaxRate] = 0;
}

$totalVatArray[$idTaxRate] += Price::getVat(
$productOrder->getPriceByTypeTotal($typeTotal) * $productOrder->quantity,
$productOrder->taxRate->value,
$this->tax_calculation_method
);
}
}

return $totalVatArray;
}

public function getPointSale()
{
if (isset($this->orders) && isset($this->orders[0])) {
return $this->orders[0]->pointSale;
} else {
return '';
}
}

public function getDistribution()
{
if (isset($this->orders) && isset($this->orders[0])) {
return $this->orders[0]->distribution;
} else {
return '';
}
}

public function getClass()
{
return str_replace('common\models\\', '', get_class($this));
}

public function getType()
{
$class = $this->getClass();

if ($class == 'Invoice') {
$documentType = 'Facture';
} elseif ($class == 'DeliveryNote') {
$documentType = 'Bon de livraison';
} elseif ($class == 'Quotation') {
$documentType = 'Devis';
}

if (isset($documentType)) {
return $documentType;
}

return '';
}

public function isValidClass($typeDocument)
{
return in_array($typeDocument, ['Invoice', 'DeliveryNote', 'Quotation']);
}

public function generateReference()
{

+ 8
- 0
common/logic/Document/Document/DocumentInterface.php 查看文件

@@ -0,0 +1,8 @@
<?php

namespace common\logic\Document\Document;

interface DocumentInterface
{

}

+ 108
- 0
common/logic/Document/Document/DocumentSolver.php 查看文件

@@ -3,9 +3,117 @@
namespace common\logic\Document\Document;

use common\logic\BaseService;
use common\logic\Order\Order\Order;
use common\logic\SolverInterface;

class DocumentSolver extends BaseService implements SolverInterface
{
public function getAmount(DocumentInterface $document, $type = Order::AMOUNT_TOTAL, $format = false)
{
return $this->_getAmountGeneric($document, $type, false, $format);
}

public function getAmountWithTax(DocumentInterface $document, $type = Order::AMOUNT_TOTAL, $format = false)
{
return $this->_getAmountGeneric($document, $type, true, $format);
}

protected function _getAmountGeneric(DocumentInterface $document, $type = Order::AMOUNT_TOTAL, $withTax = true, $format = false)
{
$amount = 0;
$totalVat = 0;

foreach($document->getProductsOrders() as $productOrderArray) {
foreach($productOrderArray as $productOrder) {
$priceLine = $productOrder->getPriceByTypeTotal($type) * $productOrder->quantity;
$amount += $priceLine;
$totalVat += Price::getVat($priceLine, $productOrder->taxRate->value, $document->tax_calculation_method);
}
}

if ($this->isTaxCalculationMethodRoundingOfTheSum()) {
$totalVat = Price::round($totalVat);
}

if ($withTax) {
$amount += $totalVat;
}

if ($format) {
return Price::format($amount);
} else {
return $amount;
}
}

public function getTotalVatArray($typeTotal)
{
$totalVatArray = [];

// Méthode de calcul via getProductOrders()
foreach($this->getProductsOrders() as $productOrderArray) {
foreach ($productOrderArray as $productOrder) {

$idTaxRate = $productOrder->taxRate->id;
if (!isset($totalVatArray[$idTaxRate])) {
$totalVatArray[$idTaxRate] = 0;
}

$totalVatArray[$idTaxRate] += Price::getVat(
$productOrder->getPriceByTypeTotal($typeTotal) * $productOrder->quantity,
$productOrder->taxRate->value,
$this->tax_calculation_method
);
}
}

return $totalVatArray;
}

public function getPointSale()
{
if (isset($this->orders) && isset($this->orders[0])) {
return $this->orders[0]->pointSale;
} else {
return '';
}
}

public function getDistribution()
{
if (isset($this->orders) && isset($this->orders[0])) {
return $this->orders[0]->distribution;
} else {
return '';
}
}

public function getClass()
{
return str_replace('common\models\\', '', get_class($this));
}

public function getType()
{
$class = $this->getClass();

if ($class == 'Invoice') {
$documentType = 'Facture';
} elseif ($class == 'DeliveryNote') {
$documentType = 'Bon de livraison';
} elseif ($class == 'Quotation') {
$documentType = 'Devis';
}

if (isset($documentType)) {
return $documentType;
}

return '';
}

public function isValidClass($typeDocument)
{
return in_array($typeDocument, ['Invoice', 'DeliveryNote', 'Quotation']);
}
}

+ 0
- 21
common/logic/Order/Order/Order.php 查看文件

@@ -198,27 +198,6 @@ class Order extends ActiveRecordCommon
return $this->hasOne(DeliveryNote::className(), ['id' => 'id_delivery_note']);
}

/**
* Retourne les options de base nécessaires à la fonction de recherche.
*
* @return array
*/
public static function defaultOptionsSearch()
{
return [
'with' => [
'productOrder',
'productOrder.product',
'creditHistory',
'creditHistory.userAction',
'pointSale'
],
'join_with' => ['distribution', 'user', 'user.userProducer'],
'orderby' => 'order.date ASC',
'attribute_id_producer' => 'distribution.id_producer'
];
}

/**
* Initialise le montant total, le montant déjà payé et le poids de la
* commande.

+ 16
- 0
common/logic/Order/Order/OrderRepository.php 查看文件

@@ -8,6 +8,22 @@ use common\logic\RepositoryInterface;

class OrderRepository extends BaseService implements RepositoryInterface
{
public function defaultOptionsSearch(): array
{
return [
'with' => [
'productOrder',
'productOrder.product',
'creditHistory',
'creditHistory.userAction',
'pointSale'
],
'join_with' => ['distribution', 'user', 'user.userProducer'],
'orderby' => 'order.date ASC',
'attribute_id_producer' => 'distribution.id_producer'
];
}

public function getByDistribution(Distribution $distribution, string $conditionAppend = '')
{
return Order::searchAll([

+ 32
- 0
common/logic/Order/ProductOrder/ProductOrderBuilder.php 查看文件

@@ -4,13 +4,45 @@ namespace common\logic\Order\ProductOrder;

use common\logic\BaseService;
use common\logic\BuilderInterface;
use common\logic\PointSale\PointSale\PointSale;
use common\logic\Product\Product\ProductSolver;
use common\logic\User\User\User;
use common\logic\User\UserProducer\UserProducer;

class ProductOrderBuilder extends BaseService implements BuilderInterface
{
protected ProductSolver $productSolver;

public function __construct()
{
$this->productSolver = $this->loadService(ProductSolver::class);
}

public function instanciate(): ProductOrder
{
$productOrder = new ProductOrder();

return $productOrder;
}

public function updatePrice(
ProductOrder $productOrder,
User $user = null,
UserProducer $userProducer = null,
PointSale $pointSale = null,
int $quantity = 1)
{
$productOrder->price = $this->productSolver->getPrice(
$productOrder->product,
[
'user' => $user,
'user_producer' => $userProducer,
'point_sale' => $pointSale,
'quantity' => $quantity
]);

$productOrder->save();

return $productOrder;
}
}

+ 13
- 1
common/logic/PointSale/PointSale/PointSaleRepository.php 查看文件

@@ -2,11 +2,23 @@

namespace common\logic\PointSale\PointSale;

use common\helpers\GlobalParam;
use common\logic\BaseService;
use common\logic\BuilderInterface;
use common\logic\Distribution\Distribution\Distribution;
use common\logic\RepositoryInterface;

class PointSaleRepository extends BaseService implements RepositoryInterface
{

public function getByDistribution(Distribution $distribution)
{
return PointSale::find()
->with(['pointSaleDistribution' => function($q) use ($distribution) {
$q->where(['id_distribution' => $distribution->id]);
}])
->where([
'id_producer' => $distribution->producer->id,
])
->all();
}
}

+ 0
- 52
common/logic/Product/Product/Product.php 查看文件

@@ -448,58 +448,6 @@ class Product extends ActiveRecordCommon
return false;
}

public function getSpecificPricesFilterByPriorityMatch($specificPrices, $user, $pointSale)
{
$priorityMatchSpecificPrice = ProductPrice::getPriorityMatchOfSpecificPriceArray($specificPrices, $user, $pointSale);
$specificPricesFilter = [];

foreach ($specificPrices as $keySpecificPrice => $specificPrice) {
if (($priorityMatchSpecificPrice && $specificPrice->$priorityMatchSpecificPrice($user, $pointSale))
|| $specificPrice->matchFromQuantityOnly()) {

$specificPricesFilter[] = $specificPrice;
}
}

return $specificPricesFilter;
}

public function getPrice($params = [])
{
$specificPrices = $this->productPrice;

$user = isset($params['user']) ? $params['user'] : false;
$userProducer = isset($params['user_producer']) ? $params['user_producer'] : false;
$pointSale = isset($params['point_sale']) ? $params['point_sale'] : false;
$quantity = (isset($params['quantity']) && $params['quantity']) ? $params['quantity'] : 1;

if ($specificPrices && ($user || $pointSale)) {
$specificPrices = $this->getSpecificPricesFilterByPriorityMatch($specificPrices, $user, $pointSale);
$bestPrice = 9999;
foreach ($specificPrices as $specificPrice) {
$fromQuantity = $specificPrice->from_quantity;
if ((($fromQuantity && $fromQuantity <= $quantity) || !$fromQuantity)
&& $specificPrice->price < $bestPrice) {
$bestPrice = $specificPrice->price;
}
}

if ($bestPrice != 9999) {
return $bestPrice;
}
}

if ($userProducer && $userProducer->product_price_percent) {
return $this->price * (1 + $userProducer->product_price_percent / 100);
}

if ($pointSale && $pointSale->product_price_percent) {
return $this->price * (1 + $pointSale->product_price_percent / 100);
}

return $this->price;
}

/**
* Retourne le prix du produit avec taxe
*/

+ 49
- 1
common/logic/Product/Product/ProductSolver.php 查看文件

@@ -3,9 +3,57 @@
namespace common\logic\Product\Product;

use common\logic\BaseService;
use common\logic\PointSale\PointSale\PointSale;
use common\logic\Product\ProductPrice\ProductPriceSolver;
use common\logic\SolverInterface;
use common\logic\User\User\User;

class ProductSolver extends BaseService implements SolverInterface
{
protected ProductPriceSolver $productPriceSolver;

public function __construct()
{
$this->productPriceSolver = $this->loadService(ProductPriceSolver::class);
}

public function getPrice(Product $product, array $params = []): float
{
$specificPriceArray = $product->productPrice;

$user = isset($params['user']) ? $params['user'] : false;
$userProducer = isset($params['user_producer']) ? $params['user_producer'] : false;
$pointSale = isset($params['point_sale']) ? $params['point_sale'] : false;
$quantity = (isset($params['quantity']) && $params['quantity']) ? $params['quantity'] : 1;

if ($specificPriceArray && ($user || $pointSale)) {
$specificPriceArray = $this->productPriceSolver->filterByPriorityMatch(
$specificPriceArray,
$user,
$pointSale
);
$bestPrice = 9999;
foreach ($specificPriceArray as $specificPrice) {
$fromQuantity = $specificPrice->from_quantity;
if ((($fromQuantity && $fromQuantity <= $quantity) || !$fromQuantity)
&& $specificPrice->price < $bestPrice) {
$bestPrice = $specificPrice->price;
}
}

if ($bestPrice != 9999) {
return $bestPrice;
}
}

if ($userProducer && $userProducer->product_price_percent) {
return $product->price * (1 + $userProducer->product_price_percent / 100);
}

if ($pointSale && $pointSale->product_price_percent) {
return $product->price * (1 + $pointSale->product_price_percent / 100);
}

return $product->price;
}
}

+ 0
- 91
common/logic/Product/ProductPrice/ProductPrice.php 查看文件

@@ -180,95 +180,4 @@ class ProductPrice extends ActiveRecordCommon

return $percentValues;
}

public static function hasMatchOfType($specificPriceArray, $typeMatch, $user, $pointSale)
{
foreach($specificPriceArray as $specificPrice) {
if($specificPrice->$typeMatch($user, $pointSale)) {
return true;
}
}

return false;
}

public static function getPriorityMatchOfSpecificPriceArray($specificPriceArray, $user, $pointSale)
{
if(self::hasMatchOfType($specificPriceArray, 'matchUser', $user, $pointSale)) {
return 'matchUser';
}

if(self::hasMatchOfType($specificPriceArray, 'matchUserGroup', $user, $pointSale)) {
return 'matchUserGroup';
}

if(self::hasMatchOfType($specificPriceArray, 'matchPointSale', $user, $pointSale)) {
return 'matchPointSale';
}

if(self::hasMatchOfType($specificPriceArray, 'matchUserPointSale', $user, $pointSale)) {
return 'matchUserPointSale';
}

if(self::hasMatchOfType($specificPriceArray, 'matchUserGroupPointSale', $user, $pointSale)) {
return 'matchUserGroupPointSale';
}

return null;
}

public function matchUser($user, $pointSale)
{
return $user
&& $this->id_user
&& !$this->id_point_sale
&& !$this->id_user_group
&& $this->id_user == $user->id;
}

public function matchUserGroup($user, $pointSale)
{
return $user
&& $this->id_user_group
&& !$this->id_point_sale
&& !$this->id_user
&& $user->belongsToUserGroup($this->id_user_group);
}

public function matchPointSale($user, $pointSale)
{
return $pointSale
&& $this->id_point_sale
&& !$this->id_user
&& !$this->id_user_group
&& $this->id_point_sale == $pointSale->id;
}

public function matchUserPointSale($user, $pointSale)
{
return $pointSale && $user
&& $this->id_point_sale
&& $this->id_user
&& $this->id_point_sale == $pointSale->id
&& $this->id_user == $user->id;
}

public function matchUserGroupPointSale($user, $pointSale)
{
return $user
&& $pointSale
&& $this->id_user_group
&& $this->id_point_sale
&& !$this->id_user
&& $user->belongsToUserGroup($this->id_user_group)
&& $this->id_point_sale == $pointSale->id;
}

public function matchFromQuantityOnly()
{
return !$this->id_user
&& !$this->id_point_sale
&& !$this->id_user_group
&& $this->from_quantity;
}
}

+ 113
- 0
common/logic/Product/ProductPrice/ProductPriceSolver.php 查看文件

@@ -3,9 +3,122 @@
namespace common\logic\Product\ProductPrice;

use common\logic\BaseService;
use common\logic\PointSale\PointSale\PointSale;
use common\logic\SolverInterface;
use common\logic\User\User\User;

class ProductPriceSolver extends BaseService implements SolverInterface
{
// getSpecificPricesFilterByPriorityMatch
public function filterByPriorityMatch(
array $specificPrices,
User $user,
PointSale $pointSale): array
{
$priorityMatchSpecificPrice = $this->getPriorityMatch($specificPrices, $user, $pointSale);
$specificPricesFilter = [];

foreach ($specificPrices as $keySpecificPrice => $specificPrice) {
if (($priorityMatchSpecificPrice && $specificPrice->$priorityMatchSpecificPrice($user, $pointSale))
|| $specificPrice->matchFromQuantityOnly()) {

$specificPricesFilter[] = $specificPrice;
}
}

return $specificPricesFilter;
}

// getPriorityMatchOfSpecificPriceArray
public function getPriorityMatch(
array $specificPriceArray,
User $user = null,
PointSale $pointSale = null): ?string
{
$typeMatchArray = [
'matchUser',
'matchUserGroup',
'matchPointSale',
'matchUserPointSale',
'matchUserGroupPointSale'
];

foreach($typeMatchArray as $typeMatch) {
if($this->hasMatchOfType($specificPriceArray, $typeMatch, $user, $pointSale)) {
return $typeMatch;
}
}

return null;
}

public function hasMatchOfType(
array $specificPriceArray,
string $typeMatch,
User $user = null,
PointSale $pointSale = null): bool
{
foreach($specificPriceArray as $specificPrice) {
if($specificPrice->$typeMatch($user, $pointSale)) {
return true;
}
}

return false;
}

public function matchUser(ProductPrice $productPrice, User $user = null, PointSale $pointSale = null): bool
{
return $user
&& $productPrice->id_user
&& !$productPrice->id_point_sale
&& !$productPrice->id_user_group
&& $productPrice->id_user == $user->id;
}

public function matchUserGroup(ProductPrice $productPrice, User $user = null, PointSale $pointSale = null): bool
{
return $user
&& $productPrice->id_user_group
&& !$productPrice->id_point_sale
&& !$productPrice->id_user
&& $user->belongsToUserGroup($productPrice->id_user_group);
}

public function matchPointSale(ProductPrice $productPrice, User $user = null, PointSale $pointSale = null): bool
{
return $pointSale
&& $productPrice->id_point_sale
&& !$productPrice->id_user
&& !$productPrice->id_user_group
&& $productPrice->id_point_sale == $pointSale->id;
}

public function matchUserPointSale(ProductPrice $productPrice, User $user = null, PointSale $pointSale = null): bool
{
return $pointSale && $user
&& $productPrice->id_point_sale
&& $productPrice->id_user
&& $productPrice->id_point_sale == $pointSale->id
&& $productPrice->id_user == $user->id;
}

public function matchUserGroupPointSale(ProductPrice $productPrice, User $user = null, PointSale $pointSale = null): bool
{
return $user
&& $pointSale
&& $productPrice->id_user_group
&& $productPrice->id_point_sale
&& !$productPrice->id_user
&& $user->belongsToUserGroup($productPrice->id_user_group)
&& $productPrice->id_point_sale == $pointSale->id;
}

public function matchFromQuantityOnly(ProductPrice $productPrice): bool
{
return !$productPrice->id_user
&& !$productPrice->id_point_sale
&& !$productPrice->id_user_group
&& $productPrice->from_quantity;
}
}

+ 2
- 1
composer.json 查看文件

@@ -38,7 +38,8 @@
"yiisoft/yii2-debug": "*",
"yiisoft/yii2-gii": "*",
"yiisoft/yii2-faker": "*",
"codeception/codeception": "^2.3"
"codeception/codeception": "^2.3",
"phpstan/phpstan": "^1.9"
},
"config": {
"process-timeout": 1800,

+ 60
- 1
composer.lock 查看文件

@@ -4,7 +4,7 @@
"Read more about it at https://getcomposer.org/doc/01-basic-usage.md#installing-dependencies",
"This file is @generated automatically"
],
"content-hash": "78a16f604e3b8e2cb623f7204619682f",
"content-hash": "85c783330a1d88a3ed3c4674e84d10ba",
"packages": [
{
"name": "2amigos/yii2-chartjs-widget",
@@ -3554,6 +3554,65 @@
},
"time": "2020-03-05T15:02:03+00:00"
},
{
"name": "phpstan/phpstan",
"version": "1.9.17",
"source": {
"type": "git",
"url": "https://github.com/phpstan/phpstan.git",
"reference": "204e459e7822f2c586463029f5ecec31bb45a1f2"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/phpstan/phpstan/zipball/204e459e7822f2c586463029f5ecec31bb45a1f2",
"reference": "204e459e7822f2c586463029f5ecec31bb45a1f2",
"shasum": ""
},
"require": {
"php": "^7.2|^8.0"
},
"conflict": {
"phpstan/phpstan-shim": "*"
},
"bin": [
"phpstan",
"phpstan.phar"
],
"type": "library",
"autoload": {
"files": [
"bootstrap.php"
]
},
"notification-url": "https://packagist.org/downloads/",
"license": [
"MIT"
],
"description": "PHPStan - PHP Static Analysis Tool",
"keywords": [
"dev",
"static analysis"
],
"support": {
"issues": "https://github.com/phpstan/phpstan/issues",
"source": "https://github.com/phpstan/phpstan/tree/1.9.17"
},
"funding": [
{
"url": "https://github.com/ondrejmirtes",
"type": "github"
},
{
"url": "https://github.com/phpstan",
"type": "github"
},
{
"url": "https://tidelift.com/funding/github/packagist/phpstan/phpstan",
"type": "tidelift"
}
],
"time": "2023-02-08T12:25:00+00:00"
},
{
"name": "phpunit/php-code-coverage",
"version": "6.1.4",

Loading…
取消
儲存