Tutorial

How To Delete Database Records in Laravel Eloquent

PHPPHP FrameworksLaravel
Part of the Series: A Practical Introduction to Laravel Eloquent ORM

Eloquent is an object relational mapper (ORM) that is included by default within the Laravel framework. In this project-based series, you’ll learn how to make database queries and how to work with relationships in Laravel Eloquent. To follow along with the examples demonstrated throughout the series, you’ll improve a demo application with new models and relationships. Visit the series introduction page for detailed instructions on how to download and set up the project.

In Eloquent, you can delete database records conveniently with the delete method from the parent Model class. The link:delete command, already implemented within the base version of the demo application, deletes links based on a valid link id. The application is still missing a command to delete lists.

In the last part of this series, you’ll create a new command to delete lists. For simplicity, any links associated with the list to be deleted will be reassigned to the default link list.

From your terminal, run the following to bootstrap a new Artisan command:

  • docker-compose exec app php artisan make:command ListDelete

This will create a new ListDelete.php file located at app/Console/Commands. Open the file in your code editor of choice:

app/Console/Commands/ListDelete.php

You’ll update this code to handle deleting a link list provided its unique slug, which is a URL-friendly name used to identify each list.

This is what your handle() method needs to do:

  • Obtain a slug provided by the user and check for the existence of a list with a matching slug in the database.
  • If a valid list cannot be found, show an error message and exit.
  • If a valid list is found, prompt the user to confirm.
  • Reassign to the default list any links associated with the list that will be deleted.
  • Delete the list from the database.

If you’ve been following along with all parts of the series so far, you have implemented similar code before when creating the LinkUpdate command. The main difference now is that you won’t need to prompt the user for additional info, and before running the delete() method you’ll need to run a mass update to change associated links to a different list.

Replace the boilerplate code in your ListDelete.php file with the following:

app/Console/Commands/ListDelete.php
<?php

namespace App\Console\Commands;

use App\Models\Link;
use App\Models\LinkList;
use Illuminate\Console\Command;

class ListDelete extends Command
{
    /**
     * The name and signature of the console command.
     *
     * @var string
     */
    protected $signature = 'list:delete {list_slug}';

    /**
     * The console command description.
     *
     * @var string
     */
    protected $description = 'Delete Lists';

    /**
     * Create a new command instance.
     *
     * @return void
     */
    public function __construct()
    {
        parent::__construct();
    }

    /**
     * Execute the console command.
     *
     * @return int
     */
    public function handle()
    {
        $list_slug = $this->argument('list_slug');
        $list = LinkList::firstWhere('slug', $list_slug);

        if ($list === null) {
            $this->error("Invalid or non-existent List.");
            return 1;
        }

        if ($this->confirm("Confirm deleting the list '$list->title'? Links will be reassigned to the default list.")) {
            $default_list = LinkList::firstWhere('slug', 'default');
            if (!$default_list) {
                $default_list = new LinkList();
                $default_list->title = 'default';
                $default_list->slug = 'default';
                $default_list->save();
            }

            $this->info("Reassigning links to default list...");

            Link::where('link_list_id', $list->id)->update(['link_list_id' => $default_list->id]);

            $list->delete();
            $this->info("List Deleted.");
        }

        return 0;
    }
}

Save the file.

In the previous code, the handle() method starts by trying to locate a link list based on the provided slug. If a valid list can’t be found, the application exits in error. When a valid list is found, the confirm() method is called to ask the user for confirmation.

When confirmed, the application will locate the default list or create a new one if necessary, assigning it to the $default_list variable.

Next, it will locate and update all links that are associated with the list that is about to be deleted. The chained call to update() will update the referenced list ID on all links that match the query, using the condition defined within the previous where() call. This line is highlighted for your reference.

Finally, the list is deleted with the delete() method, also highlighted. This method is available to all Eloquent models through the parent Model class.

To delete a list, first run link:show to obtain all links currently in the database:

  • docker-compose exec app php artisan link:show
Output
+----+-------------------------------------------------+--------------+----------------------------------+ | id | url | list | description | +----+-------------------------------------------------+--------------+----------------------------------+ | 1 | https://digitalocean.com/community | digitalocean | DO Community | | 2 | https://digitalocean.com/community/tags/laravel | digitalocean | Laravel Tutorias at DigitalOcean | | 3 | https://digitalocean.com/community/tags/php | digitalocean | PHP Tutorials at DigitalOcean | | 4 | https://twitter.com/digitalocean | social | Twitter | | 5 | https://dev.to/digitalocean | social | DEV.to | | 6 | https://laravel.com/docs/8.x/eloquent | default | Laravel Eloquent Docs | +----+-------------------------------------------------+--------------+----------------------------------+

To delete the digitalocean list and revert those links back to the default list, run:

  • docker-compose exec app php artisan list:delete digitalocean

Confirm the deletion by typing y and hitting ENTER.

Output
Confirm deleting the list 'digitalocean'? Links will be reassigned to the default list. (yes/no) [no]: > y Reassigning links to default list... List Deleted.

If you run the link:show() command again, you’ll see the updated information:

Output
+----+-------------------------------------------------+---------+----------------------------------+ | id | url | list | description | +----+-------------------------------------------------+---------+----------------------------------+ | 1 | https://digitalocean.com/community | default | DO Community | | 2 | https://digitalocean.com/community/tags/laravel | default | Laravel Tutorias at DigitalOcean | | 3 | https://digitalocean.com/community/tags/php | default | PHP Tutorials at DigitalOcean | | 4 | https://twitter.com/erikaheidi | social | Twitter | | 5 | https://dev.to/erikaheidi | social | DEV.to | | 6 | https://laravel.com/docs/8.x/eloquent | default | Laravel Eloquent Docs | +----+-------------------------------------------------+---------+----------------------------------+

The application now has a dedicated command to delete lists of links.

Creative Commons License