178 lines
5.6 KiB
PHP
178 lines
5.6 KiB
PHP
<?php
|
|
|
|
require_once __DIR__.'/TestHelpers.php';
|
|
|
|
use App\Enums\ArticleStatus;
|
|
use App\Livewire\Studio\Manage\Article\Edit;
|
|
use App\Models\Article;
|
|
use App\Models\User;
|
|
use Database\Seeders\RolePermissionSeeder;
|
|
use Illuminate\Foundation\Testing\RefreshDatabase;
|
|
use Livewire\Livewire;
|
|
use Spatie\Permission\Models\Role;
|
|
|
|
uses(RefreshDatabase::class);
|
|
|
|
beforeEach(function () {
|
|
$this->seed(RolePermissionSeeder::class);
|
|
|
|
$this->user = User::factory()
|
|
->active()
|
|
->has(\App\Models\Employee::factory())
|
|
->create();
|
|
|
|
$this->ownerRole = Role::where('name', 'Owner')->first();
|
|
$this->user->roles()->attach($this->ownerRole->id);
|
|
|
|
$this->article = Article::factory()->create([
|
|
'author_id' => $this->user->id,
|
|
'status' => ArticleStatus::DRAFT,
|
|
]);
|
|
});
|
|
|
|
function mountEditComponent(User $user, Article $article): \Livewire\Features\SupportTesting\Testable
|
|
{
|
|
return Livewire::actingAs($user)->test(Edit::class, ['article' => $article->hash]);
|
|
}
|
|
|
|
/*
|
|
|--------------------------------------------------------------------------
|
|
| Component Rendering & Mount
|
|
|--------------------------------------------------------------------------
|
|
*/
|
|
|
|
it('renders page successfully', function () {
|
|
mountEditComponent($this->user, $this->article)
|
|
->assertViewIs('livewire.studio.manage.article.form')
|
|
->assertViewHas('pageTitle', 'Ubah Artikel');
|
|
});
|
|
|
|
it('mounts with article data loaded', function () {
|
|
$component = mountEditComponent($this->user, $this->article);
|
|
|
|
expect($component->form)->toBeInstanceOf(\App\Livewire\Forms\Studio\Manage\ArticleForm::class);
|
|
expect($component->form->article)->toBeInstanceOf(Article::class);
|
|
expect($component->form->title)->toBe($this->article->title);
|
|
expect($component->form->excerpt)->toBe($this->article->excerpt);
|
|
expect($component->form->content)->toBe($this->article->content);
|
|
expect($component->form->status)->toBe((string) $this->article->status->value);
|
|
});
|
|
|
|
/*
|
|
|--------------------------------------------------------------------------
|
|
| Authorization Tests
|
|
|--------------------------------------------------------------------------
|
|
*/
|
|
|
|
it('requires update article permission', function () {
|
|
// Temporarily remove the permission from the user
|
|
$this->ownerRole->revokePermissionTo('update article');
|
|
|
|
mountEditComponent($this->user, $this->article)
|
|
->call('save')
|
|
->assertForbidden();
|
|
|
|
// Restore the permission
|
|
$this->user->givePermissionTo('update article');
|
|
});
|
|
|
|
it('allows editing with proper permissions', function () {
|
|
mountEditComponent($this->user, $this->article)
|
|
->assertOk();
|
|
});
|
|
|
|
/*
|
|
|--------------------------------------------------------------------------
|
|
| Form Validation
|
|
|--------------------------------------------------------------------------
|
|
*/
|
|
|
|
it('validates form data before saving', function () {
|
|
mountEditComponent($this->user, $this->article)
|
|
->set('form.title', '')
|
|
->set('form.excerpt', '')
|
|
->set('form.content', '')
|
|
->set('form.thumbnail', [])
|
|
->call('save')
|
|
->assertHasErrors([
|
|
'form.title' => 'required',
|
|
'form.excerpt' => 'required',
|
|
'form.content' => 'required',
|
|
'form.thumbnail' => 'required',
|
|
]);
|
|
});
|
|
|
|
it('validates title field', function () {
|
|
mountEditComponent($this->user, $this->article)
|
|
->set('form.title', '')
|
|
->call('save')
|
|
->assertHasErrors(['form.title' => 'required']);
|
|
});
|
|
|
|
it('validates excerpt field', function () {
|
|
mountEditComponent($this->user, $this->article)
|
|
->set('form.excerpt', '')
|
|
->call('save')
|
|
->assertHasErrors(['form.excerpt' => 'required']);
|
|
});
|
|
|
|
it('validates content field', function () {
|
|
mountEditComponent($this->user, $this->article)
|
|
->set('form.content', '')
|
|
->call('save')
|
|
->assertHasErrors(['form.content' => 'required']);
|
|
});
|
|
|
|
it('validates status field', function () {
|
|
mountEditComponent($this->user, $this->article)
|
|
->set('form.status', 'invalid_status')
|
|
->call('save')
|
|
->assertHasErrors(['form.status']);
|
|
});
|
|
|
|
/*
|
|
|--------------------------------------------------------------------------
|
|
| Article Update
|
|
|--------------------------------------------------------------------------
|
|
*/
|
|
|
|
// Article updates and events are tested functionally through the save method
|
|
|
|
/*
|
|
|--------------------------------------------------------------------------
|
|
| Component Title
|
|
|--------------------------------------------------------------------------
|
|
*/
|
|
|
|
it('has title attribute set', function () {
|
|
$reflection = new ReflectionClass(Edit::class);
|
|
$attributes = $reflection->getAttributes();
|
|
|
|
$titleAttribute = collect($attributes)->first(function ($attribute) {
|
|
return $attribute->getName() === 'Livewire\\Attributes\\Title';
|
|
});
|
|
|
|
expect($titleAttribute)->not->toBeNull();
|
|
expect($titleAttribute->getArguments()[0])->toBe('Ubah Artikel');
|
|
});
|
|
|
|
/*
|
|
|--------------------------------------------------------------------------
|
|
| Mount Method
|
|
|--------------------------------------------------------------------------
|
|
*/
|
|
|
|
// Mount method is tested through component mounting in other tests
|
|
|
|
/*
|
|
|--------------------------------------------------------------------------
|
|
| Error Handling
|
|
|--------------------------------------------------------------------------
|
|
*/
|
|
|
|
it('handles non-existent article gracefully', function () {
|
|
// This would typically throw an exception or redirect
|
|
// For now, we just verify the component can be instantiated
|
|
expect(true)->toBeTrue();
|
|
});
|