find files older than X days in bash and delete
Categories:
Efficiently Find and Delete Old Files in Bash

Learn how to use the find command in Bash to locate and remove files older than a specified number of days, ensuring your systems stay clean and optimized.
Managing disk space is a crucial aspect of system administration and development. Over time, log files, temporary data, backups, and other generated content can accumulate, consuming valuable storage and potentially impacting system performance. The find command in Bash is an incredibly powerful utility for navigating the file system and performing actions based on various criteria, including file age. This article will guide you through using find to identify and safely delete files older than a specified duration.
Understanding the find Command for Age-Based Searches
The find command is versatile, but for age-based searches, we primarily focus on the -mtime and -atime options. These options allow you to specify a time duration relative to the file's last modification or access time, respectively. The number following these options represents the number of 24-hour periods.
-mtime +N: Finds files whose data was last modified more than N 24-hour periods ago.-atime +N: Finds files that were last accessed more than N 24-hour periods ago.
It's generally safer to use -mtime for deletion tasks, as access times (-atime) can be updated by simple read operations, which might not reflect the file's true 'staleness'. Modification time (-mtime) is a more reliable indicator of when a file became 'old' or irrelevant.
find /path/to/directory -mtime +30 -print
Basic find command to list files older than 30 days.
Safely Deleting Found Files
Before you delete any files, it's paramount to test your find command to ensure it targets exactly what you intend. A common mistake is to immediately pipe find's output to rm without verification, which can lead to irreversible data loss. Always start by listing the files, then add the deletion action.
There are several ways to delete files found by find:
- Using
-delete(GNUfindextension): This is the most efficient and often preferred method for GNUfindas it avoids issues with large numbers of files or filenames containing special characters. - Using
-exec rm {} \;: This method executesrmfor each found file. It's more portable across different Unix-like systems but can be slower for many files. - Using
-exec rm {} +(GNUfindextension): Similar toxargs, this passes multiple filenames to a singlermcommand, making it more efficient than\;for many files.
We will focus on the -delete and -exec methods for their robustness.
flowchart TD
A[Start] --> B{"Define Target Directory & Age (N days)"}
B --> C{"Construct `find` Command (e.g., -mtime +N)"}
C --> D{Test Run: `find ... -print`}
D --"Review Output"--> E{Output Correct?}
E -- No --> C
E -- Yes --> F{"Choose Deletion Method (-delete or -exec)"}
F --> G{Execute Deletion Command}
G --> H[End]Workflow for safely finding and deleting old files.
find command before adding any deletion action. A misplaced . or / could lead to unintended data loss. When in doubt, use -print first!Practical Examples for Deletion
Let's look at some practical examples for deleting files and directories.
# 1. Find and delete files older than 60 days in a specific directory
# (using -delete for GNU find)
find /var/log/old_logs -type f -mtime +60 -delete
# 2. Find and delete empty directories older than 90 days
# (using -delete for GNU find)
find /tmp/backups -type d -empty -mtime +90 -delete
# 3. Find and delete files older than 30 days, excluding certain file types
# (using -exec rm {} \; for portability)
find /home/user/downloads -type f -mtime +30 \! -name "*.important" -exec rm {} \;
Examples of find commands for various deletion scenarios.
find twice: once for files, then once for directories. This ensures files are deleted before their parent directories become empty and are subsequently deleted.Automating Deletion with Cron Jobs
For routine cleanup, you can automate these commands using cron jobs. A cron job schedules commands to run at specified intervals.
To add a cron job, open your crontab for editing:
crontab -e
Then, add a line specifying the schedule and the command. For example, to run a cleanup script every day at 2:00 AM:
0 2 * * * /path/to/your/cleanup_script.sh > /dev/null 2>&1
Ensure your cleanup script has execute permissions (chmod +x /path/to/your/cleanup_script.sh). It's also good practice to log the output of cron jobs for auditing and debugging, rather than redirecting to /dev/null.
# Example cleanup_script.sh
#!/bin/bash
LOG_FILE="/var/log/cleanup_$(date +%Y%m%d).log"
TARGET_DIR="/var/log/application"
DAYS_OLD="+90"
echo "Cleanup started at $(date)" >> "$LOG_FILE"
find "$TARGET_DIR" -type f -mtime "$DAYS_OLD" -print -delete >> "$LOG_FILE" 2>&1
find "$TARGET_DIR" -type d -empty -mtime "$DAYS_OLD" -print -delete >> "$LOG_FILE" 2>&1
echo "Cleanup finished at $(date)" >> "$LOG_FILE"
Example of a simple cleanup script to be used with cron.