Skip to content

Commit

Permalink
MOL-75: Refactoring of line item rounding
Browse files Browse the repository at this point in the history
  • Loading branch information
boxblinkracer committed Nov 18, 2020
1 parent 834a053 commit bb7d8af
Show file tree
Hide file tree
Showing 25 changed files with 1,409 additions and 297 deletions.
5 changes: 4 additions & 1 deletion .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -3,4 +3,7 @@ logs
releases
/*.sh
/scoper.inc.php
/UpdateVersionNumber.php
/UpdateVersionNumber.php


.reports
4 changes: 2 additions & 2 deletions .travis.yml
Original file line number Diff line number Diff line change
Expand Up @@ -14,12 +14,12 @@ before_install:

_jobs_no_tests: &jobs_no_tests
script:
- find . -path ./vendor -prune -false -o -name '*.php' | xargs -n 1 -P4 php -l
- find . -name '*.php' -not -path "./vendor/*" -not -path "./Tests/*" | xargs -n 1 -P4 php -l

_jobs_full: &jobs_full
script:
- make dev -B
- find . -path ./vendor -prune -false -o -name '*.php' | xargs -n 1 -P4 php -l
- find . -name '*.php' -not -path "./vendor/*" -not -path "./Tests/*" | xargs -n 1 -P4 php -l
- make test -B

# ---------------------------------------------------------------------------------------
Expand Down
97 changes: 97 additions & 0 deletions Components/Basket/Basket.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,97 @@
<?php

namespace MollieShopware\Components\Basket;

use MollieShopware\Components\TransactionBuilder\Models\BasketItem;
use Psr\Log\LoggerInterface;
use Shopware\Components\Model\ModelManager;
use Shopware\Models\Order\Repository;

class Basket
{

/**
* @var ModelManager $modelManager
*/
private $modelManager;

/**
* @var LoggerInterface
*/
private $logger;


/**
* Basket constructor.
* @param ModelManager $modelManager
* @param LoggerInterface $logger
*/
public function __construct(ModelManager $modelManager, LoggerInterface $logger)
{
$this->modelManager = $modelManager;
$this->logger = $logger;
}


/**
* Get positions from basket
*
* @param array $userData
* @return BasketItem[]
* @throws \Exception
*/
public function getBasketLines($userData = array())
{
$items = [];

try {

/** @var Repository $basketRepo */
$basketRepo = $this->modelManager->getRepository(\Shopware\Models\Order\Basket::class);

/** @var Basket[] $basketItems */
$basketItems = $basketRepo->findBy(['sessionId' => Shopware()->Session()->offsetGet('sessionId')]);

/** @var \Shopware\Models\Order\Basket $basketItem */
foreach ($basketItems as $basketItem) {

$item = new BasketItem(
$basketItem->getId(),
$basketItem->getArticleId(),
$basketItem->getOrderNumber(),
$basketItem->getEsdArticle(),
$basketItem->getMode(),
$basketItem->getArticleName(),
$basketItem->getPrice(),
$basketItem->getNetPrice(),
$basketItem->getQuantity(),
$basketItem->getTaxRate()
);

# update our basket item ID if we have that attribute
# i dont know why - isn't it in the ID already?, but let's keep with it for now
if ($basketItem !== null && $basketItem->getAttribute() !== null && method_exists($basketItem->getAttribute(), 'setBasketItemId')) {

$basketItem->getAttribute()->setBasketItemId($basketItem->getId());

$this->modelManager->persist($basketItem);
$this->modelManager->flush($basketItem);
}

$items[] = $item;
}

} catch (\Exception $ex) {

$this->logger->error(
'Error when loading basket lines',
array(
'error' => $ex->getMessage(),
)
);
}

return $items;
}

}
72 changes: 72 additions & 0 deletions Components/MollieApi/LineItemsBuilder.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,72 @@
<?php

namespace MollieShopware\Components\MollieApi;

use MollieShopware\Components\Helpers\MollieLineItemCleaner;
use MollieShopware\Models\Transaction;
use MollieShopware\Models\TransactionItem;

class LineItemsBuilder
{

/**
* @param Transaction $transaction
* @return array
*/
public function buildLineItems(Transaction $transaction)
{
$orderlines = [];

/** @var TransactionItem $item */
foreach ($transaction->getItems() as $item) {

$orderlines[] = [
'type' => $item->getType(),
'name' => $item->getName(),
'quantity' => (int)$item->getQuantity(),
'unitPrice' => $this->formatNumberWithCurrency($transaction->getCurrency(), $item->getUnitPrice()),
'totalAmount' => $this->formatNumberWithCurrency($transaction->getCurrency(), $item->getTotalAmount()),
'vatRate' => $this->formatNumber($item->getVatRate()),
'vatAmount' => $this->formatNumberWithCurrency($transaction->getCurrency(), $item->getVatAmount()),
'sku' => null,
'imageUrl' => null,
'productUrl' => null,
'metadata' => json_encode(['transaction_item_id' => $item->getId()]),
];
}


$cleaner = new MollieLineItemCleaner();

# sometimes the advanced promotion suite has duplicate discounts in there.
# so we just remove these, otherwise we would get the error
# "amount of line items does not match provided total sum" of mollie
$orderlines = $cleaner->removeDuplicateDiscounts($orderlines);

return $orderlines;
}


/**
* @param $value
* @return string
*/
private function formatNumber($value)
{
return number_format($value, 2, '.', '');
}

/**
* @param $currency
* @param $amount
* @return array
*/
private function formatNumberWithCurrency($currency, $amount)
{
return [
'currency' => $currency,
'value' => $this->formatNumber($amount)
];
}

}
119 changes: 1 addition & 118 deletions Components/Services/BasketService.php
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@
use Exception;
use MollieShopware\Components\Config;
use MollieShopware\Components\Logger;
use MollieShopware\Components\TransactionBuilder\Models\BasketItem;
use Psr\Log\LoggerInterface;
use Shopware\Components\Model\ModelManager;
use Shopware\Models\Order\Basket;
Expand Down Expand Up @@ -243,124 +244,6 @@ private function getOrderDetailsAttributes($id)
return $orderDetailAttributesResult[0];
}

/**
* Get positions from basket
*
* @param array $userData
* @return array
* @throws Exception
*/
function getBasketLines($userData = array())
{
$items = [];

try {
/** @var Repository $basketRepo */
$basketRepo = Shopware()->Container()->get('models')->getRepository(
Basket::class
);

/** @var Basket[] $basketItems */
$basketItems = $basketRepo->findBy([
'sessionId' => Shopware()->Session()->offsetGet('sessionId')
]);

foreach ($basketItems as $basketItem) {
$unitPrice = round($basketItem->getPrice(), 2);
$netPrice = round($basketItem->getNetPrice(), 2);
$totalAmount = $unitPrice * $basketItem->getQuantity();
$vatAmount = 0;

if (
isset($userData['additional']['charge_vat'], $userData['additional']['show_net'])
&& $userData['additional']['charge_vat'] === true
&& $userData['additional']['show_net'] === false
) {
$unitPrice = $unitPrice * ($basketItem->getTaxRate() + 100) / 100;
$unitPrice = round($unitPrice, 2);
$totalAmount = $unitPrice * $basketItem->getQuantity();
}

if (
isset($userData['additional']['charge_vat'])
&& $userData['additional']['charge_vat'] === true
) {
$vatAmount = $totalAmount * ($basketItem->getTaxRate() / ($basketItem->getTaxRate() + 100));
$vatAmount = round($vatAmount, 2);
}

// build the order line array
$orderLine = [
'basket_item_id' => $basketItem->getId(),
'article_id' => $basketItem->getArticleId(),
'name' => $basketItem->getArticleName(),
'type' => $this->getOrderType($basketItem, $unitPrice),
'quantity' => $basketItem->getQuantity(),
'unit_price' => $unitPrice,
'net_price' => $netPrice,
'total_amount' => $totalAmount,
'vat_rate' => $vatAmount == 0 ? 0 : $basketItem->getTaxRate(),
'vat_amount' => $vatAmount,
];

if (
$basketItem !== null
&& $basketItem->getAttribute() !== null
&& method_exists($basketItem->getAttribute(), 'setBasketItemId')
) {
$basketItem->getAttribute()->setBasketItemId($basketItem->getId());

$this->modelManager->persist($basketItem);
$this->modelManager->flush($basketItem);
}

// add the order line to items
$items[] = $orderLine;
}
} catch (Exception $ex) {

$this->logger->error(
'Error when loading basket lines',
array(
'error' => $ex->getMessage(),
)
);
}

return $items;
}

/**
* @param $basketItem
* @param float $unitPrice
* @return string
*/
private function getOrderType($basketItem, $unitPrice)
{
// set the order line type
if (strpos($basketItem->getOrderNumber(), 'surcharge') !== false) {
return 'surcharge';
}

if (strpos($basketItem->getOrderNumber(), 'discount') !== false) {
return 'discount';
}

if ($basketItem->getEsdArticle() > 0) {
return 'digital';
}

if ($basketItem->getMode() == 2) {
return 'discount';
}

if ($unitPrice < 0) {
return 'discount';
}

return 'physical';
}

/**
* Get a voucher by it's id
*
Expand Down

0 comments on commit bb7d8af

Please sign in to comment.