Files

96 lines
3.0 KiB
PHP
Raw Permalink Normal View History

<?php
namespace Tests\Feature;
use App\Models\Approval;
use App\Models\CashCategory;
use App\Models\CashRecord;
use App\Models\User;
use App\Models\Vote;
use Illuminate\Foundation\Testing\RefreshDatabase;
use Tests\TestCase;
class CashRecordObserverTest extends TestCase
{
use RefreshDatabase;
private User $user;
private CashCategory $category;
protected function setUp(): void
{
parent::setUp();
$this->user = User::factory()->create();
$this->category = CashCategory::create(['name' => 'Umum']);
$this->actingAs($this->user);
}
private function makeRecord(int $amount): CashRecord
{
return CashRecord::create([
'amount' => $amount,
'category_id' => $this->category->id,
'description' => 'Test',
'date' => now()->toDateString(),
'created_by' => $this->user->id,
]);
}
public function test_small_transaction_creates_no_approval_or_vote(): void
{
$record = $this->makeRecord(100_000);
$this->assertDatabaseMissing('approvals', ['model_id' => $record->id]);
$this->assertDatabaseMissing('votes', ['related_id' => $record->id]);
}
public function test_mid_transaction_creates_approval(): void
{
$record = $this->makeRecord(1_000_000);
$this->assertDatabaseHas('approvals', [
'model_type' => CashRecord::class,
'model_id' => $record->id,
'status' => 'pending',
]);
$this->assertDatabaseMissing('votes', ['related_id' => $record->id]);
}
public function test_mid_transaction_does_not_duplicate_approval(): void
{
$record = $this->makeRecord(1_000_000);
// Simulate retry — observer called again
(new \App\Observers\CashRecordObserver)->created($record);
$this->assertSame(1, Approval::where('model_id', $record->id)->count());
}
public function test_large_transaction_creates_vote(): void
{
$record = $this->makeRecord(3_000_000);
$this->assertDatabaseHas('votes', [
'related_type' => CashRecord::class,
'related_id' => $record->id,
'type' => 'finance',
]);
$this->assertDatabaseMissing('approvals', ['model_id' => $record->id]);
}
public function test_verified_record_cannot_be_deleted(): void
{
$record = $this->makeRecord(100_000);
$record->update(['verified_by' => $this->user->id, 'verified_at' => now()]);
// Beri permission Delete:CashRecord agar Policy logic yang diuji (bukan permission check)
\Spatie\Permission\Models\Permission::firstOrCreate(['name' => 'Delete:CashRecord', 'guard_name' => 'web']);
$this->user->givePermissionTo('Delete:CashRecord');
// CashRecordPolicy::delete() return false jika verified_at !== null
$this->assertFalse(
$this->user->can('delete', $record),
'User seharusnya tidak bisa menghapus transaksi yang sudah diverifikasi.'
);
}
}