Skip to content

Commit

Permalink
add Taxable trait and tests
Browse files Browse the repository at this point in the history
  • Loading branch information
Yorchi committed Mar 18, 2018
1 parent 1e68cd9 commit a4af189
Show file tree
Hide file tree
Showing 8 changed files with 369 additions and 8 deletions.
3 changes: 2 additions & 1 deletion src/Models/Tax.php
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,8 @@ public function taxGroup()

public function info(): TaxContract
{
$className = '\\FeiMx\\Tax\\Taxes\\'. strtoupper($this->name);
$className = '\\FeiMx\\Tax\\Taxes\\'.strtoupper($this->name);

return new $className($this->retention);
}

Expand Down
4 changes: 2 additions & 2 deletions src/TaxManager.php
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@ public function addTax($tax, $retention = false)
$tax = new $className($retention);
}

if (! in_array($tax, $this->taxes)) {
if (!in_array($tax, $this->taxes)) {
$this->taxes[] = $tax;
}

Expand Down Expand Up @@ -107,7 +107,7 @@ public function get()
public function stringToClassName($tax)
{
$className = 'FeiMx\\Tax\\Taxes\\'.strtoupper($tax);
if (! class_exists($className)) {
if (!class_exists($className)) {
throw new TaxErrorException("The tax '{$tax}' is not valid");
}

Expand Down
2 changes: 1 addition & 1 deletion src/TaxServiceProvider.php
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@ class TaxServiceProvider extends ServiceProvider
*/
public function boot()
{
if (! class_exists('CreateTaxesTables')) {
if (!class_exists('CreateTaxesTables')) {
$timestamp = date('Y_m_d_His', time());
$this->publishes([
__DIR__.'/../database/migrations/create_taxes_tables.php.stub' => $this->app->databasePath()."/migrations/{$timestamp}_create_taxes_tables.php",
Expand Down
182 changes: 182 additions & 0 deletions src/Traits/Taxable.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,182 @@
<?php

namespace FeiMx\Tax\Traits;

use FeiMx\Tax\Exceptions\TaxErrorException;
use FeiMx\Tax\Models\TaxGroup;
use Illuminate\Database\Eloquent\Relations\MorphToMany;

trait Taxable
{
/**
* Column name used for get the price of the model.
*
* @return string Column name
*/
public static function priceColumn()
{
return 'price';
}

/**
* [taxGroups description].
*
* @return [type] [description]
*/
public function taxGroups(): MorphToMany
{
return $this->morphToMany(
TaxGroup::class,
'model',
'model_has_tax_groups',
'model_id',
'tax_group_id'
);
}

public function hasTaxGroups()
{
return (bool) $this->taxGroups->count();
}

/**
* Determine if the model has (one of) the given tax group(s).
*
* @param string|array|\FeiMx\Tax\Models\TaxGroup|\Illuminate\Support\Collection $taxGroups
*
* @return bool
*/
public function hasTaxGroup($taxGroups)
{
if (is_string($taxGroups)) {
return $this->taxGroups->contains('name', $taxGroups);
}
if ($taxGroups instanceof TaxGroup) {
return $this->taxGroups->contains('id', $taxGroups->id);
}
if (is_array($taxGroups)) {
foreach ($taxGroups as $taxGroup) {
if ($this->hasTaxGroup($taxGroup)) {
return true;
}
}

return false;
}

return $taxGroups->intersect($this->taxGroups)->isNotEmpty();
}

/**
* Assign the given taxGroup to the model.
*
* @param array|string|\FeiMx\Tax\Models\TaxGroup ...$taxGroups
*
* @return $this
*/
public function assignTaxGroup(...$taxGroups)
{
if (0 == count($taxGroups)) {
throw new TaxErrorException('You must pass a valid TaxGroup');
}

$taxGroups = collect($taxGroups)
->flatten()
->map(function ($taxGroup) {
return $this->getStoredTaxGroup($taxGroup);
})
->all();

$this->taxGroups()->saveMany($taxGroups);

return $this;
}

/**
* Revoke the given role from the model.
*
* @param string|\FeiMx\Tax\Models\TaxGroup $taxGroup
*/
public function removeTaxGroup($taxGroup)
{
$this->taxGroups()->detach($this->getStoredTaxGroup($taxGroup));
}

/**
* Remove all current tax groups and set the given ones.
*
* @param array|\FeiMx\Tax\Models\TaxGroup|string ...$taxGroups
*
* @return $this
*/
public function syncTaxGroups(...$taxGroups)
{
$this->taxGroups()->detach();

return $this->assignTaxGroup($taxGroups);
}

/**
* Get total amount for current TaxGroup.
*
* @param \FeiMx\Tax\Models\TaxGroup|string $taxGroup
*
* @return $total
*/
public function total($taxGroup = null)
{
if (null === $taxGroup) {
throw new TaxErrorException('You must pass a valid TaxGroup');
}

$taxGroup = $this->getStoredTaxGroup($taxGroup);
$column = self::priceColumn();

return $total = $taxGroup->taxManager($this->{$column})
->addTaxes(
$taxGroup->taxes->map(function ($tax) {
return $tax->info();
})
->all()
)
->total();
}

/**
* Get a list of taxes with amount calculated for the given TaxGroup.
*
* @param \FeiMx\Tax\Models\TaxGroup|string $taxGroup
*
* @return $total
*/
public function getAmounts($taxGroup = null)
{
if (null === $taxGroup) {
throw new TaxErrorException('You must pass a valid TaxGroup');
}

$taxGroup = $this->getStoredTaxGroup($taxGroup);
$column = self::priceColumn();

return $taxGroup->taxManager($this->{$column})
->addTaxes(
$taxGroup->taxes->map(function ($tax) {
return $tax->info();
})
->all()
)
->get();
}

protected function getStoredTaxGroup($taxGroup): TaxGroup
{
if (is_numeric($taxGroup)) {
return TaxGroup::find($taxGroup);
}
if (is_string($taxGroup)) {
return TaxGroup::whereName($taxGroup)->first();
}

return $taxGroup;
}
}
6 changes: 5 additions & 1 deletion tests/Product.php
Original file line number Diff line number Diff line change
@@ -1,10 +1,14 @@
<?php

namespace FeiMx\Tax\Tests;

use FeiMx\Tax\Traits\Taxable;
use Illuminate\Database\Eloquent\Model;

class Product extends Model
{
use Taxable;

/**
* The attributes that are mass assignable.
*
Expand All @@ -15,4 +19,4 @@ class Product extends Model
public $timestamps = false;

protected $table = 'products';
}
}
16 changes: 15 additions & 1 deletion tests/Service.php
Original file line number Diff line number Diff line change
@@ -1,10 +1,14 @@
<?php

namespace FeiMx\Tax\Tests;

use FeiMx\Tax\Traits\Taxable;
use Illuminate\Database\Eloquent\Model;

class Service extends Model
{
use Taxable;

/**
* The attributes that are mass assignable.
*
Expand All @@ -15,4 +19,14 @@ class Service extends Model
public $timestamps = false;

protected $table = 'services';
}

/**
* Column name used for get the price of the model.
*
* @return string Column name
*/
public static function priceColumn()
{
return 'amount';
}
}
Loading

0 comments on commit a4af189

Please sign in to comment.