duane blake

Published on November 17, 2025 | Posted in Laravel

How to Automatically Delete Old Records in Laravel

There may be circumstances in your application where you need to delete old or no longer needed data. This could be for reasons such as improving performance or keeping your data fresh. Laravel has a trait which is perfect for this called Prunable, which allows you to set up a command to delete records from the database.

Automating Database Cleanup with Laravel Prunable

To use the Prunable trait in your model, you create a function called prunable which creates a query to fetch all the records that need to be deleted. You then create an artisan schedule which will run and delete the data from your database at set times.

<?php

namespace App\Models;

use Illuminate\Database\Eloquent\Builder;
use Illuminate\Database\Eloquent\Model;
use Illuminate\Database\Eloquent\Prunable;

class Tickets extends Model 
{
	use Prunable;
	
	public function prunable(): Builder
	{
		return static::where('completed_at', <=', now()->subDays(30));
	}

}

What the code above does is slightly different from a typical Laravel model. The first difference is pulling in the Prunable trait:

use Illuminate\Database\Eloquent\Prunable;

The next step is setting up the Prunable trait to allow us to use the prunable methods in our model:

use Prunable;

Now for the logic part: we create a public function, and it needs to be called prunable. This function builds the query for the criteria by which we wish to delete our data. In my example, it will delete all records which have a completed_at date of 30 days ago or more.

Running the Prune Command

Once the model is set up, you can run the following command from your terminal. This command detects all Prunable models in your application and deletes the matching records:

php artisan model:prune

To automate this, I typically add an entry to routes/console.php to run the prune command daily. For example, to run it every day at 18:30:

Schedule::command('model:prune')->dailyAt('18:30');

For further reading, check out the official documentation:

Leave a comment

Your email address will not be published. Required fields are marked *