131 lines
4.3 KiB
PHP
131 lines
4.3 KiB
PHP
<?php
|
|
|
|
namespace Tests\Feature;
|
|
|
|
use App\Http\Requests\ContractRequest;
|
|
use App\Models\Contract;
|
|
use App\Services\ContractService;
|
|
use Illuminate\Database\Schema\Blueprint;
|
|
use Illuminate\Support\Facades\Schema;
|
|
use Illuminate\Support\Facades\Validator;
|
|
use Illuminate\Validation\ValidationException;
|
|
use Tests\Support\IsolatedDatabaseTestCase;
|
|
|
|
class ContractPersistenceTest extends IsolatedDatabaseTestCase
|
|
{
|
|
protected function setUp(): void
|
|
{
|
|
parent::setUp();
|
|
Schema::table('contracts', function (Blueprint $table) {
|
|
$table->decimal('go_ki')->nullable();
|
|
$table->string('code')->nullable();
|
|
$table->string('supply_type')->nullable();
|
|
});
|
|
}
|
|
|
|
public function test_duplicate_supply_code_requires_explicit_confirmation(): void
|
|
{
|
|
$user = $this->authenticate();
|
|
Contract::create([
|
|
'client_id' => 1,
|
|
'code' => 'CPE-123',
|
|
'supply_type' => 'cpe',
|
|
]);
|
|
|
|
$request = ContractRequest::create('/contract', 'POST', [
|
|
'code' => 'CPE-123',
|
|
'supply_type' => 'cpe',
|
|
]);
|
|
$request->setUserResolver(fn () => $user);
|
|
$validator = Validator::make($request->all(), []);
|
|
$request->withValidator($validator);
|
|
|
|
$this->assertFalse($validator->passes());
|
|
$this->assertArrayHasKey('duplicate_code', $validator->errors()->messages());
|
|
|
|
$request->merge(['confirm_duplicate' => '1']);
|
|
$confirmedValidator = Validator::make($request->all(), []);
|
|
$request->withValidator($confirmedValidator);
|
|
|
|
$this->assertTrue($confirmedValidator->passes());
|
|
}
|
|
|
|
public function test_update_persists_chargeback_and_deducts_it_from_profit(): void
|
|
{
|
|
$user = $this->authenticate(financial: true);
|
|
$contract = Contract::create([
|
|
'client_id' => 1,
|
|
'contract_value' => 882.32,
|
|
'commission_value' => 588.92,
|
|
'profit_value' => 293.40,
|
|
'go_ki' => 1,
|
|
]);
|
|
|
|
$requestData = [
|
|
'contract_value' => 882.32,
|
|
'commission_value' => 588.92,
|
|
'chargeback_value' => -935.79,
|
|
'chargeback_date' => '2026-09-21',
|
|
'go_ki' => 1,
|
|
];
|
|
$request = $this->contractRequest($requestData, $user);
|
|
|
|
app(ContractService::class)->update($request, (string) $contract->id);
|
|
|
|
$this->assertDatabaseHas('contracts', [
|
|
'id' => $contract->id,
|
|
'chargeback' => true,
|
|
'chargeback_value' => -935.79,
|
|
'chargeback_date' => '2026-09-21',
|
|
'profit_value' => -642.39,
|
|
]);
|
|
}
|
|
|
|
public function test_update_reports_an_error_when_model_save_is_cancelled(): void
|
|
{
|
|
$user = $this->authenticate(financial: true);
|
|
$contract = Contract::create([
|
|
'client_id' => 1,
|
|
'contract_value' => 100,
|
|
'commission_value' => 10,
|
|
'profit_value' => 90,
|
|
'go_ki' => 1,
|
|
]);
|
|
Contract::saving(fn () => false);
|
|
|
|
$requestData = [
|
|
'contract_value' => 100,
|
|
'commission_value' => 10,
|
|
'chargeback' => false,
|
|
'go_ki' => 1,
|
|
'notes' => 'This save must be rejected',
|
|
];
|
|
$request = $this->contractRequest($requestData, $user);
|
|
|
|
try {
|
|
app(ContractService::class)->update($request, (string) $contract->id);
|
|
$this->fail('A cancelled contract save must be reported as an error.');
|
|
} catch (ValidationException $exception) {
|
|
$this->assertArrayHasKey('contract', $exception->errors());
|
|
}
|
|
|
|
$this->assertDatabaseMissing('contracts', [
|
|
'id' => $contract->id,
|
|
'notes' => 'This save must be rejected',
|
|
]);
|
|
}
|
|
|
|
private function contractRequest(array $data, object $user): ContractRequest
|
|
{
|
|
$request = ContractRequest::create('/contract/1/update', 'PUT', $data);
|
|
$request->setUserResolver(fn () => $user);
|
|
$prepareForValidation = new \ReflectionMethod(ContractRequest::class, 'prepareForValidation');
|
|
$prepareForValidation->invoke($request);
|
|
$requestData = $request->all();
|
|
$rules = array_fill_keys(array_keys($requestData), ['sometimes']);
|
|
$request->setValidator(app('validator')->make($requestData, $rules));
|
|
|
|
return $request;
|
|
}
|
|
}
|