open-webui / crypt.sh
wwforonce's picture
add gemini auth files
6fe053e
#!/bin/bash
# Enhanced file encryption/decryption script with multiple password input methods
# Author: Claude
# Date: July 9, 2025
set -e # Exit immediately if a command exits with non-zero status
# ANSI color codes for better readability
RED='\033[0;31m'
GREEN='\033[0;32m'
YELLOW='\033[0;33m'
BLUE='\033[0;34m'
NC='\033[0m' # No Color
# Function to display usage information
usage() {
echo -e "${BLUE}File Encryption/Decryption Utility${NC}"
echo
echo "Usage: $0 <encrypt|decrypt> <filename> [options]"
echo
echo "Required arguments:"
echo " encrypt|decrypt Action to perform"
echo " filename Path to the file to process"
echo
echo "Password options (one method required):"
echo " -i Interactive mode (prompt for password)"
echo " -p <password> Direct password input (least secure)"
echo " -e <env_var> Use password from environment variable"
echo " -f <password_file> Read password from file"
echo
echo "Other options:"
echo " -o <output_file> Specify output filename"
echo " -a <algorithm> Encryption algorithm (default: aes-256-cbc)"
echo " -h Display this help message"
echo
echo -e "${YELLOW}Security Notice:${NC}"
echo " - Interactive mode (-i) is the most secure option"
echo " - Direct password (-p) is visible in process listings and command history"
echo " - Environment variables (-e) are more secure than direct input"
echo " - Password files (-f) should be stored securely and deleted after use"
echo
exit 1
}
# Function to log messages
log_info() {
echo -e "${GREEN}[INFO]${NC} $1"
}
log_warn() {
echo -e "${YELLOW}[WARNING]${NC} $1"
}
log_error() {
echo -e "${RED}[ERROR]${NC} $1"
}
# Function to securely delete a file
secure_delete() {
local file="$1"
if command -v shred &> /dev/null; then
shred -u "$file"
elif command -v srm &> /dev/null; then
srm "$file"
else
rm "$file"
log_warn "Secure deletion tools (shred/srm) not found. Used regular rm instead."
fi
}
# Default values
ACTION=""
INPUT_FILE=""
OUTPUT_FILE=""
ALGORITHM="aes-256-cbc"
PASS_OPTION=""
TEMP_PWD_FILE=""
INTERACTIVE=0
# Parse arguments
if [ $# -lt 2 ]; then
usage
fi
ACTION="$1"
INPUT_FILE="$2"
shift 2
# Check if action is valid
if [[ "$ACTION" != "encrypt" && "$ACTION" != "decrypt" ]]; then
log_error "Invalid action: $ACTION. Must be 'encrypt' or 'decrypt'."
usage
fi
# Check if the input file exists
if [ ! -f "$INPUT_FILE" ]; then
log_error "File not found: $INPUT_FILE"
exit 1
fi
# Process remaining arguments
while [ $# -gt 0 ]; do
case "$1" in
-o)
if [ $# -lt 2 ]; then
log_error "Missing output filename after -o"
usage
fi
OUTPUT_FILE="$2"
shift 2
;;
-a)
if [ $# -lt 2 ]; then
log_error "Missing algorithm after -a"
usage
fi
ALGORITHM="$2"
shift 2
;;
-i)
INTERACTIVE=1
shift
;;
-p)
if [ $# -lt 2 ]; then
log_error "Missing password after -p"
usage
fi
if [ $INTERACTIVE -eq 1 ] || [ -n "$PASS_OPTION" ]; then
log_error "Only one password method can be used at a time."
usage
fi
log_warn "Using password on command line is insecure!"
PASS_OPTION="-pass pass:$2"
shift 2
;;
-e)
if [ $# -lt 2 ]; then
log_error "Missing environment variable name after -e"
usage
fi
if [ $INTERACTIVE -eq 1 ] || [ -n "$PASS_OPTION" ]; then
log_error "Only one password method can be used at a time."
usage
fi
ENV_VAR_NAME="$2"
if [ -z "${!ENV_VAR_NAME}" ]; then
log_error "Environment variable $ENV_VAR_NAME is not set or empty"
exit 1
fi
PASS_OPTION="-pass env:$ENV_VAR_NAME"
shift 2
;;
-f)
if [ $# -lt 2 ]; then
log_error "Missing password file after -f"
usage
fi
if [ $INTERACTIVE -eq 1 ] || [ -n "$PASS_OPTION" ]; then
log_error "Only one password method can be used at a time."
usage
fi
PASSWORD_FILE="$2"
if [ ! -f "$PASSWORD_FILE" ]; then
log_error "Password file not found: $PASSWORD_FILE"
exit 1
fi
PASS_OPTION="-pass file:$PASSWORD_FILE"
shift 2
;;
-h)
usage
;;
*)
log_error "Unknown option: $1"
usage
;;
esac
done
# Determine the output filename if not specified
if [ -z "$OUTPUT_FILE" ]; then
case "$ACTION" in
encrypt)
OUTPUT_FILE="${INPUT_FILE}.enc"
;;
decrypt)
OUTPUT_FILE="${INPUT_FILE%.enc}"
# If removing .enc doesn't change the filename, append .decrypted
if [ "$OUTPUT_FILE" = "$INPUT_FILE" ]; then
OUTPUT_FILE="${INPUT_FILE}.decrypted"
fi
;;
esac
fi
# Check if output file already exists
if [ -f "$OUTPUT_FILE" ]; then
read -p "Output file already exists. Overwrite? (y/n): " -n 1 -r
echo
if [[ ! $REPLY =~ ^[Yy]$ ]]; then
log_info "Operation cancelled."
exit 0
fi
fi
# Interactive mode (takes precedence if no other method was specified)
if [ $INTERACTIVE -eq 1 ] || [ -z "$PASS_OPTION" ]; then
# Create a temporary file for the password
TEMP_PWD_FILE=$(mktemp)
chmod 600 "$TEMP_PWD_FILE" # Secure permissions
# Get password securely
if [ "$ACTION" = "encrypt" ]; then
read -s -p "Enter password for encryption: " PASSWORD
echo
read -s -p "Confirm password: " PASSWORD_CONFIRM
echo
if [ "$PASSWORD" != "$PASSWORD_CONFIRM" ]; then
secure_delete "$TEMP_PWD_FILE"
log_error "Passwords do not match."
exit 1
fi
else
read -s -p "Enter password for decryption: " PASSWORD
echo
fi
echo "$PASSWORD" > "$TEMP_PWD_FILE"
PASS_OPTION="-pass file:$TEMP_PWD_FILE"
fi
# Validate that we have a password method
if [ -z "$PASS_OPTION" ]; then
log_error "No password method specified."
usage
fi
# Perform the requested action
log_info "Processing file: $INPUT_FILE$OUTPUT_FILE"
log_info "Using algorithm: $ALGORITHM"
# For OpenSSL 1.1.1 and newer, add pbkdf2 for better security
OPENSSL_VERSION=$(openssl version | awk '{print $2}')
PBKDF_OPTION=""
if [[ "$OPENSSL_VERSION" > "1.1.0" ]]; then
PBKDF_OPTION="-pbkdf2"
fi
if [ "$ACTION" = "encrypt" ]; then
# Attempt encryption
if openssl enc -base64 -$ALGORITHM -salt -in "$INPUT_FILE" -out "$OUTPUT_FILE" $PBKDF_OPTION $PASS_OPTION; then
log_info "File encrypted successfully!"
else
log_error "Encryption failed!"
[ -f "$OUTPUT_FILE" ] && rm -f "$OUTPUT_FILE"
[ -n "$TEMP_PWD_FILE" ] && secure_delete "$TEMP_PWD_FILE"
exit 1
fi
else
# Attempt decryption
if openssl enc -base64 -d -$ALGORITHM -salt -in "$INPUT_FILE" -out "$OUTPUT_FILE" $PBKDF_OPTION $PASS_OPTION; then
log_info "File decrypted successfully!"
else
log_error "Decryption failed! This could be due to an incorrect password or corrupted file."
[ -f "$OUTPUT_FILE" ] && rm -f "$OUTPUT_FILE"
[ -n "$TEMP_PWD_FILE" ] && secure_delete "$TEMP_PWD_FILE"
exit 1
fi
fi
# Clean up temporary password file if used
if [ -n "$TEMP_PWD_FILE" ]; then
secure_delete "$TEMP_PWD_FILE"
fi
# Verify the output file exists
if [ -f "$OUTPUT_FILE" ]; then
log_info "Output written to: $OUTPUT_FILE"
# Show file details
log_info "File details:"
ls -lh "$OUTPUT_FILE" | awk '{print " Size: " $5 " Created: " $6 " " $7 " " $8}'
else
log_error "Failed to create output file!"
exit 1
fi
exit 0