38 Commits

Author SHA1 Message Date
Jordan 5739796801 Update README.md v2.0.2 2023-11-13 19:16:40 +01:00
Jordan e6d63a99c9 Update pvekclean.sh v2.0.2 2023-11-13 19:03:13 +01:00
Jordan e7853e3741 Update pvekclean.sh v2.0.2 2023-11-13 13:29:42 +01:00
Jordan 0a4fcb889d Update README.md v2.0.2 2023-11-13 13:18:22 +01:00
Jordan d7a2c688b0 Example v2.0.2 2023-11-13 13:16:48 +01:00
Jordan 3f817fc7d2 Update README.md v2.0.2 2023-11-13 04:09:25 +01:00
Jordan cc58a1b77f Update version.txt v2.0.2 2023-11-13 03:30:07 +01:00
Jordan 9e413967ce Update pvekclean.sh v2.0.2 2023-11-13 03:28:48 +01:00
Jordan ea19f62165 Update pvekclean.sh v2.0.1 2023-11-13 03:09:05 +01:00
Jordan 6401ccd2ba Update pvekclean.sh v2.0.1 2023-11-13 02:19:39 +01:00
Jordan 6ce2bb2f3e Update version.txt 2023-11-13 01:53:30 +01:00
Jordan bd991921dc Update pvekclean.sh v2.0.1 2023-11-13 01:52:56 +01:00
Jordan a6f37f50a3 Update pvekclean.sh 2023-11-13 01:43:40 +01:00
Jordan 8b7b7ce603 Update README.md 2023-11-12 23:34:49 +01:00
Jordan c910d0a40d Update README.md 2023-11-12 23:16:43 +01:00
Jordan d7da5f57e3 Example of v2.0 2023-11-12 23:15:03 +01:00
Jordan 5c432a0002 Banner of PVE Kernel Cleaner 2023-11-12 23:14:37 +01:00
Jordan d0dc6e5933 Example of v1.2 2023-11-12 23:14:10 +01:00
Jordan 7550785c9d Delete assets/example1.jpg 2023-11-12 23:13:51 +01:00
Jordan eca4370c60 Delete assets/example.jpg 2023-11-12 23:13:40 +01:00
Jordan a27b1f84fa Example of PVE Kernel Cleaner 2023-11-12 23:12:05 +01:00
Jordan e5ec7b37a3 Example of PVE Kernel Cleaner 2023-11-12 23:10:15 +01:00
Jordan 5dc03d7c67 Delete assets/example.jpg 2023-11-12 23:09:53 +01:00
Jordan 9de178bbd9 Example of PVE Kernel Cleaner 2023-11-12 23:07:37 +01:00
Jordan ecedcad905 Delete assets/example.jpg 2023-11-12 23:07:15 +01:00
Jordan 292add9b07 Example use of PVE Kernel Cleaner 2023-11-12 23:02:32 +01:00
Jordan a12ab207ee Create README.md 2023-11-12 23:01:53 +01:00
Jordan 65c6bc2641 Update README.md 2023-11-12 22:48:57 +01:00
Jordan 8f5af65eba Update README.md 2023-11-12 22:47:51 +01:00
Jordan ebbe8b3fa4 Update README.md 2023-11-12 22:41:11 +01:00
Jordan 207547b3ab Update README.md 2023-11-12 20:54:24 +01:00
Jordan 3110d396be Update README.md 2023-11-12 20:03:49 +01:00
Jordan c60c8bae59 Update pvekclean.sh 2023-11-12 20:00:54 +01:00
Jordan efa86a4734 Update pvekclean.sh 2023-11-12 19:47:31 +01:00
Jordan 695bb3c4cf Update pvekclean.sh 2023-11-12 19:37:38 +01:00
Jordan ea222ba5ad Update version.txt 2023-11-12 17:14:39 +01:00
Jordan 3b91a45492 Update README.md 2023-11-12 17:14:11 +01:00
Jordan f1174b1381 Update pvekclean.sh v2.0 2023-11-12 17:10:22 +01:00
8 changed files with 160 additions and 77 deletions
+54 -16
View File
@@ -1,8 +1,8 @@
![PVEKCLEAN Logo](https://jordanhillis.com/images/github/pvekclean/pvekclean_banner.png)
![PVEKCLEAN Logo](assets/banner.png)
Easily remove old/unused PVE kernels on your Proxmox VE system
[![Version](https://img.shields.io/badge/Version-v1.3-brightgreen)](https://github.com/jordanhillis/pvekclean)
[![Version](https://img.shields.io/badge/Version-v2.0.2-brightgreen)](https://github.com/jordanhillis/pvekclean)
[![License: MIT](https://img.shields.io/badge/License-MIT-brightgreen.svg)](https://opensource.org/licenses/MIT)
![Updated](https://img.shields.io/github/last-commit/jordanhillis/pvekclean)
![Proxmox](https://img.shields.io/badge/-Proxmox-orange)
@@ -14,7 +14,7 @@ PVE Kernel Cleaner is a program to compliment Proxmox Virtual Environment which
## Example Usage
![PVEKCLEAN Example](https://jordanhillis.com/images/github/pvekclean/pvekclean_example3.png)
![PVEKCLEAN Example](assets/example-2.0.2.png)
## Features
@@ -29,36 +29,54 @@ PVE Kernel Cleaner is a program to compliment Proxmox Virtual Environment which
## Latest Version
* v1.3
* v2.0.2
## Prerequisites
Before using this program you will need to have the following packages installed.
* cron
* curl
* git
To install all required packages enter the following command.
##### Debian:
```
sudo apt-get install cron
sudo apt-get install cron curl git
```
## Installing
To install PVE Kernel Cleaner please enter the following commands
You can install PVE Kernel Cleaner using either Git or Curl. Choose the method that suits you best:
```
### Installation via Git
1. Open your terminal.
2. Enter the following commands one by one to install PVE Kernel Cleaner:
```bash
git clone https://github.com/jordanhillis/pvekclean.git
cd pvekclean
chmod +x pvekclean.sh
./pvekclean.sh
```
### Installation via Curl
1. Open your terminal.
2. Use the following command to install PVE Kernel Cleaner:
```bash
curl -o pvekclean.sh https://raw.githubusercontent.com/jordanhillis/pvekclean/master/pvekclean.sh
chmod +x pvekclean.sh
./pvekclean.sh
```
## Updating
To update PVE Kernel Cleaner please run the same commands as described in the "Installing" section.
PVE Kernel Cleaner checks for updates automatically when you run it. If an update is available, you'll be notified within the program. Simply follow the on-screen instructions to install the update, and you're all set with the latest version!
## Usage
@@ -71,31 +89,51 @@ Example of usage:
-f, --force Force the removal of old PVE kernels without confirm prompts
-rn, --remove-newer Remove kernels that are newer than the currently running kernel
-s, --scheduler Have old PVE kernels removed on a scheduled basis
-v, --version Shows current version of $program_name
-r, --remove Uninstall $program_name from the system
-d, --debug Run the program in debug mode for testing without making system changes
-v, --version Shows current version of pvekclean
-r, --remove Uninstall pvekclean from the system
-i, --install Install pvekclean to the system
-d, --dry-run Run the program in dry run mode for testing without making system changes
```
## Usage Examples:
Here are some common ways to use PVE Kernel Cleaner:
**Remove Old Kernels Non-Interactively:**
* **Remove Old Kernels Non-Interactively:**
```bash
pvekclean -f
```
**Set Number of Kernels to Keep:**
<sub> This command removes old PVE kernels without requiring user confirmation.</sub>
* **Set Number of Kernels to Keep:**
```bash
pvekclean -k 3
```
**Force Remove Old Kernels While Keeping a Certain Number:**
<sub>This command specifies the number of most recent PVE kernels to keep on the system.</sub>
* **Force Remove Old Kernels While Keeping a Certain Number:**
```bash
pvekclean -f -k 3
```
**Remove Newer Kernels and Keep a Specific Number:**
<sub>This command forces the removal of old PVE kernels while retaining a specific number of the most recent ones.</sub>
* **Remove Newer Kernels and Keep a Specific Number:**
```bash
pvekclean -rn -k 2
```
<sub>This command removes newer PVE kernels and keeps a specified number of the most recent ones.</sub>
* **Schedule Regular Kernel Removal:**
```bash
pvekclean -s
```
<sub>This command sets up PVE Kernel Cleaner to remove old PVE kernels on a scheduled basis. You can configure the schedule according to your needs.</sub>
* **Perform a Dry Run without Making Changes:**
```bash
pvekclean -d
```
<sub>This command runs PVE Kernel Cleaner in dry run mode, simulating actions without actually removing any kernels or making changes to your system. It's useful for testing and understanding what the script would do.</sub>
## Developers
+1
View File
@@ -0,0 +1 @@
Asset files here only. Not intended for program use.
BIN
View File
Binary file not shown.

After

Width:  |  Height:  |  Size: 17 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 80 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 77 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 168 KiB

+104 -60
View File
@@ -36,8 +36,8 @@ boot_critical_percent="80"
# To check for updates or not
check_for_updates=true
# Debug mode is for testing without actually removing anything
debug=false
# Dry run mode is for testing without actually removing anything
dry_run=false
# Current kernel
current_kernel=$(uname -r)
@@ -46,7 +46,7 @@ current_kernel=$(uname -r)
program_name="pvekclean"
# Version
version="1.3"
version="2.0.2"
# Text Colors
black="\e[38;2;0;0;0m"
@@ -99,26 +99,45 @@ version() {
# Header for PVE Kernel Cleaner
header_info() {
echo -e " ${bg_black}${orange} ${reset}
${bg_black}${orange} █▀▀█ ▀█ █▀ █▀▀ █ █ █▀▀ █▀▀█ █▀▀▄ █▀▀ █ ${reset}
${bg_black}${orange} █ █ █▄█ █▀▀ █▀▄ █▀▀ █▄▄▀ █ █ █▀▀ █ ${reset}
${bg_black}${orange} █▀▀▀ ▀ ▀▀▀ ▀ ▀ ▀▀▀ ▀ ▀▀ ▀ ▀ ▀▀▀ ▀▀▀ ${reset}
${bg_black}${orange} ${reset}
${bg_black}${white} █▀▀ █ █▀▀ █▀▀█ █▀▀▄ █▀▀ █▀▀█ ${reset}
${bg_black}${white} █ █ █▀▀ █▄▄█ █ █ █▀▀ █▄▄▀ ${white}${bold}⎦˚◡˚⎣ v$version ${reset}
${bg_black}${white} ▀▀▀ ▀▀▀ ▀▀▀ ▀ ▀ ▀ ▀ ▀▀▀ ▀ ▀▀ ${reset}
${bg_orange}${black} ${bold}By Jordan Hillis [jordan@hillis.email] ${reset}
echo -e " ${bg_black}${orange} ${reset}
${bg_black}${orange} █▀▀█ ▀█ █▀ █▀▀ █ █ █▀▀ █▀▀█ █▀▀▄ █▀▀ █ ${reset}
${bg_black}${orange} █ █ █▄█ █▀▀ █▀▄ █▀▀ █▄▄▀ █ █ █▀▀ █ ${reset}
${bg_black}${orange} █▀▀▀ ▀ ▀▀▀ ▀ ▀ ▀▀▀ ▀ ▀▀ ▀ ▀ ▀▀▀ ▀▀▀ ${reset}
${bg_black}${orange} ${reset}
${bg_black}${white} █▀▀ █ █▀▀ █▀▀█ █▀▀▄ █▀▀ █▀▀█ ${reset}
${bg_black}${white} █ █ █▀▀ █▄▄█ █ █ █▀▀ █▄▄▀ ${white}${bold}⎦˚◡˚⎣ v$version ${reset}
${bg_black}${white} ▀▀▀ ▀▀▀ ▀▀▀ ▀ ▀ ▀ ▀ ▀▀▀ ▀ ▀▀ ${reset}
${bg_orange}${black} ${bold}By Jordan Hillis [jordan@hillis.email] ${reset}
___________________________________________
"
if [ "$debug" == "true" ]; then
printf " ${bg_black}${orange}${bold} DEBUG MODE IS ${green}ON ${reset}\n\n"
if [ "$dry_run" == "true" ]; then
printf " ${bg_yellow}${black}${bold} DRY RUN MODE IS: ${red}ON ${reset}\n"
printf "${bg_green}${bold}${black} This is what the script would do in regular mode ${reset}\n${bg_green}${bold}${black} (but without making actual changes) ${reset}\n\n"
fi
}
# Function to get drive status based on usage percentage
get_drive_status() {
local usage=$1
# Check if the input is a number
if ! [[ $usage =~ ^[0-9]+$ ]]; then
echo "${bold}N/A${reset}"
else
if (( usage <= 50 )); then
echo "${bold}${green}Healthy${reset}"
elif (( usage > 50 && usage <= 75 )); then
echo "${bold}${orange}Moderate Capacity${reset}"
else
echo "${bold}${red}Critically Full${reset}"
fi
fi
}
# Show current system information
kernel_info() {
# Lastest kernel installed
latest_kernel=$(dpkg --list | awk '/proxmox-kernel-.*-pve/{print $2}' | sed -n 's/proxmox-kernel-//p' | sort -V | tail -n 1 | tr -d '[:space:]')
[ -z "$latest_kernel" ] && latest_kernel="N/A"
# Show operating system used
printf " ${bold}OS:${reset} $(cat /etc/os-release | grep "PRETTY_NAME" | sed 's/PRETTY_NAME=//g' | sed 's/["]//g' | awk '{print $0}')\n"
# Get information about the /boot folder
@@ -131,7 +150,7 @@ kernel_info() {
if [[ "$current_kernel" == *"pve"* ]]; then
# Check if we are running the latest kernel, if not warn
if [[ "$latest_kernel" != *"$current_kernel"* ]]; then
printf " ${bold}Latest Kernel:${reset} $latest_kernel\n"
printf " ${bold}Latest Kernel:${reset} ${latest_kernel}\n"
fi
# Warn them that they aren't on a PVE kernel
else
@@ -165,7 +184,8 @@ show_usage() {
printf " -s, --scheduler Have old PVE kernels removed on a scheduled basis\n"
printf " -v, --version Shows current version of $program_name\n"
printf " -r, --remove Uninstall $program_name from the system\n"
printf " -d, --debug Run the program in debug mode for testing without making system changes\n"
printf " -i, --install Install $program_name to the system\n"
printf " -d, --dry-run Run the program in dry run mode for testing without making system changes\n"
printf "___________________________________________\n\n"
fi
}
@@ -239,6 +259,9 @@ scheduler() {
# Installs PVE Kernel Cleaner for easier access
install_program() {
force_pvekclean_update=false
local tmp_file="/tmp/.pvekclean_install_lock"
local install=false
local ask_interval=3600 # 1 hour in seconds
# If pvekclean exists on the system
if [ -e /usr/local/sbin/$program_name ]; then
# Get current version of pvekclean
@@ -250,29 +273,37 @@ install_program() {
force_pvekclean_update=true
fi
fi
# If pvekclean does not exist on the system or force_purge is enabled
if [ ! -f /usr/local/sbin/$program_name ] || [ $force_pvekclean_update == true ]; then
# Ask user if we can install it to their system
if [ $force_purge == true ]; then
REPLY="n"
else
# Ask if we can install it
printf "${bold}[-]${reset} Can we install PVE Kernel Cleaner to your /usr/local/sbin for easier access [y/N] "
read -n 1 -r
printf "\n"
fi
# User agrees to have it installed
if [[ $REPLY =~ ^[Yy]$ ]]; then
# Copy the script to /usr/local/sbin and set execution permissions
cp $0 /usr/local/sbin/$program_name
chmod +x /usr/local/sbin/$program_name
# Tell user how to use it
printf "${bold}[*]${reset} Installed PVE Kernel Cleaner to /usr/local/sbin/$program_name\n"
printf "${bold}[*]${reset} Run the command \"$program_name\" to begin using this program.\n"
printf "${bold}[-]${reset} Run the command \"$program_name -r\" to remove this program at any time.\n"
exit 0
# Check if the file doesn't exist or it's been over an hour since the last ask
if [ ! -e "$tmp_file" ] || [ ! -f "$tmp_file" ] || [ $(( $(date +%s) - $(cat "$tmp_file") )) -gt $ask_interval ] || [ $force_pvekclean_update == true ] || [ -n "$force_pvekclean_install" ]; then
# If pvekclean does not exist on the system or force_purge is enabled
if [ ! -f /usr/local/sbin/$program_name ] || [ $force_pvekclean_update == true ] || [ -n "$force_pvekclean_install" ]; then
# Ask user if we can install it to their system
if [ $force_purge == true ]; then
REPLY="n"
else
# Update the timestamp in the file to record the time of the last ask
echo $(date +%s) > "$tmp_file"
# Ask if we can install it
printf "${bold}[-]${reset} Can we install PVE Kernel Cleaner to your /usr/local/sbin for easier access [y/N] "
read -n 1 -r
printf "\n"
fi
# User agrees to have it installed
if [[ $REPLY =~ ^[Yy]$ ]]; then
# Copy the script to /usr/local/sbin and set execution permissions
cp $0 /usr/local/sbin/$program_name
chmod +x /usr/local/sbin/$program_name
# Tell user how to use it
printf "${bold}[*]${reset} Installed PVE Kernel Cleaner to /usr/local/sbin/$program_name\n"
printf "${bold}[*]${reset} Run the command \"$program_name\" to begin using this program.\n"
printf "${bold}[-]${reset} Run the command \"$program_name -r\" to remove this program at any time.\n"
exit 0
fi
fi
fi
if [ -n "$force_pvekclean_install" ]; then
exit 0
fi
}
# Uninstall pvekclean from the system
@@ -302,24 +333,21 @@ uninstall_program() {
# PVE Kernel Clean main function
pve_kernel_clean() {
# Find all the PVE kernels on the system
kernels=$(dpkg --list | grep -E '(pve-kernel|proxmox-kernel)-.*-pve' | awk '{print $2}' | sed -n 's/\(pve\|proxmox\)-kernel-\(.*\)/\2/p' | sort -V)
kernels=$(dpkg --list | grep -E "(pve-kernel|proxmox-kernel)-[0-9].*" | grep -E "Kernel Image" | grep -vE "${latest_kernel%-pve}|series|transitional" | awk '{print $2}' | sed -n 's/\(pve\|proxmox\)-kernel-\(.*\)/\2/p' | sort -V)
# List of kernels that will be removed (adds them as the script goes on)
kernels_to_remove=()
# Check the /boot used
printf "${bold}[*]${reset} Boot disk space used is "
# Warn user when the /boot is critically full
if [[ "${boot_info[4]}" -ge "$boot_critical_percent" ]]; then
printf "${bold}${orange}critically full${reset} "
# Tell them if it is at an acceptable percentage
else
printf "${bold}${green}healthy${reset} "
fi
# Display percentage used and available space left
printf "at ${boot_info[4]}%% capacity (${boot_info[3]} free)\n"
# Boot drive status
boot_drive_status=$(get_drive_status ${boot_info[4]})
# Show space used, status and free space available
printf "${bold}[*]${reset} Boot disk space used is ${bold}${boot_drive_status}${reset} at ${boot_info[4]}%% capacity (${boot_info[3]} free)\n"
# For each kernel that was found via dpkg
current_kernel_passed=false
for kernel in $kernels
do
# Check if the kernel is already in the array
if [[ " ${kernels_to_remove[@]} " =~ " $kernel " ]]; then
continue # Skip adding it again
fi
# Only if not removing newer kernels and kernel matches the current kernel
if [ "$(echo $kernel | grep "$current_kernel")" ]; then
if [ "$remove_newer" == "false" ]; then
@@ -334,9 +362,9 @@ pve_kernel_clean() {
fi
done
# If remove_newer is set keep the last kernel installed as its newest
if [ "$remove_newer" == "true" ] && [ "$current_kernel_passed" == "true" ] && [ ${#kernels_to_remove[@]} -gt 0 ]; then
unset kernels_to_remove[-1]
fi
# if [ "$remove_newer" == "true" ] && [ "$current_kernel_passed" == "true" ] && [ ${#kernels_to_remove[@]} -gt 0 ]; then
# unset kernels_to_remove[-1]
# fi
# If keep_kernels is set we remove this number from the array to remove
if [[ -n "$keep_kernels" ]] && [[ "$keep_kernels" =~ ^[0-9]+$ ]]; then
if [ $keep_kernels -gt 0 ]; then
@@ -384,7 +412,7 @@ pve_kernel_clean() {
do
printf "${bold}[-]${reset} Removing kernel: $kernel..."
# Purge the old kernels via apt and suppress output
if [ "$debug" != "true" ]; then
if [ "$dry_run" != "true" ]; then
/usr/bin/apt purge -y pve-kernel-$kernel > /dev/null 2>&1
/usr/bin/apt purge -y proxmox-kernel-$kernel > /dev/null 2>&1
/usr/bin/apt purge -y pve-kernel-${kernel%-pve} > /dev/null 2>&1
@@ -393,14 +421,18 @@ pve_kernel_clean() {
/usr/bin/apt purge -y proxmox-headers-${kernel%-pve} > /dev/null 2>&1
fi
sleep 1
printf "DONE!\n"
printf "${bold}${green}DONE!${reset}\n"
done
printf "${bold}[*]${reset} Updating GRUB..."
# Update grub after kernels are removed, suppress output
if [ "$debug" != "true" ]; then
if [ "$dry_run" != "true" ]; then
/usr/sbin/update-grub > /dev/null 2>&1
fi
printf "DONE!\n"
printf "${bold}${green}DONE!${reset}\n"
# Get information about the /boot folder
boot_info=($(echo $(df -Ph | grep /boot | tail -1) | sed 's/%//g'))
# Show information about the /boot
printf "${bold}[-]${reset} ${bold}Boot Disk:${reset} ${boot_info[4]}%% full [${boot_info[2]}/${boot_info[1]} used, ${boot_info[3]} free] \n"
# Script finished successfully
printf "${bold}[-]${reset} Have a nice $(timeGreeting) ⎦˚◡˚⎣\n"
# User wishes to not remove the kernels above, exit
@@ -415,12 +447,19 @@ pve_kernel_clean() {
# Function to check for updates
check_for_update() {
if [ "$check_for_updates" == "true" ] && [ "$force_purge" == "false" ]; then
local remote_version=$(curl -s -m 10 https://raw.githubusercontent.com/jordanhillis/pvekclean/master/version.txt || echo "")
# Get latest version number
local remote_version=$(curl -s -m 10 https://raw.githubusercontent.com/jordanhillis/pvekclean/master/version.txt | tr -d '\n' || echo "")
# Unable to fetch remote version, so just skip the update check
if [ -z "$remote_version" ]; then
printf "${bold}[*]${reset} Failed to check for updates. Skipping update check.\n"
return
fi
# Validate the remote_version format using a regex
if [[ ! "$remote_version" =~ ^[0-9]+(\.[0-9]+)*$ ]]; then
printf "${bold}[*]${reset} Invalid remote version format: ${bold}${orange}$remote_version${reset}. Skipping update check.\n"
return
fi
# If version isn't the same
if [ "$remote_version" != "$version" ]; then
printf "*** A new version $remote_version is available! ***\n"
printf "${bold}[*]${reset} Do you want to update? [y/N] "
@@ -443,7 +482,7 @@ check_for_update() {
}
timeGreeting() {
h=$(date +%H)
h=$(date +%k) # Use %k to get the hour as a decimal number (no leading zero)
((h >= 5 && h < 12)) && echo "morning" && return
((h >= 12 && h < 17)) && echo "afternoon" && return
((h >= 17 && h < 21)) && echo "evening" && return
@@ -467,6 +506,11 @@ main() {
while [[ $# -gt 0 ]]; do
case "$1" in
-i|--install )
force_pvekclean_install=true
main
install_program
;;
-r|--remove )
main
uninstall_program
@@ -502,8 +546,8 @@ while [[ $# -gt 0 ]]; do
shift
continue
;;
-d|--debug)
debug=true
-d|--dry-run)
dry_run=true
shift
continue
;;
+1 -1
View File
@@ -1 +1 @@
1.3
2.0.2