Skip to content

Instantly share code, notes, and snippets.

@cdosborn
Last active May 14, 2022 19:58
Show Gist options
  • Save cdosborn/45bf23649a0d84da4cce to your computer and use it in GitHub Desktop.
Save cdosborn/45bf23649a0d84da4cce to your computer and use it in GitHub Desktop.
Truncate log files such that the end of the file is preserved
#! /bin/bash
# Truncate to last 100 lines of each file.
# logtrunc file1 file2 file3
# Truncate to last 50 lines of each file.
# logtrunc -n 50 file1 file2 file3
# WARNING * WARNING * WARNING
# This script is not highly tested
# WARNING * WARNING * WARNING
# Set a default for the number of lines printed
NUMLINES=100
while `true`; do
# Enable interactive mode
if [[ $1 =~ ^(-i|--interactive)$ ]]; then
INTERACTIVE=1;
# Allow -n 100 for example
elif [[ $1 =~ ^-n$ ]]; then
NUMLINES=$2;
shift;
# Allow -100 for example
elif [[ $1 =~ ^-[0-9]+$ ]]; then
NUMLINES=${1##-};
# Read -h or --help and then exit
elif [[ $1 =~ ^(-h|--help)$ ]]; then
echo "logtrunc [[ OPTIONS ]] <files>";
echo " -n <number> Trim to the last n lines";
echo " -<number>";
echo " ";
echo " -d, --dry-run Only print don't truncate";
echo " -i, --interactive Ask before trunacting";
echo " -h, --help How meta";
echo " ";
echo "Version: 0.1.0"
echo "Author: cdosborn"
exit 0;
elif [[ $1 =~ ^(-d|--dry-run)$ ]]; then
DRYRUN=1;
# We didn't parse an option
else
break;
fi
# Pop off last option
shift;
done;
if [[ $INTERACTIVE && $DRYRUN ]]; then
echo "** Error incomatible options: interactive, dry run";
exit 1;
fi;
FILES=$@;
# Truncate a file to its last n lines;
# trunc n file
function trunc {
tail -n "$1" < "$2" > "$2.bak";
mv "$2.bak" "$2";
}
for file in $FILES; do
# Silently skip directories
if [[ -d "$file" ]]; then
continue;
fi;
# Continue if not a regular file
if [[ ! -f "$file" ]]; then
echo "Cannot find file \"$file\"";
continue;
fi;
LENGTH="$(wc -l < "$file" 2>&-)";
# File needs to be truncated
if [[ "$LENGTH" -gt "$NUMLINES" ]]; then
if [[ $DRYRUN ]]; then
echo "(dry run) Trimming $file";
continue;
fi;
if [[ ! $INTERACTIVE ]]; then
echo "Trimming $file";
trunc $NUMLINES $file
continue;
fi;
# Prompt to truncate file
read -ep "Trim $file? (y/N/q) " answer;
if [[ "$answer" =~ ^(q|Q)$ ]]; then
echo "Quitting.";
exit 0;
elif [[ "$answer" =~ ^(y|Y)$ ]]; then
echo "Trimmming $file"
trunc $NUMLINES $file
else
echo "Skipping $file"
fi
else
echo "Skipping $file of length $LENGTH"
fi
done;
@amercer1
Copy link

amercer1 commented Jan 5, 2016

+1

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment