Last active
December 19, 2025 11:25
-
-
Save anhvandev/23c4f7504bf7aec8f1fb854facb36030 to your computer and use it in GitHub Desktop.
Basic secure for vps, ver 2
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| #!/bin/bash | |
| ############################################# | |
| # VPS Security Hardening Script | |
| # Hỗ trợ: Ubuntu, Debian, CentOS, RHEL, | |
| # Fedora, AlmaLinux, Rocky Linux, Oracle Linux | |
| ############################################# | |
| set -e | |
| # Màu sắc cho output | |
| RED='\033[0;31m' | |
| GREEN='\033[0;32m' | |
| YELLOW='\033[1;33m' | |
| NC='\033[0m' # No Color | |
| # File lưu thông tin | |
| INFO_FILE="/root/vps_security_info_$(date +%Y%m%d_%H%M%S).txt" | |
| # Hàm in thông báo | |
| print_status() { | |
| echo -e "${GREEN}[✓]${NC} $1" | |
| } | |
| print_error() { | |
| echo -e "${RED}[✗]${NC} $1" | |
| } | |
| print_warning() { | |
| echo -e "${YELLOW}[!]${NC} $1" | |
| } | |
| # Kiểm tra quyền root | |
| if [ "$EUID" -ne 0 ]; then | |
| print_error "Script này cần chạy với quyền root!" | |
| exit 1 | |
| fi | |
| # Phát hiện hệ điều hành | |
| detect_os() { | |
| if [ -f /etc/os-release ]; then | |
| . /etc/os-release | |
| OS=$ID | |
| VER=$VERSION_ID | |
| OS_FAMILY="" | |
| case $OS in | |
| ubuntu|debian) | |
| OS_FAMILY="debian" | |
| PKG_MANAGER="apt" | |
| ;; | |
| centos|rhel|fedora|almalinux|rocky|ol) | |
| OS_FAMILY="rhel" | |
| if command -v dnf &> /dev/null; then | |
| PKG_MANAGER="dnf" | |
| else | |
| PKG_MANAGER="yum" | |
| fi | |
| ;; | |
| *) | |
| print_error "Hệ điều hành không được hỗ trợ: $OS" | |
| exit 1 | |
| ;; | |
| esac | |
| print_status "Phát hiện hệ điều hành: $NAME $VERSION" | |
| else | |
| print_error "Không thể phát hiện hệ điều hành" | |
| exit 1 | |
| fi | |
| } | |
| # Phát hiện SSH mode (socket-based hay service-based) | |
| # Ubuntu 22.10+ sử dụng ssh.socket mặc định | |
| detect_ssh_mode() { | |
| SSH_MODE="service" # Mặc định là service mode | |
| # Kiểm tra xem ssh.socket có đang active không | |
| if systemctl is-active --quiet ssh.socket 2>/dev/null; then | |
| SSH_MODE="socket" | |
| print_status "Phát hiện SSH mode: socket-based (ssh.socket)" | |
| return | |
| fi | |
| # Kiểm tra xem ssh.socket có enabled không (có thể chưa start) | |
| if systemctl is-enabled --quiet ssh.socket 2>/dev/null; then | |
| SSH_MODE="socket" | |
| print_status "Phát hiện SSH mode: socket-based (ssh.socket)" | |
| return | |
| fi | |
| # Kiểm tra theo OS version cho các hệ thống Debian-based | |
| if [ "$OS_FAMILY" = "debian" ]; then | |
| case $OS in | |
| ubuntu) | |
| # Ubuntu 22.10 (Kinetic) trở lên dùng ssh.socket | |
| # 22.10 = 22.10, 23.04 = 23.04, 23.10 = 23.10, 24.04 = 24.04, etc. | |
| if [ -n "$VER" ]; then | |
| MAJOR_VER=$(echo "$VER" | cut -d. -f1) | |
| MINOR_VER=$(echo "$VER" | cut -d. -f2) | |
| # Version comparison: 22.10+ or 23+ or 24+ | |
| if [ "$MAJOR_VER" -gt 22 ] 2>/dev/null; then | |
| SSH_MODE="socket" | |
| elif [ "$MAJOR_VER" -eq 22 ] && [ "$MINOR_VER" -ge 10 ] 2>/dev/null; then | |
| SSH_MODE="socket" | |
| fi | |
| fi | |
| ;; | |
| debian) | |
| # Debian 12 (Bookworm) trở lên có thể dùng ssh.socket | |
| # Nhưng cần kiểm tra xem có được enable không | |
| if [ -n "$VER" ]; then | |
| MAJOR_VER=$(echo "$VER" | cut -d. -f1) | |
| if [ "$MAJOR_VER" -ge 12 ] 2>/dev/null; then | |
| # Kiểm tra xem ssh.socket unit có tồn tại không | |
| if systemctl list-unit-files ssh.socket &>/dev/null; then | |
| # Debian 12+ hỗ trợ nhưng không bắt buộc | |
| # Giữ nguyên mode service nếu socket chưa được enable | |
| : # No-op, giữ service mode | |
| fi | |
| fi | |
| fi | |
| ;; | |
| esac | |
| fi | |
| if [ "$SSH_MODE" = "socket" ]; then | |
| print_status "Phát hiện SSH mode: socket-based (ssh.socket) - OS version detection" | |
| else | |
| print_status "Phát hiện SSH mode: service-based (sshd.service/ssh.service)" | |
| fi | |
| } | |
| # Cập nhật hệ thống | |
| update_system() { | |
| print_status "Đang cập nhật hệ thống..." | |
| if [ "$OS_FAMILY" = "debian" ]; then | |
| export DEBIAN_FRONTEND=noninteractive | |
| apt update -y | |
| apt upgrade -y | |
| apt autoremove -y | |
| else | |
| $PKG_MANAGER update -y | |
| $PKG_MANAGER upgrade -y | |
| $PKG_MANAGER autoremove -y | |
| fi | |
| print_status "Cập nhật hệ thống hoàn tất" | |
| } | |
| # Tạo mật khẩu ngẫu nhiên mạnh | |
| generate_password() { | |
| openssl rand -base64 32 | tr -d "=+/" | cut -c1-24 | |
| } | |
| # Tạo SSH port ngẫu nhiên | |
| generate_ssh_port() { | |
| # Port từ 10000 đến 65000 để tránh conflict | |
| echo $((RANDOM % 55000 + 10000)) | |
| } | |
| # Nhập thông tin user | |
| get_user_info() { | |
| while true; do | |
| read -p "Nhập tên user mới (không phải root): " NEW_USER | |
| if [ -z "$NEW_USER" ]; then | |
| print_error "Tên user không được để trống!" | |
| continue | |
| fi | |
| if [ "$NEW_USER" = "root" ]; then | |
| print_error "Không thể sử dụng tên 'root'!" | |
| continue | |
| fi | |
| if id "$NEW_USER" &>/dev/null; then | |
| print_error "User đã tồn tại!" | |
| continue | |
| fi | |
| break | |
| done | |
| NEW_PASSWORD=$(generate_password) | |
| SSH_PORT=$(generate_ssh_port) | |
| print_status "Thông tin được tạo:" | |
| echo " - Username: $NEW_USER" | |
| echo " - Password: $NEW_PASSWORD" | |
| echo " - SSH Port: $SSH_PORT" | |
| } | |
| # Tạo user mới với sudo | |
| create_user() { | |
| print_status "Đang tạo user mới..." | |
| useradd -m -s /bin/bash "$NEW_USER" | |
| echo "$NEW_USER:$NEW_PASSWORD" | chpasswd | |
| # Thêm vào sudo group | |
| if [ "$OS_FAMILY" = "debian" ]; then | |
| usermod -aG sudo "$NEW_USER" | |
| else | |
| usermod -aG wheel "$NEW_USER" | |
| fi | |
| print_status "User $NEW_USER đã được tạo với quyền sudo" | |
| } | |
| # Tạo SSH key | |
| setup_ssh_key() { | |
| print_status "Đang tạo SSH key..." | |
| USER_HOME="/home/$NEW_USER" | |
| SSH_DIR="$USER_HOME/.ssh" | |
| mkdir -p "$SSH_DIR" | |
| chmod 700 "$SSH_DIR" | |
| # Tạo SSH key pair | |
| ssh-keygen -t ed25519 -C "$NEW_USER@$(hostname)" -f "$SSH_DIR/id_ed25519" -N "" -q | |
| # Tạo authorized_keys | |
| cat "$SSH_DIR/id_ed25519.pub" > "$SSH_DIR/authorized_keys" | |
| chmod 600 "$SSH_DIR/authorized_keys" | |
| # Copy private key ra ngoài để admin lấy | |
| cp "$SSH_DIR/id_ed25519" "/root/${NEW_USER}_ssh_key" | |
| chmod 600 "/root/${NEW_USER}_ssh_key" | |
| # Set ownership | |
| chown -R "$NEW_USER:$NEW_USER" "$SSH_DIR" | |
| SSH_PRIVATE_KEY_PATH="/root/${NEW_USER}_ssh_key" | |
| SSH_PUBLIC_KEY=$(cat "$SSH_DIR/id_ed25519.pub") | |
| print_status "SSH key đã được tạo" | |
| } | |
| # Cấu hình SSH | |
| configure_ssh() { | |
| print_status "Đang cấu hình SSH..." | |
| SSHD_CONFIG="/etc/ssh/sshd_config" | |
| # Backup cấu hình cũ | |
| cp "$SSHD_CONFIG" "${SSHD_CONFIG}.backup.$(date +%Y%m%d_%H%M%S)" | |
| # Cấu hình SSH với sed để tương thích với nhiều phiên bản | |
| sed -i 's/^#\?Port .*/Port '"$SSH_PORT"'/' "$SSHD_CONFIG" | |
| sed -i 's/^#\?PermitRootLogin .*/PermitRootLogin no/' "$SSHD_CONFIG" | |
| sed -i 's/^#\?PasswordAuthentication .*/PasswordAuthentication no/' "$SSHD_CONFIG" | |
| sed -i 's/^#\?PubkeyAuthentication .*/PubkeyAuthentication yes/' "$SSHD_CONFIG" | |
| sed -i 's/^#\?ChallengeResponseAuthentication .*/ChallengeResponseAuthentication no/' "$SSHD_CONFIG" | |
| sed -i 's/^#\?UsePAM .*/UsePAM yes/' "$SSHD_CONFIG" | |
| sed -i 's/^#\?X11Forwarding .*/X11Forwarding no/' "$SSHD_CONFIG" | |
| # Thêm các cấu hình bảo mật nâng cao nếu chưa có | |
| grep -q "^MaxAuthTries" "$SSHD_CONFIG" || echo "MaxAuthTries 3" >> "$SSHD_CONFIG" | |
| grep -q "^MaxSessions" "$SSHD_CONFIG" || echo "MaxSessions 2" >> "$SSHD_CONFIG" | |
| grep -q "^ClientAliveInterval" "$SSHD_CONFIG" || echo "ClientAliveInterval 300" >> "$SSHD_CONFIG" | |
| grep -q "^ClientAliveCountMax" "$SSHD_CONFIG" || echo "ClientAliveCountMax 2" >> "$SSHD_CONFIG" | |
| grep -q "^AllowUsers" "$SSHD_CONFIG" || echo "AllowUsers $NEW_USER" >> "$SSHD_CONFIG" | |
| # Cấu hình thêm cho SSH socket mode (Ubuntu 22.10+, Debian 12+) | |
| if [ "$SSH_MODE" = "socket" ]; then | |
| print_status "Đang cấu hình cho SSH socket mode..." | |
| # Trong Ubuntu 24.04+, port từ sshd_config được systemd generator tự động đọc | |
| # Không cần cấu hình riêng ssh.socket như các version cũ (22.10, 23.04, 23.10) | |
| # Kiểm tra xem có cần tạo override cho ssh.socket không | |
| # (Áp dụng cho Ubuntu 22.10, 23.04, 23.10 - các version không có systemd generator) | |
| SSH_SOCKET_NEEDS_OVERRIDE=false | |
| if [ "$OS" = "ubuntu" ] && [ -n "$VER" ]; then | |
| MAJOR_VER=$(echo "$VER" | cut -d. -f1) | |
| MINOR_VER=$(echo "$VER" | cut -d. -f2) | |
| # Ubuntu 22.10, 23.04, 23.10 cần override | |
| # Ubuntu 24.04+ không cần vì có systemd generator | |
| if [ "$MAJOR_VER" -eq 22 ] && [ "$MINOR_VER" -eq 10 ]; then | |
| SSH_SOCKET_NEEDS_OVERRIDE=true | |
| elif [ "$MAJOR_VER" -eq 23 ]; then | |
| SSH_SOCKET_NEEDS_OVERRIDE=true | |
| fi | |
| fi | |
| if [ "$SSH_SOCKET_NEEDS_OVERRIDE" = true ]; then | |
| print_status "Tạo override cho ssh.socket (Ubuntu $VER)..." | |
| # Tạo override directory | |
| mkdir -p /etc/systemd/system/ssh.socket.d | |
| # Tạo override file để thay đổi port | |
| cat > /etc/systemd/system/ssh.socket.d/override.conf << EOF | |
| [Socket] | |
| ListenStream= | |
| ListenStream=$SSH_PORT | |
| EOF | |
| print_status "Đã tạo override ssh.socket với port $SSH_PORT" | |
| else | |
| print_status "Ubuntu $VER sử dụng systemd generator - port tự động đọc từ sshd_config" | |
| fi | |
| # Reload systemd để nhận cấu hình mới | |
| systemctl daemon-reload | |
| fi | |
| print_status "SSH đã được cấu hình" | |
| } | |
| # Restart SSH service | |
| restart_ssh() { | |
| print_status "Đang restart SSH ($SSH_MODE mode)..." | |
| if [ "$SSH_MODE" = "socket" ]; then | |
| # Socket-based SSH (Ubuntu 22.10+) | |
| # Cần reload systemd trước để nhận cấu hình mới | |
| systemctl daemon-reload | |
| # Restart ssh.socket | |
| if systemctl restart ssh.socket 2>/dev/null; then | |
| print_status "SSH socket đã được restart (ssh.socket)" | |
| # Hiển thị trạng thái | |
| if systemctl is-active --quiet ssh.socket; then | |
| print_status "SSH socket đang lắng nghe trên port $SSH_PORT" | |
| fi | |
| else | |
| print_error "Không thể restart ssh.socket" | |
| print_warning "Đang thử restart theo cách truyền thống..." | |
| # Fallback: thử restart service | |
| if systemctl restart sshd 2>/dev/null || systemctl restart ssh 2>/dev/null; then | |
| print_status "SSH service đã được restart (fallback)" | |
| else | |
| print_error "Không thể restart SSH" | |
| return 1 | |
| fi | |
| fi | |
| else | |
| # Traditional service-based SSH | |
| if systemctl restart sshd 2>/dev/null; then | |
| print_status "SSH service đã được restart (sshd)" | |
| elif systemctl restart ssh 2>/dev/null; then | |
| print_status "SSH service đã được restart (ssh)" | |
| else | |
| print_error "Không thể restart SSH service" | |
| return 1 | |
| fi | |
| fi | |
| # Verify SSH is working | |
| sleep 1 | |
| if [ "$SSH_MODE" = "socket" ]; then | |
| if systemctl is-active --quiet ssh.socket; then | |
| print_status "SSH đang hoạt động bình thường (socket mode)" | |
| else | |
| print_warning "SSH socket không active - kiểm tra cấu hình" | |
| fi | |
| else | |
| if systemctl is-active --quiet sshd 2>/dev/null || systemctl is-active --quiet ssh 2>/dev/null; then | |
| print_status "SSH đang hoạt động bình thường (service mode)" | |
| else | |
| print_warning "SSH service không active - kiểm tra cấu hình" | |
| fi | |
| fi | |
| } | |
| # Cài đặt và cấu hình firewall | |
| setup_firewall() { | |
| print_status "Đang cài đặt firewall..." | |
| if [ "$OS_FAMILY" = "debian" ]; then | |
| # UFW cho Debian/Ubuntu | |
| apt install -y ufw | |
| # Reset về mặc định | |
| ufw --force reset | |
| # Cấu hình mặc định | |
| ufw default deny incoming | |
| ufw default allow outgoing | |
| # Cho phép SSH port mới | |
| ufw allow "$SSH_PORT/tcp" | |
| # Cho phép HTTP/HTTPS nếu cần | |
| read -p "Bạn có muốn mở port HTTP (80) và HTTPS (443)? (y/n): " OPEN_WEB | |
| if [[ "$OPEN_WEB" =~ ^[Yy]$ ]]; then | |
| ufw allow 80/tcp | |
| ufw allow 443/tcp | |
| print_status "Đã mở port 80 và 443" | |
| fi | |
| # Enable UFW | |
| ufw --force enable | |
| print_status "UFW firewall đã được cấu hình" | |
| else | |
| # FirewallD cho RHEL-based | |
| $PKG_MANAGER install -y firewalld | |
| systemctl enable firewalld | |
| systemctl start firewalld | |
| # Cấu hình firewall | |
| firewall-cmd --permanent --add-port="$SSH_PORT/tcp" | |
| # Cho phép HTTP/HTTPS nếu cần | |
| read -p "Bạn có muốn mở port HTTP (80) và HTTPS (443)? (y/n): " OPEN_WEB | |
| if [[ "$OPEN_WEB" =~ ^[Yy]$ ]]; then | |
| firewall-cmd --permanent --add-service=http | |
| firewall-cmd --permanent --add-service=https | |
| print_status "Đã mở port 80 và 443" | |
| fi | |
| # Xóa SSH port mặc định nếu có | |
| firewall-cmd --permanent --remove-service=ssh 2>/dev/null || true | |
| firewall-cmd --reload | |
| print_status "FirewallD đã được cấu hình" | |
| fi | |
| } | |
| # Cài đặt và cấu hình fail2ban | |
| setup_fail2ban() { | |
| print_status "Đang cài đặt fail2ban..." | |
| if [ "$OS_FAMILY" = "debian" ]; then | |
| apt install -y fail2ban | |
| else | |
| # Enable EPEL cho các bản RHEL-based | |
| if [ "$OS" = "centos" ] || [ "$OS" = "rhel" ] || [ "$OS" = "almalinux" ] || [ "$OS" = "rocky" ] || [ "$OS" = "ol" ]; then | |
| if [ "$PKG_MANAGER" = "dnf" ]; then | |
| dnf install -y epel-release | |
| else | |
| yum install -y epel-release | |
| fi | |
| fi | |
| $PKG_MANAGER install -y fail2ban | |
| fi | |
| # Cấu hình fail2ban | |
| cat > /etc/fail2ban/jail.local << EOF | |
| [DEFAULT] | |
| bantime = 3600 | |
| findtime = 600 | |
| maxretry = 3 | |
| destemail = root@localhost | |
| sendername = Fail2Ban | |
| action = %(action_mwl)s | |
| [sshd] | |
| enabled = true | |
| port = $SSH_PORT | |
| filter = sshd | |
| logpath = /var/log/auth.log | |
| maxretry = 3 | |
| bantime = 7200 | |
| EOF | |
| # Đối với RHEL-based, log path khác | |
| if [ "$OS_FAMILY" = "rhel" ]; then | |
| sed -i 's|/var/log/auth.log|/var/log/secure|' /etc/fail2ban/jail.local | |
| fi | |
| systemctl enable fail2ban | |
| systemctl start fail2ban | |
| print_status "Fail2ban đã được cài đặt và cấu hình" | |
| } | |
| # Cài đặt các công cụ bảo mật bổ sung | |
| install_security_tools() { | |
| print_status "Đang cài đặt các công cụ bảo mật bổ sung..." | |
| if [ "$OS_FAMILY" = "debian" ]; then | |
| apt install -y \ | |
| unattended-upgrades #\ | |
| # logwatch \ | |
| # rkhunter \ | |
| # aide \ | |
| # auditd | |
| # Cấu hình tự động cập nhật bảo mật | |
| dpkg-reconfigure -plow unattended-upgrades 2>/dev/null || true | |
| else | |
| # Cấu hình tự động cập nhật | |
| if [ "$PKG_MANAGER" = "dnf" ]; then | |
| $PKG_MANAGER install -y \ | |
| dnf-automatic | |
| sed -i 's/apply_updates = no/apply_updates = yes/' /etc/dnf/automatic.conf 2>/dev/null || true | |
| systemctl enable dnf-automatic.timer | |
| systemctl start dnf-automatic.timer | |
| else | |
| $PKG_MANAGER install -y \ | |
| yum-cron | |
| sed -i 's/apply_updates = no/apply_updates = yes/' /etc/yum/yum-cron.conf 2>/dev/null || true | |
| systemctl enable yum-cron | |
| systemctl start yum-cron | |
| fi | |
| fi | |
| print_status "Các công cụ bảo mật đã được cài đặt" | |
| } | |
| # Hardening kernel parameters | |
| kernel_hardening() { | |
| print_status "Đang cấu hình kernel hardening..." | |
| cat >> /etc/sysctl.conf << EOF | |
| # Kernel Hardening | |
| net.ipv4.conf.default.rp_filter = 1 | |
| net.ipv4.conf.all.rp_filter = 1 | |
| net.ipv4.tcp_syncookies = 1 | |
| net.ipv4.conf.all.accept_redirects = 0 | |
| net.ipv6.conf.all.accept_redirects = 0 | |
| net.ipv4.conf.all.send_redirects = 0 | |
| net.ipv4.conf.all.accept_source_route = 0 | |
| net.ipv6.conf.all.accept_source_route = 0 | |
| net.ipv4.conf.all.log_martians = 1 | |
| kernel.randomize_va_space = 2 | |
| net.ipv4.icmp_echo_ignore_broadcasts = 1 | |
| net.ipv4.icmp_ignore_bogus_error_responses = 1 | |
| EOF | |
| sysctl -p > /dev/null 2>&1 | |
| print_status "Kernel hardening đã được áp dụng" | |
| } | |
| # Thiết lập Swap | |
| setup_swap() { | |
| print_status "Đang kiểm tra và thiết lập Swap..." | |
| # Kiểm tra swap hiện tại | |
| CURRENT_SWAP=$(free -m | grep Swap | awk '{print $2}') | |
| if [ "$CURRENT_SWAP" -gt 0 ]; then | |
| print_status "Hệ thống đã có ${CURRENT_SWAP}MB swap" | |
| read -p "Bạn có muốn tạo thêm swap mới? (y/n): " CREATE_NEW_SWAP | |
| if [[ ! "$CREATE_NEW_SWAP" =~ ^[Yy]$ ]]; then | |
| print_status "Bỏ qua thiết lập swap" | |
| return 0 | |
| fi | |
| fi | |
| # Tính toán kích thước swap theo RAM | |
| TOTAL_RAM_MB=$(free -m | grep Mem | awk '{print $2}') | |
| TOTAL_RAM_GB=$((TOTAL_RAM_MB / 1024)) | |
| # Logic tính swap size theo best practices | |
| if [ "$TOTAL_RAM_GB" -lt 2 ]; then | |
| # RAM < 2GB: Swap = 2x RAM | |
| SWAP_SIZE_MB=$((TOTAL_RAM_MB * 2)) | |
| REASON="RAM < 2GB, khuyến nghị: 2x RAM" | |
| elif [ "$TOTAL_RAM_GB" -lt 8 ]; then | |
| # RAM 2-8GB: Swap = 1x RAM | |
| SWAP_SIZE_MB=$TOTAL_RAM_MB | |
| REASON="RAM 2-8GB, khuyến nghị: 1x RAM" | |
| elif [ "$TOTAL_RAM_GB" -lt 64 ]; then | |
| # RAM 8-64GB: Swap = 0.5x RAM (minimum 4GB) | |
| SWAP_SIZE_MB=$((TOTAL_RAM_MB / 2)) | |
| if [ "$SWAP_SIZE_MB" -lt 4096 ]; then | |
| SWAP_SIZE_MB=4096 | |
| fi | |
| REASON="RAM 8-64GB, khuyến nghị: 0.5x RAM (min 4GB)" | |
| else | |
| # RAM > 64GB: Swap = 4GB cố định | |
| SWAP_SIZE_MB=4096 | |
| REASON="RAM > 64GB, khuyến nghị: 4GB cố định" | |
| fi | |
| SWAP_SIZE_GB=$((SWAP_SIZE_MB / 1024)) | |
| echo "" | |
| print_status "Thông tin RAM:" | |
| echo " - Tổng RAM: ${TOTAL_RAM_MB}MB (~${TOTAL_RAM_GB}GB)" | |
| echo " - Swap hiện tại: ${CURRENT_SWAP}MB" | |
| echo " - Swap khuyến nghị: ${SWAP_SIZE_MB}MB (~${SWAP_SIZE_GB}GB)" | |
| echo " - Lý do: $REASON" | |
| echo "" | |
| read -p "Bạn có muốn tạo swap với kích thước khuyến nghị? (y/n): " CONFIRM_SWAP | |
| if [[ ! "$CONFIRM_SWAP" =~ ^[Yy]$ ]]; then | |
| read -p "Nhập kích thước swap bạn muốn (MB) [0 để bỏ qua]: " CUSTOM_SWAP | |
| if [ -z "$CUSTOM_SWAP" ] || [ "$CUSTOM_SWAP" -eq 0 ]; then | |
| print_status "Bỏ qua thiết lập swap" | |
| return 0 | |
| fi | |
| SWAP_SIZE_MB=$CUSTOM_SWAP | |
| fi | |
| # Đường dẫn swap file | |
| SWAP_FILE="/swapfile" | |
| # Kiểm tra file swap đã tồn tại | |
| if [ -f "$SWAP_FILE" ]; then | |
| print_warning "File swap đã tồn tại tại $SWAP_FILE" | |
| read -p "Xóa và tạo lại? (y/n): " RECREATE_SWAP | |
| if [[ "$RECREATE_SWAP" =~ ^[Yy]$ ]]; then | |
| swapoff "$SWAP_FILE" 2>/dev/null || true | |
| rm -f "$SWAP_FILE" | |
| else | |
| print_status "Giữ nguyên swap hiện tại" | |
| return 0 | |
| fi | |
| fi | |
| print_status "Đang tạo swap file ${SWAP_SIZE_MB}MB..." | |
| # Tạo swap file | |
| dd if=/dev/zero of="$SWAP_FILE" bs=1M count="$SWAP_SIZE_MB" status=progress 2>/dev/null || \ | |
| dd if=/dev/zero of="$SWAP_FILE" bs=1M count="$SWAP_SIZE_MB" 2>/dev/null | |
| # Set quyền đúng (bảo mật) | |
| chmod 600 "$SWAP_FILE" | |
| # Tạo swap area | |
| mkswap "$SWAP_FILE" > /dev/null | |
| # Kích hoạt swap | |
| swapon "$SWAP_FILE" | |
| # Thêm vào fstab để persistent sau reboot | |
| if ! grep -q "$SWAP_FILE" /etc/fstab; then | |
| echo "$SWAP_FILE none swap sw 0 0" >> /etc/fstab | |
| fi | |
| # Tối ưu swappiness (khuyến nghị 10-20 cho VPS/Server) | |
| # Swappiness thấp = ưu tiên dùng RAM, ít swap hơn | |
| SWAPPINESS=10 | |
| if grep -q "^vm.swappiness" /etc/sysctl.conf; then | |
| sed -i "s/^vm.swappiness.*/vm.swappiness = $SWAPPINESS/" /etc/sysctl.conf | |
| else | |
| echo "" >> /etc/sysctl.conf | |
| echo "# Swap Configuration" >> /etc/sysctl.conf | |
| echo "vm.swappiness = $SWAPPINESS" >> /etc/sysctl.conf | |
| fi | |
| # Áp dụng swappiness ngay | |
| sysctl vm.swappiness=$SWAPPINESS > /dev/null | |
| # Cấu hình vfs_cache_pressure (khuyến nghị 50 cho VPS) | |
| # Giảm xu hướng kernel cache bộ nhớ của filesystem | |
| if ! grep -q "^vm.vfs_cache_pressure" /etc/sysctl.conf; then | |
| echo "vm.vfs_cache_pressure = 50" >> /etc/sysctl.conf | |
| fi | |
| sysctl vm.vfs_cache_pressure=50 > /dev/null | |
| print_status "Swap đã được thiết lập thành công!" | |
| echo " - Kích thước: ${SWAP_SIZE_MB}MB" | |
| echo " - Swappiness: $SWAPPINESS (ưu tiên RAM)" | |
| echo " - Location: $SWAP_FILE" | |
| echo "" | |
| # Hiển thị thông tin swap hiện tại | |
| print_status "Thông tin swap hiện tại:" | |
| free -h | grep -E "Mem:|Swap:" | |
| } | |
| # Vô hiệu hóa các dịch vụ không cần thiết | |
| disable_unused_services() { | |
| print_status "Đang kiểm tra các dịch vụ không cần thiết..." | |
| SERVICES_TO_DISABLE=("bluetooth" "cups" "avahi-daemon") | |
| for service in "${SERVICES_TO_DISABLE[@]}"; do | |
| if systemctl is-enabled "$service" &>/dev/null; then | |
| systemctl disable "$service" &>/dev/null || true | |
| systemctl stop "$service" &>/dev/null || true | |
| print_status "Đã tắt dịch vụ: $service" | |
| fi | |
| done | |
| } | |
| # Lưu thông tin | |
| save_info() { | |
| print_status "Đang lưu thông tin vào file..." | |
| cat > "$INFO_FILE" << EOF | |
| ================================ | |
| VPS SECURITY SETUP INFORMATION | |
| ================================ | |
| Ngày thiết lập: $(date) | |
| Hệ điều hành: $NAME $VERSION | |
| USER INFORMATION | |
| ---------------- | |
| Username: $NEW_USER | |
| Password: $NEW_PASSWORD | |
| SSH CONFIGURATION | |
| ----------------- | |
| SSH Port: $SSH_PORT | |
| SSH Private Key Path: $SSH_PRIVATE_KEY_PATH | |
| CONNECTION COMMAND | |
| ------------------ | |
| ssh -i $SSH_PRIVATE_KEY_PATH -p $SSH_PORT $NEW_USER@YOUR_SERVER_IP | |
| SSH PUBLIC KEY | |
| -------------- | |
| $SSH_PUBLIC_KEY | |
| SWAP CONFIGURATION | |
| ------------------ | |
| Swap Status: $(free -h | grep Swap | awk '{print $2}' | grep -q "^0" && echo "Not configured" || echo "Configured") | |
| Swap Size: $(free -h | grep Swap | awk '{print $2}') | |
| Swappiness: $(sysctl -n vm.swappiness 2>/dev/null || echo "N/A") | |
| IMPORTANT NOTES | |
| --------------- | |
| 1. Lưu private key ($SSH_PRIVATE_KEY_PATH) vào máy tính của bạn | |
| 2. Thay đổi quyền: chmod 600 /path/to/private_key | |
| 3. Port SSH mới: $SSH_PORT | |
| 4. Root login đã bị vô hiệu hóa | |
| 5. Password authentication đã bị vô hiệu hóa | |
| 6. Chỉ có thể đăng nhập bằng SSH key | |
| SECURITY FEATURES ENABLED | |
| ------------------------- | |
| - SSH key authentication only | |
| - Custom SSH port | |
| - Firewall (UFW/FirewallD) | |
| - Fail2ban | |
| - Automatic security updates | |
| - Kernel hardening | |
| - Swap memory configured | |
| - Root login disabled | |
| ================================ | |
| LƯU Ý QUAN TRỌNG: Sao lưu file này và private key trước khi reboot! | |
| ================================ | |
| EOF | |
| chmod 600 "$INFO_FILE" | |
| print_status "Thông tin đã được lưu vào: $INFO_FILE" | |
| } | |
| # Hiển thị thông tin | |
| display_info() { | |
| echo "" | |
| echo "========================================" | |
| echo " THIẾT LẬP BẢO MẬT HOÀN TẤT!" | |
| echo "========================================" | |
| echo "" | |
| cat "$INFO_FILE" | |
| echo "" | |
| echo "========================================" | |
| } | |
| # Reboot hệ thống | |
| reboot_system() { | |
| echo "" | |
| print_status "SSH đã được cấu hình và đang hoạt động trên port $SSH_PORT" | |
| print_status "Bạn có thể sử dụng hệ thống ngay bây giờ mà không cần reboot" | |
| echo "" | |
| read -p "Bạn có muốn reboot hệ thống để hoàn tất? (khuyến nghị) (y/n): " CONFIRM_REBOOT | |
| if [[ "$CONFIRM_REBOOT" =~ ^[Yy]$ ]]; then | |
| print_warning "Hệ thống sẽ reboot sau 10 giây..." | |
| print_warning "Hãy chắc chắn bạn đã:" | |
| print_warning " - Lưu file thông tin: $INFO_FILE" | |
| print_warning " - Lưu private key: $SSH_PRIVATE_KEY_PATH" | |
| print_warning " - Test kết nối SSH mới thành công" | |
| echo "" | |
| print_status "Sau khi reboot, kết nối bằng:" | |
| echo -e "${GREEN}ssh -i $SSH_PRIVATE_KEY_PATH -p $SSH_PORT $NEW_USER@YOUR_SERVER_IP${NC}" | |
| sleep 10 | |
| reboot | |
| else | |
| echo "" | |
| print_status "Thiết lập hoàn tất! SSH đang hoạt động bình thường." | |
| print_warning "Khuyến nghị reboot hệ thống khi thuận tiện để áp dụng tất cả kernel updates" | |
| echo "" | |
| print_status "Để kết nối SSH:" | |
| echo -e "${GREEN}ssh -i $SSH_PRIVATE_KEY_PATH -p $SSH_PORT $NEW_USER@YOUR_SERVER_IP${NC}" | |
| fi | |
| } | |
| # Main function | |
| main() { | |
| echo "========================================" | |
| echo " VPS Security Hardening Script" | |
| echo "========================================" | |
| echo "" | |
| detect_os | |
| detect_ssh_mode | |
| get_user_info | |
| echo "" | |
| print_warning "Script sẽ thực hiện các thay đổi quan trọng đến hệ thống!" | |
| read -p "Bạn có chắc chắn muốn tiếp tục? (y/n): " CONFIRM | |
| if [[ ! "$CONFIRM" =~ ^[Yy]$ ]]; then | |
| print_error "Đã hủy bỏ" | |
| exit 1 | |
| fi | |
| echo "" | |
| update_system | |
| create_user | |
| setup_ssh_key | |
| configure_ssh | |
| restart_ssh | |
| setup_firewall | |
| setup_fail2ban | |
| install_security_tools | |
| kernel_hardening | |
| setup_swap | |
| disable_unused_services | |
| save_info | |
| display_info | |
| reboot_system | |
| } | |
| # Chạy script | |
| main |
Author
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
curl -sSL https://gist.githubusercontent.com/anhvandev/23c4f7504bf7aec8f1fb854facb36030/raw/50d8fbee6dffc13e267be600bb583f6b290cd332/secure_vps.sh -o secure_vps.sh && chmod +x secure_vps.sh && bash secure_vps.sh