Skip to content

Commit

Permalink
Merge pull request #48 from mrk-j/master
Browse files Browse the repository at this point in the history
Calculate net from gross amount
  • Loading branch information
mpociot authored Apr 11, 2017
2 parents 1ae3444 + a84e263 commit 86776da
Show file tree
Hide file tree
Showing 2 changed files with 271 additions and 0 deletions.
31 changes: 31 additions & 0 deletions src/Mpociot/VatCalculator/VatCalculator.php
Original file line number Diff line number Diff line change
Expand Up @@ -431,6 +431,37 @@ public function calculate($netPrice, $countryCode = null, $postalCode = null, $c
return $this->value;
}

/**
* Calculate the net price on the gross price, country code and indication if the
* customer is a company or not.
*
* @param int|float $gross The gross price to use for the calculation
* @param null|string $countryCode The country code to use for the rate lookup
* @param null|string $postalCode The postal code to use for the rate exception lookup
* @param null|bool $company
*
* @return float
*/
public function calculateNet($gross, $countryCode = null, $postalCode = null, $company = null)
{
if ($countryCode) {
$this->setCountryCode($countryCode);
}
if ($postalCode) {
$this->setPostalCode($postalCode);
}
if (!is_null($company) && $company !== $this->isCompany()) {
$this->setCompany($company);
}

$this->value = floatval($gross);
$this->taxRate = $this->getTaxRateForLocation($this->getCountryCode(), $this->getPostalCode(), $this->isCompany());
$this->taxValue = $this->taxRate > 0 ? $this->value / (1 + $this->taxRate) * $this->taxRate : 0;
$this->netPrice = $this->value - $this->taxValue;

return $this->netPrice;
}

/**
* @return float
*/
Expand Down
240 changes: 240 additions & 0 deletions tests/VatCalculatorTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -599,4 +599,244 @@ public function testShouldCollectVATFromConfig()
$vatCalculator = new VatCalculator($config);
$this->assertTrue($vatCalculator->shouldCollectVAT($countryCode));
}

public function testCalculateNetPriceWithoutCountry()
{
$config = m::mock('Illuminate\Contracts\Config\Repository');

$config->shouldReceive('has')
->once()
->with('vat_calculator.business_country_code')
->andReturn(false);

$config->shouldReceive('has')
->once()
->with('vat_calculator.rules.')
->andReturn(false);

$gross = 25.00;

$vatCalculator = new VatCalculator($config);
$result = $vatCalculator->calculateNet($gross);
$this->assertEquals(25.00, $result);
}

public function testCalculateNetPriceWithoutCountryAndConfig()
{
$gross = 25.00;

$vatCalculator = new VatCalculator();
$result = $vatCalculator->calculateNet($gross);
$this->assertEquals(25.00, $result);
}

public function testCalculateNetPriceWithPredefinedRules()
{
$gross = 28.56;
$countryCode = 'DE';

$config = m::mock('Illuminate\Contracts\Config\Repository');
$config->shouldReceive('get')
->never();

$config->shouldReceive('has')
->once()
->with('vat_calculator.rules.DE')
->andReturn(false);

$config->shouldReceive('has')
->once()
->with('vat_calculator.business_country_code')
->andReturn(false);

$vatCalculator = new VatCalculator($config);
$result = $vatCalculator->calculateNet($gross, $countryCode);
$this->assertEquals(24.00, $result);
$this->assertEquals(0.19, $vatCalculator->getTaxRate());
$this->assertEquals(4.56, $vatCalculator->getTaxValue());
}

public function testCalculateNetPriceWithPredefinedRulesWithoutConfig()
{
$gross = 28.56;
$countryCode = 'DE';

$vatCalculator = new VatCalculator();
$result = $vatCalculator->calculateNet($gross, $countryCode);
$this->assertEquals(24.00, $result);
$this->assertEquals(0.19, $vatCalculator->getTaxRate());
$this->assertEquals(4.56, $vatCalculator->getTaxValue());
}

public function testCalculateNetPriceWithPredefinedRulesOverwrittenByConfiguration()
{
$gross = 36.00;
$countryCode = 'DE';

$taxKey = 'vat_calculator.rules.'.strtoupper($countryCode);

$config = m::mock('Illuminate\Contracts\Config\Repository');
$config->shouldReceive('get')
->once()
->with($taxKey, 0)
->andReturn(0.50);

$config->shouldReceive('has')
->once()
->with($taxKey)
->andReturn(true);

$config->shouldReceive('has')
->once()
->with('vat_calculator.business_country_code')
->andReturn(false);

$vatCalculator = new VatCalculator($config);
$result = $vatCalculator->calculateNet($gross, $countryCode);
$this->assertEquals(24.00, $result);
$this->assertEquals(0.50, $vatCalculator->getTaxRate());
$this->assertEquals(12.00, $vatCalculator->getTaxValue());
}

public function testCalculateNetPriceWithCountryDirectSet()
{
$gross = 28.56;
$countryCode = 'DE';

$config = m::mock('Illuminate\Contracts\Config\Repository');
$config->shouldReceive('get')
->once()
->with('vat_calculator.rules.'.$countryCode, 0)
->andReturn(0.19);

$config->shouldReceive('has')
->once()
->with('vat_calculator.rules.'.$countryCode)
->andReturn(true);

$config->shouldReceive('has')
->once()
->with('vat_calculator.business_country_code')
->andReturn(false);

$vatCalculator = new VatCalculator($config);
$result = $vatCalculator->calculateNet($gross, $countryCode);
$this->assertEquals(24.00, $result);
$this->assertEquals(0.19, $vatCalculator->getTaxRate());
$this->assertEquals(4.56, $vatCalculator->getTaxValue());
}

public function testCalculateNetPriceWithCountryDirectSetWithoutConfiguration()
{
$gross = 28.56;
$countryCode = 'DE';

$vatCalculator = new VatCalculator();

$result = $vatCalculator->calculateNet($gross, $countryCode);
$this->assertEquals(24.00, $result);
$this->assertEquals(0.19, $vatCalculator->getTaxRate());
$this->assertEquals(4.56, $vatCalculator->getTaxValue());
}

public function testCalculateNetPriceWithCountryPreviousSet()
{
$gross = 28.56;
$countryCode = 'DE';

$config = m::mock('Illuminate\Contracts\Config\Repository');
$config->shouldReceive('get')
->once()
->with('vat_calculator.rules.'.$countryCode, 0)
->andReturn(0.19);

$config->shouldReceive('has')
->once()
->with('vat_calculator.rules.'.$countryCode)
->andReturn(true);

$config->shouldReceive('has')
->once()
->with('vat_calculator.business_country_code')
->andReturn(false);

$vatCalculator = new VatCalculator($config);
$vatCalculator->setCountryCode($countryCode);

$result = $vatCalculator->calculateNet($gross);
$this->assertEquals(24.00, $result);
$this->assertEquals(0.19, $vatCalculator->getTaxRate());
$this->assertEquals(4.56, $vatCalculator->getTaxValue());
}

public function testCalculateNetPriceWithCountryAndCompany()
{
$gross = 28.56;
$countryCode = 'DE';
$postalCode = null;
$company = true;

$config = m::mock('Illuminate\Contracts\Config\Repository');
$config->shouldReceive('get')
->never();

$config->shouldReceive('has')
->once()
->with('vat_calculator.business_country_code')
->andReturn(false);

$vatCalculator = new VatCalculator($config);
$result = $vatCalculator->calculateNet($gross, $countryCode, $postalCode, $company);
$this->assertEquals(28.56, $result);
$this->assertEquals(0, $vatCalculator->getTaxRate());
$this->assertEquals(0, $vatCalculator->getTaxValue());
}

public function testCalculateNetPriceWithCountryAndCompanySet()
{
$gross = 24.00;
$countryCode = 'DE';
$company = true;

$config = m::mock('Illuminate\Contracts\Config\Repository');
$config->shouldReceive('get')
->never();

$config->shouldReceive('has')
->once()
->with('vat_calculator.business_country_code')
->andReturn(false);

$vatCalculator = new VatCalculator($config);
$vatCalculator->setCompany($company);
$result = $vatCalculator->calculateNet($gross, $countryCode);
$this->assertEquals(24.00, $result);
$this->assertEquals(24.00, $vatCalculator->getNetPrice());
$this->assertEquals(0, $vatCalculator->getTaxRate());
$this->assertEquals(0, $vatCalculator->getTaxValue());
}

public function testCalculateNetPriceWithCountryAndCompanyBothSet()
{
$gross = 24.00;
$countryCode = 'DE';
$company = true;

$config = m::mock('Illuminate\Contracts\Config\Repository');
$config->shouldReceive('get')
->never();

$config->shouldReceive('has')
->once()
->with('vat_calculator.business_country_code')
->andReturn(false);

$vatCalculator = new VatCalculator($config);
$vatCalculator->setCountryCode($countryCode);
$vatCalculator->setCompany($company);
$result = $vatCalculator->calculateNet($gross);
$this->assertEquals(24.00, $result);
$this->assertEquals(0, $vatCalculator->getTaxRate());
$this->assertEquals(0, $vatCalculator->getTaxValue());
}
}

0 comments on commit 86776da

Please sign in to comment.