| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130 |
- <?php
- namespace Tests\Unit\Financeiro;
- use App\Models\City;
- use App\Models\Country;
- use App\Models\FranchiseeContract;
- use App\Models\InhabitantClassification;
- use App\Models\MunicipalitySize;
- use App\Models\State;
- use App\Models\Tbr;
- use App\Models\Unit;
- use App\Models\UnitFinancial;
- use App\Services\TbrBillingPreviewService;
- use Carbon\Carbon;
- use Illuminate\Foundation\Testing\RefreshDatabase;
- use Illuminate\Support\Facades\Bus;
- use Tests\TestCase;
- /**
- * A tela de billing preview (GET /tbr-billing-preview) tinha uma segunda
- * implementação da regra de royalties/FNM/manutenção, divergente da oficial
- * (não comparava com faturamento, ignorava as flags charge_roi/charge_fnm).
- * Ela agora delega para TbrCalculationService::previewBatch() — este teste
- * garante que a tela mostra os mesmos números e critérios do cálculo oficial.
- */
- class TbrBillingPreviewServiceTest extends TestCase
- {
- use RefreshDatabase;
- private TbrBillingPreviewService $service;
- private Unit $unit;
- protected function setUp(): void
- {
- parent::setUp();
- Bus::fake();
- Carbon::setTestNow(Carbon::create(2026, 4, 15));
- $this->service = app(TbrBillingPreviewService::class);
- $country = Country::create(['name' => 'Brasil', 'code' => 'BR']);
- $state = State::create(['name' => 'Paraná', 'code' => 'PR', 'country_id' => $country->id]);
- $city = City::create(['name' => 'Maringá', 'country_id' => $country->id, 'state_id' => $state->id]);
- $this->unit = Unit::create([
- 'fantasy_name' => 'Unidade Teste', 'social_reason' => 'Unidade Teste LTDA',
- 'cnpj' => '00000000000191', 'street' => 'Rua Teste', 'neighborhood' => 'Centro',
- 'postal_code' => '87000000', 'city_id' => $city->id, 'state_id' => $state->id,
- 'email' => 'unidade@teste.com', 'name_responsible' => 'Responsável Teste',
- ]);
- $size = MunicipalitySize::create(['acronym' => 'GP', 'description' => 'De 100 mil a 200 mil habitantes']);
- foreach ([[1, 3, 0.0], [4, 12, 0.75], [13, 60, 1.00]] as [$start, $end, $percentage]) {
- InhabitantClassification::create([
- 'municipality_size_id' => $size->id, 'description' => "Faixa {$start}-{$end}",
- 'start' => $start, 'end' => $end, 'tbr_percentage' => $percentage, 'is_renewal' => false,
- ]);
- }
- Tbr::create([
- 'year' => 2026, 'tbr_value' => 1000.00,
- 'royalties_percentage' => 0.08, 'fnm_percentage' => 0.20, 'maintenance_percentage' => 0.30,
- ]);
- FranchiseeContract::create([
- 'unit_id' => $this->unit->id, 'protocol' => 1, 'name' => 'Contrato de Franquia',
- 'description' => 'Contrato de teste', 'start_date' => '2026-01-01', 'end_date' => '2031-01-01',
- 'signature_date' => '2026-01-01', 'validity_months' => 60, 'invoice_due_date' => 10,
- 'municipality_size_id' => $size->id, 'tbr_fixed_value' => 1000.00,
- ]);
- }
- protected function tearDown(): void
- {
- Carbon::setTestNow();
- parent::tearDown();
- }
- /**
- * Regra: A tela usa exatamente a mesma fórmula do cálculo oficial — fixo (8%
- * base x 75% da faixa GP = 6% da TBR = R$ 60,00) vence porque não há faturamento
- * lançado (nenhuma parcela cadastrada).
- */
- public function test_usa_a_mesma_regra_do_calculo_oficial(): void
- {
- $result = $this->service->getAll()->firstWhere('id', $this->unit->id);
- $this->assertNotNull($result);
- $this->assertEquals(60.0, $result['royalties_value']);
- $this->assertSame('Fixo TBR', $result['royalties_rule']);
- $this->assertEquals(200.0, $result['fnm_value']);
- $this->assertSame('Fixo TBR', $result['fnm_rule']);
- $this->assertEquals(300.0, $result['maintenance_value']);
- $this->assertEquals(560.0, $result['total']);
- }
- /**
- * Regra: Respeita a flag charge_roi da unidade — royalties zerado, rótulo
- * "Não cobrado", assim como no cálculo oficial.
- */
- public function test_respeita_a_flag_charge_roi(): void
- {
- UnitFinancial::create(['unit_id' => $this->unit->id, 'charge_roi' => false, 'charge_fnm' => true]);
- $result = $this->service->getAll()->firstWhere('id', $this->unit->id);
- $this->assertEquals(0.0, $result['royalties_value']);
- $this->assertSame('Não cobrado', $result['royalties_rule']);
- }
- /**
- * Regra: Mês 1-3 aparece como "Isento" em vez de "Fixo TBR".
- */
- public function test_marca_isento_nos_meses_1_a_3(): void
- {
- Carbon::setTestNow(Carbon::create(2026, 2, 15)); // mês de contrato 2
- $result = $this->service->getAll()->firstWhere('id', $this->unit->id);
- $this->assertEquals(0.0, $result['royalties_value']);
- $this->assertSame('Isento', $result['royalties_rule']);
- $this->assertEquals(0.0, $result['fnm_value']);
- $this->assertSame('Isento', $result['fnm_rule']);
- $this->assertEquals(300.0, $result['maintenance_value']);
- }
- }
|