seed(RolePermissionSeeder::class); }); // ─── CachesQuery Trait ───────────────────────────────────── describe('CachesQuery Trait', function () { test('cacheRemember stores and retrieves value', function () { $service = new class { use CachesQuery; public function callRemember(): array { return $this->cacheRemember('test:key', 60, function () { return ['foo' => 'bar']; }); } }; $result = $service->callRemember(); expect($result)->toBe(['foo' => 'bar']); expect(Cache::has('test:key'))->toBeTrue(); }); test('cacheRemember returns cached value on second call', function () { $service = new class { use CachesQuery; public int $callCount = 0; public function callRemember(): array { return $this->cacheRemember('test:counter', 60, function () { $this->callCount++; return ['count' => $this->callCount]; }); } }; $first = $service->callRemember(); $second = $service->callRemember(); expect($first)->toBe(['count' => 1]); expect($second)->toBe(['count' => 1]); expect($service->callCount)->toBe(1); }); test('cacheForget removes cached value', function () { $service = new class { use CachesQuery; public function callRemember(): array { return $this->cacheRemember('test:forget', 60, function () { return ['data' => true]; }); } public function callForget(): void { $this->cacheForget('test:forget'); } }; $service->callRemember(); expect(Cache::has('test:forget'))->toBeTrue(); $service->callForget(); expect(Cache::has('test:forget'))->toBeFalse(); }); test('cacheForever stores value without expiration', function () { $service = new class { use CachesQuery; public function callForever(): string { return $this->cacheForever('test:forever', function () { return 'permanent'; }); } }; $result = $service->callForever(); expect($result)->toBe('permanent'); expect(Cache::has('test:forever'))->toBeTrue(); }); }); // ─── Category Cache ──────────────────────────────────────── describe('Category Caching', function () { test('getSelectOptions caches results', function () { Category::factory()->count(3)->create(); $service = app(CategoryService::class); $first = $service->getSelectOptions(); expect($first)->toHaveCount(3); expect(Cache::has('master:categories:options'))->toBeTrue(); Category::create(['name' => 'New Category']); $second = $service->getSelectOptions(); expect($second)->toHaveCount(3); Cache::forget('master:categories:options'); $third = $service->getSelectOptions(); expect($third)->toHaveCount(4); }); test('create invalidates category cache', function () { $service = app(CategoryService::class); $service->getSelectOptions(); expect(Cache::has('master:categories:options'))->toBeTrue(); $service->create(['name' => 'Test']); expect(Cache::has('master:categories:options'))->toBeFalse(); }); test('update invalidates category cache', function () { $category = Category::factory()->create(); $service = app(CategoryService::class); $service->getSelectOptions(); expect(Cache::has('master:categories:options'))->toBeTrue(); $service->update($category, ['name' => 'Updated']); expect(Cache::has('master:categories:options'))->toBeFalse(); }); test('delete invalidates category cache', function () { $category = Category::factory()->create(); $service = app(CategoryService::class); $service->getSelectOptions(); expect(Cache::has('master:categories:options'))->toBeTrue(); $service->delete($category); expect(Cache::has('master:categories:options'))->toBeFalse(); }); }); // ─── Supplier Cache ──────────────────────────────────────── describe('Supplier Caching', function () { test('getSelectOptions caches results', function () { Supplier::factory()->count(3)->create(); $service = app(SupplierService::class); $first = $service->getSelectOptions(); expect($first)->toHaveCount(3); expect(Cache::has('master:suppliers:options'))->toBeTrue(); Cache::forget('master:suppliers:options'); $second = $service->getSelectOptions(); expect($second)->toHaveCount(3); }); test('create invalidates supplier cache', function () { $service = app(SupplierService::class); $service->getSelectOptions(); expect(Cache::has('master:suppliers:options'))->toBeTrue(); $service->create(['name' => 'Test Supplier', 'phone_number' => '08123', 'address' => 'Jl. Test']); expect(Cache::has('master:suppliers:options'))->toBeFalse(); }); test('update invalidates supplier cache', function () { $supplier = Supplier::factory()->create(); $service = app(SupplierService::class); $service->getSelectOptions(); expect(Cache::has('master:suppliers:options'))->toBeTrue(); $service->update($supplier, ['name' => 'Updated']); expect(Cache::has('master:suppliers:options'))->toBeFalse(); }); test('delete invalidates supplier cache', function () { $supplier = Supplier::factory()->create(); $service = app(SupplierService::class); $service->getSelectOptions(); expect(Cache::has('master:suppliers:options'))->toBeTrue(); $service->delete($supplier); expect(Cache::has('master:suppliers:options'))->toBeFalse(); }); }); // ─── Customer Cache ──────────────────────────────────────── describe('Customer Caching', function () { test('getSelectOptions caches results', function () { Customer::factory()->count(3)->create(); $service = app(CustomerService::class); $first = $service->getSelectOptions(); expect($first)->toHaveCount(3); expect(Cache::has('master:customers:options'))->toBeTrue(); Cache::forget('master:customers:options'); $second = $service->getSelectOptions(); expect($second)->toHaveCount(3); }); test('create invalidates customer cache', function () { $service = app(CustomerService::class); $service->getSelectOptions(); expect(Cache::has('master:customers:options'))->toBeTrue(); $service->create(['name' => 'Test Customer', 'phone_number' => '08123', 'address' => 'Jl. Test']); expect(Cache::has('master:customers:options'))->toBeFalse(); }); test('createAndReturn invalidates customer cache', function () { $service = app(CustomerService::class); $service->getSelectOptions(); expect(Cache::has('master:customers:options'))->toBeTrue(); $customer = $service->createAndReturn(['name' => 'Test', 'phone_number' => '08123', 'address' => 'Jl. Test']); expect($customer)->toBeInstanceOf(Customer::class); expect(Cache::has('master:customers:options'))->toBeFalse(); }); test('update invalidates customer cache', function () { $customer = Customer::factory()->create(); $service = app(CustomerService::class); $service->getSelectOptions(); expect(Cache::has('master:customers:options'))->toBeTrue(); $service->update($customer, ['name' => 'Updated']); expect(Cache::has('master:customers:options'))->toBeFalse(); }); test('delete invalidates customer cache', function () { $customer = Customer::factory()->create(); $service = app(CustomerService::class); $service->getSelectOptions(); expect(Cache::has('master:customers:options'))->toBeTrue(); $service->delete($customer); expect(Cache::has('master:customers:options'))->toBeFalse(); }); }); // ─── Cache Key Isolation ─────────────────────────────────── describe('Cache Key Isolation', function () { test('different services use different cache keys', function () { Category::factory()->count(2)->create(); Supplier::factory()->count(3)->create(); app(CategoryService::class)->getSelectOptions(); app(SupplierService::class)->getSelectOptions(); expect(Cache::has('master:categories:options'))->toBeTrue(); expect(Cache::has('master:suppliers:options'))->toBeTrue(); Cache::forget('master:categories:options'); expect(Cache::has('master:categories:options'))->toBeFalse(); expect(Cache::has('master:suppliers:options'))->toBeTrue(); }); });