Enable gross price as base price

This commit is contained in:
sartoric
2020-02-12 22:42:41 +01:00
parent 97e021f4cc
commit 2078f119ec
3 changed files with 113 additions and 24 deletions

View File

@@ -7,6 +7,18 @@ use Illuminate\Contracts\Support\Arrayable;
use Illuminate\Contracts\Support\Jsonable;
use Illuminate\Support\Arr;
/**
* @property-read mixed discount
* @property-read float discountTotal
* @property-read float priceTarget
* @property-read float priceNet
* @property-read float priceTotal
* @property-read float subtotal
* @property-read float taxTotal
* @property-read float tax
* @property-read float total
* @property-read float priceTax
*/
class CartItem implements Arrayable, Jsonable
{
/**
@@ -371,39 +383,66 @@ class CartItem implements Arrayable, Jsonable
$decimals = config('cart.format.decimals', 2);
switch ($attribute) {
case 'discount':
return $this->price * ($this->discountRate / 100);
case 'tax':
return round($this->priceTarget * ($this->taxRate / 100), $decimals);
case 'priceTax':
return round($this->priceTarget + $this->tax, $decimals);
case 'discountTotal':
return round($this->discount * $this->qty, $decimals);
case 'weightTotal':
return round($this->weight * $this->qty, $decimals);
case 'priceTotal':
return round($this->price * $this->qty, $decimals);
case 'subtotal':
return round($this->priceTotal - $this->discountTotal, $decimals);
case 'priceTarget':
return round(($this->priceTotal - $this->discountTotal) / $this->qty, $decimals);
case 'taxTotal':
return round($this->subtotal * ($this->taxRate / 100), $decimals);
case 'total':
return round($this->subtotal + $this->taxTotal, $decimals);
case 'model':
if (isset($this->associatedModel)) {
return with(new $this->associatedModel())->find($this->id);
}
case 'modelFQCN':
if (isset($this->associatedModel)) {
return $this->associatedModel;
}
case 'weightTotal':
return round($this->weight * $this->qty, $decimals);
}
default:
return;
if (config('cart.gross_price')) {
switch ($attribute) {
case 'priceNet':
return round($this->price / (1 + ($this->taxRate / 100)), $decimals);
case 'discount':
return $this->priceNet * ($this->discountRate / 100);
case 'tax':
return round($this->priceTarget * ($this->taxRate / 100), $decimals);
case 'priceTax':
return round($this->priceTarget + $this->tax, $decimals);
case 'discountTotal':
return round($this->discount * $this->qty, $decimals);
case 'priceTotal':
return round($this->priceNet * $this->qty, $decimals);
case 'subtotal':
return round($this->priceTotal - $this->discountTotal, $decimals);
case 'priceTarget':
return round(($this->priceTotal - $this->discountTotal) / $this->qty, $decimals);
case 'taxTotal':
return round($this->subtotal * ($this->taxRate / 100), $decimals);
case 'total':
return round($this->subtotal + $this->taxTotal, $decimals);
default:
return;
}
} else {
switch ($attribute) {
case 'discount':
return $this->price * ($this->discountRate / 100);
case 'tax':
return round($this->priceTarget * ($this->taxRate / 100), $decimals);
case 'priceTax':
return round($this->priceTarget + $this->tax, $decimals);
case 'discountTotal':
return round($this->discount * $this->qty, $decimals);
case 'priceTotal':
return round($this->price * $this->qty, $decimals);
case 'subtotal':
return round($this->priceTotal - $this->discountTotal, $decimals);
case 'priceTarget':
return round(($this->priceTotal - $this->discountTotal) / $this->qty, $decimals);
case 'taxTotal':
return round($this->subtotal * ($this->taxRate / 100), $decimals);
case 'total':
return round($this->subtotal + $this->taxTotal, $decimals);
default:
return;
}
}
}

View File

@@ -2,6 +2,18 @@
return [
/*
|--------------------------------------------------------------------------
| Gross price as base price
|--------------------------------------------------------------------------
|
| This default value is used to select the method to calculate prices and taxes
| If true the item price is managed as a gross price, so taxes will be calculated by separation/exclusion
|
*/
'gross_price' => false,
/*
|--------------------------------------------------------------------------
| Default tax rate

View File

@@ -1329,6 +1329,44 @@ class CartTest extends TestCase
$this->assertEquals($cart->totalFloat(), $cart->subtotalFloat() + $cart->taxFloat());
}
/** @test */
public function it_use_gross_price_as_base_price()
{
$cart = $this->getCartDiscount(0);
config(['cart.gross_price' => true]);
$cartItem = $cart->add(new BuyableProduct(1, 'First item', 100), 2);
$cart->setGlobalTax(22);
// check net price
$this->assertEquals(81.97, round($cartItem->priceNet,2));
}
/** @test */
public function it_use_gross_price_and_it_use_correctly_rounded_values_for_totals_and_cart_summary()
{
$this->setConfigFormat(2, ',', '');
config(['cart.gross_price' => true]);
$cart = $this->getCartDiscount(6);
$cartItem = $cart->add(new BuyableProduct(1, 'First item', 0.23093), 1000);
$cart->add(new BuyableProduct(2, 'Second item', 5.38791), 5);
$cart->add(new BuyableProduct(3, 'Third item', 0.46354), 25);
$cart->setGlobalTax(22);
// check total
$this->assertEquals('254,12', $cart->total());
// check item price total
$this->assertEquals(190, $cartItem->priceTotal);
// check that the sum of cart subvalues matches the total (in order to avoid cart summary to looks wrong)
$this->assertEquals($cart->totalFloat(), $cart->subtotalFloat() + $cart->taxFloat());
}
/**
* Get an instance of the cart.
*