mirror of
https://github.com/acedanger/shell.git
synced 2025-12-06 02:20:11 -08:00
- backup-env-files.sh: Main backup script with Gitea integration - validate-env-backups.sh: Validation and integrity checking - env-backup-integration.sh: Integration with existing backup system - completions/env-backup-completion.bash: Tab completion support - docs/env-backup-system.md: Documentation for the backup system These scripts provide secure backup of .env files to private Gitea repository.
228 lines
7.7 KiB
Bash
Executable File
228 lines
7.7 KiB
Bash
Executable File
#!/bin/bash
|
|
|
|
# validate-env-backups.sh - Validate .env file backups
|
|
# Author: Shell Repository
|
|
# Description: Verify integrity and consistency of .env file backups
|
|
|
|
set -e
|
|
|
|
# Colors for output
|
|
GREEN='\033[0;32m'
|
|
YELLOW='\033[0;33m'
|
|
RED='\033[0;31m'
|
|
BLUE='\033[0;34m'
|
|
NC='\033[0m' # No Color
|
|
|
|
# Configuration
|
|
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
|
|
DOCKER_DIR="$HOME/docker"
|
|
BACKUP_DIR="$HOME/.env-backup"
|
|
LOG_FILE="$SCRIPT_DIR/logs/env-backup-validation.log"
|
|
|
|
# Ensure logs directory exists
|
|
mkdir -p "$(dirname "$LOG_FILE")"
|
|
|
|
# Logging function
|
|
log() {
|
|
echo "$(date '+%Y-%m-%d %H:%M:%S') - $1" | tee -a "$LOG_FILE"
|
|
}
|
|
|
|
# Display usage information
|
|
usage() {
|
|
echo "Usage: $0 [OPTIONS]"
|
|
echo ""
|
|
echo "Validate .env file backups against source files"
|
|
echo ""
|
|
echo "Options:"
|
|
echo " -h, --help Show this help message"
|
|
echo " -v, --verbose Verbose output"
|
|
echo " -s, --summary-only Show only summary"
|
|
echo " -m, --missing-only Show only missing files"
|
|
echo " -d, --diff Show differences between files"
|
|
echo ""
|
|
echo "Examples:"
|
|
echo " $0 # Basic validation"
|
|
echo " $0 --verbose # Detailed validation"
|
|
echo " $0 --missing-only # Show only missing backups"
|
|
echo " $0 --diff # Show file differences"
|
|
}
|
|
|
|
# Validate backups
|
|
validate_backups() {
|
|
local verbose="$1"
|
|
local summary_only="$2"
|
|
local missing_only="$3"
|
|
local show_diff="$4"
|
|
|
|
echo -e "${BLUE}=== .env Backup Validation ===${NC}"
|
|
echo "Source: $DOCKER_DIR"
|
|
echo "Backup: $BACKUP_DIR"
|
|
echo ""
|
|
|
|
if [ ! -d "$BACKUP_DIR" ]; then
|
|
echo -e "${RED}Error: Backup directory not found at $BACKUP_DIR${NC}"
|
|
echo "Run backup-env-files.sh --init first"
|
|
exit 1
|
|
fi
|
|
|
|
local total_source=0
|
|
local total_backup=0
|
|
local missing_backup=0
|
|
local outdated_backup=0
|
|
local identical_files=0
|
|
local different_files=0
|
|
local backup_only=0
|
|
|
|
# Arrays to store file lists
|
|
declare -a missing_files=()
|
|
declare -a outdated_files=()
|
|
declare -a different_files_list=()
|
|
declare -a backup_only_files=()
|
|
|
|
# Count and validate source files
|
|
echo -e "${YELLOW}Scanning source files...${NC}"
|
|
while IFS= read -r source_file; do
|
|
if [ -n "$source_file" ]; then
|
|
((total_source++))
|
|
|
|
# Determine backup path
|
|
local rel_path="${source_file#$DOCKER_DIR/}"
|
|
local backup_file="$BACKUP_DIR/docker-containers/$rel_path"
|
|
|
|
if [ ! -f "$backup_file" ]; then
|
|
((missing_backup++))
|
|
missing_files+=("$rel_path")
|
|
[ "$summary_only" != true ] && [ "$missing_only" != true ] && echo -e "${RED}✗ Missing backup: $rel_path${NC}"
|
|
else
|
|
# Compare files
|
|
if cmp -s "$source_file" "$backup_file"; then
|
|
((identical_files++))
|
|
[ "$verbose" = true ] && [ "$summary_only" != true ] && [ "$missing_only" != true ] && echo -e "${GREEN}✓ Identical: $rel_path${NC}"
|
|
else
|
|
# Check if backup is older
|
|
if [ "$source_file" -nt "$backup_file" ]; then
|
|
((outdated_backup++))
|
|
outdated_files+=("$rel_path")
|
|
[ "$summary_only" != true ] && [ "$missing_only" != true ] && echo -e "${YELLOW}⚠ Outdated backup: $rel_path${NC}"
|
|
else
|
|
((different_files++))
|
|
different_files_list+=("$rel_path")
|
|
[ "$summary_only" != true ] && [ "$missing_only" != true ] && echo -e "${BLUE}△ Different: $rel_path${NC}"
|
|
fi
|
|
|
|
# Show diff if requested
|
|
if [ "$show_diff" = true ] && [ "$summary_only" != true ] && [ "$missing_only" != true ]; then
|
|
echo -e "${YELLOW} Differences:${NC}"
|
|
diff -u "$backup_file" "$source_file" | head -20 || true
|
|
echo ""
|
|
fi
|
|
fi
|
|
fi
|
|
fi
|
|
done < <(find "$DOCKER_DIR" -type f \( -name "*.env" -o -name ".env*" -o -name "env.*" \) 2>/dev/null | sort)
|
|
|
|
# Check for backup-only files
|
|
echo -e "${YELLOW}Scanning backup files...${NC}"
|
|
if [ -d "$BACKUP_DIR/docker-containers" ]; then
|
|
while IFS= read -r backup_file; do
|
|
if [ -n "$backup_file" ]; then
|
|
((total_backup++))
|
|
|
|
# Determine source path
|
|
local rel_path="${backup_file#$BACKUP_DIR/docker-containers/}"
|
|
local source_file="$DOCKER_DIR/$rel_path"
|
|
|
|
if [ ! -f "$source_file" ]; then
|
|
((backup_only++))
|
|
backup_only_files+=("$rel_path")
|
|
[ "$summary_only" != true ] && [ "$missing_only" != true ] && echo -e "${BLUE}⚡ Backup only: $rel_path${NC}"
|
|
fi
|
|
fi
|
|
done < <(find "$BACKUP_DIR/docker-containers" -type f \( -name "*.env" -o -name ".env*" -o -name "env.*" \) 2>/dev/null | sort)
|
|
fi
|
|
|
|
# Display missing files if requested
|
|
if [ "$missing_only" = true ] && [ ${#missing_files[@]} -gt 0 ]; then
|
|
echo -e "${RED}=== Missing Backup Files ===${NC}"
|
|
for file in "${missing_files[@]}"; do
|
|
echo -e "${RED}✗ $file${NC}"
|
|
done
|
|
echo ""
|
|
fi
|
|
|
|
# Summary
|
|
echo -e "${BLUE}=== Validation Summary ===${NC}"
|
|
echo -e "Source files: ${BLUE}$total_source${NC}"
|
|
echo -e "Backup files: ${BLUE}$total_backup${NC}"
|
|
echo -e "Identical: ${GREEN}$identical_files${NC}"
|
|
echo -e "Missing backups: ${RED}$missing_backup${NC}"
|
|
echo -e "Outdated backups: ${YELLOW}$outdated_backup${NC}"
|
|
echo -e "Different files: ${BLUE}$different_files${NC}"
|
|
echo -e "Backup only: ${BLUE}$backup_only${NC}"
|
|
echo ""
|
|
|
|
# Recommendations
|
|
if [ $missing_backup -gt 0 ] || [ $outdated_backup -gt 0 ]; then
|
|
echo -e "${YELLOW}=== Recommendations ===${NC}"
|
|
if [ $missing_backup -gt 0 ]; then
|
|
echo -e "${YELLOW}• Run backup-env-files.sh to backup missing files${NC}"
|
|
fi
|
|
if [ $outdated_backup -gt 0 ]; then
|
|
echo -e "${YELLOW}• Run backup-env-files.sh to update outdated backups${NC}"
|
|
fi
|
|
echo ""
|
|
fi
|
|
|
|
# Log summary
|
|
log "Validation completed - Source: $total_source, Backup: $total_backup, Missing: $missing_backup, Outdated: $outdated_backup"
|
|
|
|
# Exit with error code if issues found
|
|
if [ $missing_backup -gt 0 ] || [ $outdated_backup -gt 0 ]; then
|
|
exit 1
|
|
fi
|
|
}
|
|
|
|
# Main function
|
|
main() {
|
|
local verbose=false
|
|
local summary_only=false
|
|
local missing_only=false
|
|
local show_diff=false
|
|
|
|
# Parse command line arguments
|
|
while [[ $# -gt 0 ]]; do
|
|
case $1 in
|
|
-h|--help)
|
|
usage
|
|
exit 0
|
|
;;
|
|
-v|--verbose)
|
|
verbose=true
|
|
shift
|
|
;;
|
|
-s|--summary-only)
|
|
summary_only=true
|
|
shift
|
|
;;
|
|
-m|--missing-only)
|
|
missing_only=true
|
|
shift
|
|
;;
|
|
-d|--diff)
|
|
show_diff=true
|
|
shift
|
|
;;
|
|
*)
|
|
echo "Unknown option: $1"
|
|
usage
|
|
exit 1
|
|
;;
|
|
esac
|
|
done
|
|
|
|
validate_backups "$verbose" "$summary_only" "$missing_only" "$show_diff"
|
|
}
|
|
|
|
# Run main function with all arguments
|
|
main "$@"
|