Langsung ke konten

06. Menghapus Chirp

Terkadang, mengedit saja tidak cukup untuk memperbaiki sebuah pesan, jadi mari kita beri kemampuan kepada pengguna untuk menghapus Chirp mereka.

Semoga Anda sudah mulai terbiasa dengan alur kerjanya sekarang. Kami rasa Anda akan terkesan betapa cepatnya kita bisa menambahkan fitur ini.

Memperbarui komponen

Untuk memulai, mari perbarui komponen Livewire chirp.list kita agar memiliki tombol hapus dan tambahkan aksi untuk menghapus Chirp saat tombol tersebut diklik:

resources/views/livewire/chirps/list.blade.php
<?php
 ...
 
use App\Models\Chirp;
use Illuminate\Database\Eloquent\Collection;
use Livewire\Attributes\On;
use Livewire\Volt\Component;
 
new class extends Component
{
 ...
public Collection $chirps;
 
public ?Chirp $editing = null;
 
public function mount(): void
{
$this->getChirps();
}
 
#[On('chirp-created')]
public function getChirps(): void
{
$this->chirps = Chirp::with('user')
->latest()
->get();
}
 
public function edit(Chirp $chirp): void
{
$this->editing = $chirp;
 
$this->getChirps();
}
 
#[On('chirp-edit-canceled')]
#[On('chirp-updated')]
public function disableEditing(): void
{
$this->editing = null;
 
$this->getChirps();
}
+ 
+ public function delete(Chirp $chirp): void
+ {
+ $this->authorize('delete', $chirp);
+ 
+ $chirp->delete();
+ 
+ $this->getChirps();
+ }
}; ?>
 
<div class="mt-6 bg-white shadow-sm rounded-lg divide-y">
@foreach ($chirps as $chirp)
<div class="p-6 flex space-x-2" wire:key="{{ $chirp->id }}">
<svg xmlns="http://www.w3.org/2000/svg" class="h-6 w-6 text-gray-600 -scale-x-100" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2">
<path stroke-linecap="round" stroke-linejoin="round" d="M8 12h.01M12 12h.01M16 12h.01M21 12c0 4.418-4.03 8-9 8a9.863 9.863 0 01-4.255-.949L3 20l1.395-3.72C3.512 15.042 3 13.574 3 12c0-4.418 4.03-8 9-8s9 3.582 9 8z" />
</svg>
<div class="flex-1">
<div class="flex justify-between items-center">
<div>
<span class="text-gray-800">{{ $chirp->user->name }}</span>
<small class="ml-2 text-sm text-gray-600">{{ $chirp->created_at->format('j M Y, g:i a') }}</small>
@unless ($chirp->created_at->eq($chirp->updated_at))
<small class="text-sm text-gray-600"> &middot; {{ __('edited') }}</small>
@endunless
</div>
@if ($chirp->user->is(auth()->user()))
<x-dropdown>
<x-slot name="trigger">
<button>
<svg xmlns="http://www.w3.org/2000/svg" class="h-4 w-4 text-gray-400" viewBox="0 0 20 20" fill="currentColor">
<path d="M6 10a2 2 0 11-4 0 2 2 0 014 0zM12 10a2 2 0 11-4 0 2 2 0 014 0zM16 12a2 2 0 100-4 2 2 0 000 4z" />
</svg>
</button>
</x-slot>
<x-slot name="content">
<x-dropdown-link wire:click="edit({{ $chirp->id }})">
{{ __('Edit') }}
</x-dropdown-link>
+ <x-dropdown-link wire:click="delete({{ $chirp->id }})" wire:confirm="Are you sure to delete this chirp?">
+ {{ __('Delete') }}
+ </x-dropdown-link>
</x-slot>
</x-dropdown>
@endif
</div>
<p class="mt-4 text-lg text-gray-900">{{ $chirp->message }}</p>
@if ($chirp->is($editing))
<livewire:chirps.edit :chirp="$chirp" :key="$chirp->id" />
@else
<p class="mt-4 text-lg text-gray-900">{{ $chirp->message }}</p>
@endif
</div>
</div>
@endforeach
</div>
resources/views/livewire/chirps/list.blade.php
<?php
 ...
use App\Models\Chirp;
use function Livewire\Volt\{on, state};
 
$getChirps = fn () => $this->chirps = Chirp::with('user')->latest()->get();
 
$disableEditing = function () {
$this->editing = null;
 
return $this->getChirps();
};
 
state(['chirps' => $getChirps, 'editing' => null]);
 
on([
'chirp-created' => $getChirps,
'chirp-updated' => $disableEditing,
'chirp-edit-canceled' => $disableEditing,
]);
 
$edit = function (Chirp $chirp) {
$this->editing = $chirp;
 
$this->getChirps();
};
+ 
+$delete = function (Chirp $chirp) {
+ $this->authorize('delete', $chirp);
+ 
+ $chirp->delete();
+ 
+ $this->getChirps();
+};
 
?>
 
<div class="mt-6 bg-white shadow-sm rounded-lg divide-y">
@foreach ($chirps as $chirp)
<div class="p-6 flex space-x-2" wire:key="{{ $chirp->id }}">
<svg xmlns="http://www.w3.org/2000/svg" class="h-6 w-6 text-gray-600 -scale-x-100" fill="none" viewBox="0 0 24 24" stroke="currentColor" stroke-width="2">
<path stroke-linecap="round" stroke-linejoin="round" d="M8 12h.01M12 12h.01M16 12h.01M21 12c0 4.418-4.03 8-9 8a9.863 9.863 0 01-4.255-.949L3 20l1.395-3.72C3.512 15.042 3 13.574 3 12c0-4.418 4.03-8 9-8s9 3.582 9 8z" />
</svg>
<div class="flex-1">
<div class="flex justify-between items-center">
<div>
<span class="text-gray-800">{{ $chirp->user->name }}</span>
<small class="ml-2 text-sm text-gray-600">{{ $chirp->created_at->format('j M Y, g:i a') }}</small>
@unless ($chirp->created_at->eq($chirp->updated_at))
<small class="text-sm text-gray-600"> &middot; {{ __('edited') }}</small>
@endunless
</div>
@if ($chirp->user->is(auth()->user()))
<x-dropdown>
<x-slot name="trigger">
<button>
<svg xmlns="http://www.w3.org/2000/svg" class="h-4 w-4 text-gray-400" viewBox="0 0 20 20" fill="currentColor">
<path d="M6 10a2 2 0 11-4 0 2 2 0 014 0zM12 10a2 2 0 11-4 0 2 2 0 014 0zM16 12a2 2 0 100-4 2 2 0 000 4z" />
</svg>
</button>
</x-slot>
<x-slot name="content">
<x-dropdown-link wire:click="edit({{ $chirp->id }})">
{{ __('Edit') }}
</x-dropdown-link>
+ <x-dropdown-link wire:click="delete({{ $chirp->id }})" wire:confirm="Are you sure to delete this chirp?">
+ {{ __('Delete') }}
+ </x-dropdown-link>
</x-slot>
</x-dropdown>
@endif
</div>
<p class="mt-4 text-lg text-gray-900">{{ $chirp->message }}</p>
@if ($chirp->is($editing))
<livewire:chirps.edit :chirp="$chirp" :key="$chirp->id" />
@else
<p class="mt-4 text-lg text-gray-900">{{ $chirp->message }}</p>
@endif
</div>
</div>
@endforeach
</div>

Otorisasi

Sama seperti saat mengedit, kita hanya ingin penulis Chirp yang dapat menghapus Chirp mereka sendiri, jadi mari perbarui metode delete di kelas ChirpPolicy kita:

app/Policies/ChirpPolicy.php
<?php
 ...
namespace App\Policies;
 
use App\Models\Chirp;
use App\Models\User;
use Illuminate\Auth\Access\HandlesAuthorization;
 
class ChirpPolicy
{
 ...
use HandlesAuthorization;
 
/**
* Tentukan apakah pengguna dapat melihat model apa saja.
*/
public function viewAny(User $user): bool
{
//
}
 
/**
* Tentukan apakah pengguna dapat melihat model yang ditentukan.
*/
public function view(User $user, Chirp $chirp): bool
{
//
}
 
/**
* Tentukan apakah pengguna dapat membuat model.
*/
public function create(User $user): bool
{
//
}
 
/**
* Menentukan apakah pengguna dapat memperbarui model.
*/
public function update(User $user, Chirp $chirp): bool
{
return $chirp->user()->is($user);
}
 
/**
* Menentukan apakah pengguna dapat menghapus model.
*/
public function delete(User $user, Chirp $chirp): bool
{
- //
+ return $this->update($user, $chirp);
}
 ...
/**
* Menentukan apakah pengguna dapat merestorasi model.
*/
public function restore(User $user, Chirp $chirp): bool
{
//
}
 
/**
* Menentukan apakah pengguna dapat menghapus model secara permanen.
*/
public function forceDelete(User $user, Chirp $chirp): bool
{
//
}
 
}

Alih-alih mengulang logika dari metode update, kita dapat mendefinisikan logika yang sama dengan memanggil metode update dari dalam metode delete. Siapa pun yang berwenang untuk memperbarui Chirp sekarang juga akan berwenang untuk menghapusnya.

Coba sekarang

Jika Anda pernah mengirim Chirp yang tidak memuaskan, cobalah menghapusnya!

Menghapus sebuah chirp

Lanjutkan ke notifikasi & event...