Initial commit
This commit is contained in:
266
tests/Unit/MemberTest.php
Normal file
266
tests/Unit/MemberTest.php
Normal file
@@ -0,0 +1,266 @@
|
||||
<?php
|
||||
|
||||
namespace Tests\Unit;
|
||||
|
||||
use App\Models\Member;
|
||||
use App\Models\User;
|
||||
use App\Models\MembershipPayment;
|
||||
use Illuminate\Foundation\Testing\RefreshDatabase;
|
||||
use Tests\TestCase;
|
||||
|
||||
class MemberTest extends TestCase
|
||||
{
|
||||
use RefreshDatabase;
|
||||
|
||||
protected function setUp(): void
|
||||
{
|
||||
parent::setUp();
|
||||
$this->artisan('db:seed', ['--class' => 'RoleSeeder']);
|
||||
}
|
||||
|
||||
public function test_member_has_required_fillable_fields(): void
|
||||
{
|
||||
$member = Member::factory()->create([
|
||||
'full_name' => 'Test Member',
|
||||
'email' => 'test@example.com',
|
||||
'phone' => '0912345678',
|
||||
]);
|
||||
|
||||
$this->assertEquals('Test Member', $member->full_name);
|
||||
$this->assertEquals('test@example.com', $member->email);
|
||||
$this->assertEquals('0912345678', $member->phone);
|
||||
}
|
||||
|
||||
public function test_member_belongs_to_user(): void
|
||||
{
|
||||
$user = User::factory()->create();
|
||||
$member = Member::factory()->create(['user_id' => $user->id]);
|
||||
|
||||
$this->assertInstanceOf(User::class, $member->user);
|
||||
$this->assertEquals($user->id, $member->user->id);
|
||||
}
|
||||
|
||||
public function test_member_has_many_payments(): void
|
||||
{
|
||||
$member = Member::factory()->create();
|
||||
$payment1 = MembershipPayment::factory()->create(['member_id' => $member->id]);
|
||||
$payment2 = MembershipPayment::factory()->create(['member_id' => $member->id]);
|
||||
|
||||
$this->assertCount(2, $member->payments);
|
||||
$this->assertTrue($member->payments->contains($payment1));
|
||||
$this->assertTrue($member->payments->contains($payment2));
|
||||
}
|
||||
|
||||
public function test_has_paid_membership_returns_true_when_active_with_future_expiry(): void
|
||||
{
|
||||
$member = Member::factory()->create([
|
||||
'membership_status' => Member::STATUS_ACTIVE,
|
||||
'membership_started_at' => now()->subMonth(),
|
||||
'membership_expires_at' => now()->addYear(),
|
||||
]);
|
||||
|
||||
$this->assertTrue($member->hasPaidMembership());
|
||||
}
|
||||
|
||||
public function test_has_paid_membership_returns_false_when_pending(): void
|
||||
{
|
||||
$member = Member::factory()->create([
|
||||
'membership_status' => Member::STATUS_PENDING,
|
||||
'membership_started_at' => null,
|
||||
'membership_expires_at' => null,
|
||||
]);
|
||||
|
||||
$this->assertFalse($member->hasPaidMembership());
|
||||
}
|
||||
|
||||
public function test_has_paid_membership_returns_false_when_expired(): void
|
||||
{
|
||||
$member = Member::factory()->create([
|
||||
'membership_status' => Member::STATUS_ACTIVE,
|
||||
'membership_started_at' => now()->subYear()->subMonth(),
|
||||
'membership_expires_at' => now()->subMonth(),
|
||||
]);
|
||||
|
||||
$this->assertFalse($member->hasPaidMembership());
|
||||
}
|
||||
|
||||
public function test_has_paid_membership_returns_false_when_suspended(): void
|
||||
{
|
||||
$member = Member::factory()->create([
|
||||
'membership_status' => Member::STATUS_SUSPENDED,
|
||||
'membership_started_at' => now()->subMonth(),
|
||||
'membership_expires_at' => now()->addYear(),
|
||||
]);
|
||||
|
||||
$this->assertFalse($member->hasPaidMembership());
|
||||
}
|
||||
|
||||
public function test_can_submit_payment_returns_true_when_pending_and_no_pending_payment(): void
|
||||
{
|
||||
$member = Member::factory()->create([
|
||||
'membership_status' => Member::STATUS_PENDING,
|
||||
]);
|
||||
|
||||
$this->assertTrue($member->canSubmitPayment());
|
||||
}
|
||||
|
||||
public function test_can_submit_payment_returns_false_when_already_has_pending_payment(): void
|
||||
{
|
||||
$member = Member::factory()->create([
|
||||
'membership_status' => Member::STATUS_PENDING,
|
||||
]);
|
||||
|
||||
MembershipPayment::factory()->create([
|
||||
'member_id' => $member->id,
|
||||
'status' => MembershipPayment::STATUS_PENDING,
|
||||
]);
|
||||
|
||||
$this->assertFalse($member->canSubmitPayment());
|
||||
}
|
||||
|
||||
public function test_can_submit_payment_returns_false_when_active(): void
|
||||
{
|
||||
$member = Member::factory()->create([
|
||||
'membership_status' => Member::STATUS_ACTIVE,
|
||||
]);
|
||||
|
||||
$this->assertFalse($member->canSubmitPayment());
|
||||
}
|
||||
|
||||
public function test_get_pending_payment_returns_pending_payment(): void
|
||||
{
|
||||
$member = Member::factory()->create();
|
||||
|
||||
$pendingPayment = MembershipPayment::factory()->create([
|
||||
'member_id' => $member->id,
|
||||
'status' => MembershipPayment::STATUS_PENDING,
|
||||
]);
|
||||
|
||||
$approvedPayment = MembershipPayment::factory()->create([
|
||||
'member_id' => $member->id,
|
||||
'status' => MembershipPayment::STATUS_APPROVED_CHAIR,
|
||||
]);
|
||||
|
||||
$result = $member->getPendingPayment();
|
||||
|
||||
$this->assertNotNull($result);
|
||||
$this->assertEquals($pendingPayment->id, $result->id);
|
||||
}
|
||||
|
||||
public function test_get_pending_payment_returns_null_when_no_pending_payments(): void
|
||||
{
|
||||
$member = Member::factory()->create();
|
||||
|
||||
MembershipPayment::factory()->create([
|
||||
'member_id' => $member->id,
|
||||
'status' => MembershipPayment::STATUS_APPROVED_CHAIR,
|
||||
]);
|
||||
|
||||
$this->assertNull($member->getPendingPayment());
|
||||
}
|
||||
|
||||
public function test_national_id_encryption_and_decryption(): void
|
||||
{
|
||||
$member = Member::factory()->create([
|
||||
'full_name' => 'Test Member',
|
||||
]);
|
||||
|
||||
$nationalId = 'A123456789';
|
||||
$member->national_id = $nationalId;
|
||||
$member->save();
|
||||
|
||||
// Refresh from database
|
||||
$member->refresh();
|
||||
|
||||
// Check encrypted value is different from plain text
|
||||
$this->assertNotEquals($nationalId, $member->national_id_encrypted);
|
||||
|
||||
// Check decryption works
|
||||
$this->assertEquals($nationalId, $member->national_id);
|
||||
}
|
||||
|
||||
public function test_national_id_hash_created_for_search(): void
|
||||
{
|
||||
$member = Member::factory()->create();
|
||||
$nationalId = 'A123456789';
|
||||
|
||||
$member->national_id = $nationalId;
|
||||
$member->save();
|
||||
|
||||
$member->refresh();
|
||||
|
||||
// Check hash was created
|
||||
$this->assertNotNull($member->national_id_hash);
|
||||
|
||||
// Check hash matches SHA256
|
||||
$expectedHash = hash('sha256', $nationalId);
|
||||
$this->assertEquals($expectedHash, $member->national_id_hash);
|
||||
}
|
||||
|
||||
public function test_is_pending_returns_true_when_status_is_pending(): void
|
||||
{
|
||||
$member = Member::factory()->create(['membership_status' => Member::STATUS_PENDING]);
|
||||
$this->assertTrue($member->isPending());
|
||||
}
|
||||
|
||||
public function test_is_active_returns_true_when_status_is_active(): void
|
||||
{
|
||||
$member = Member::factory()->create(['membership_status' => Member::STATUS_ACTIVE]);
|
||||
$this->assertTrue($member->isActive());
|
||||
}
|
||||
|
||||
public function test_is_expired_returns_true_when_status_is_expired(): void
|
||||
{
|
||||
$member = Member::factory()->create(['membership_status' => Member::STATUS_EXPIRED]);
|
||||
$this->assertTrue($member->isExpired());
|
||||
}
|
||||
|
||||
public function test_is_suspended_returns_true_when_status_is_suspended(): void
|
||||
{
|
||||
$member = Member::factory()->create(['membership_status' => Member::STATUS_SUSPENDED]);
|
||||
$this->assertTrue($member->isSuspended());
|
||||
}
|
||||
|
||||
public function test_membership_status_label_returns_chinese_text(): void
|
||||
{
|
||||
$member = Member::factory()->create(['membership_status' => Member::STATUS_PENDING]);
|
||||
$this->assertEquals('待繳費', $member->membership_status_label);
|
||||
|
||||
$member->membership_status = Member::STATUS_ACTIVE;
|
||||
$this->assertEquals('已啟用', $member->membership_status_label);
|
||||
|
||||
$member->membership_status = Member::STATUS_EXPIRED;
|
||||
$this->assertEquals('已過期', $member->membership_status_label);
|
||||
|
||||
$member->membership_status = Member::STATUS_SUSPENDED;
|
||||
$this->assertEquals('已暫停', $member->membership_status_label);
|
||||
}
|
||||
|
||||
public function test_membership_type_label_returns_chinese_text(): void
|
||||
{
|
||||
$member = Member::factory()->create(['membership_type' => Member::TYPE_REGULAR]);
|
||||
$this->assertEquals('一般會員', $member->membership_type_label);
|
||||
|
||||
$member->membership_type = Member::TYPE_STUDENT;
|
||||
$this->assertEquals('學生會員', $member->membership_type_label);
|
||||
|
||||
$member->membership_type = Member::TYPE_HONORARY;
|
||||
$this->assertEquals('榮譽會員', $member->membership_type_label);
|
||||
|
||||
$member->membership_type = Member::TYPE_LIFETIME;
|
||||
$this->assertEquals('終身會員', $member->membership_type_label);
|
||||
}
|
||||
|
||||
public function test_membership_status_badge_returns_correct_css_class(): void
|
||||
{
|
||||
$member = Member::factory()->create(['membership_status' => Member::STATUS_PENDING]);
|
||||
$badge = $member->membership_status_badge;
|
||||
|
||||
$this->assertStringContainsString('待繳費', $badge);
|
||||
$this->assertStringContainsString('bg-yellow', $badge);
|
||||
|
||||
$member->membership_status = Member::STATUS_ACTIVE;
|
||||
$badge = $member->membership_status_badge;
|
||||
$this->assertStringContainsString('bg-green', $badge);
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user