Остання активність 1 month ago

Версія 2fd1867af61be7cdd9a4c2f99e22892a135028b6

server_harden.sh Неформатований
1#!/bin/bash
2
3
4
5################################################################################
6
7# 服务器自动化加固脚本
8
9# 作者: Mercas
10
11# 日期: 2025-11-09
12
13# 说明: 本脚本用于自动化加固Ubuntu 22.04服务器安全配置
14
15# 版本: v1.4 (多选项菜单版 - 简化交互流程)
16
17# 新增功能:
18
19# - 全菜单式操作界面
20
21# - 模块化选择加固项目
22
23# - 预设配置选项
24
25# - 一键快速加固
26
27################################################################################
28
29
30
31# 终端类型兼容性处理
32
33if [[ "$TERM" == "xterm-kitty" ]]; then
34
35export TERM=xterm-color
36
37log_info "检测到xterm-kitty终端,已自动切换到xterm-color"
38
39elif [[ -z "$TERM" ]] || [[ "$TERM" == "unknown" ]]; then
40
41export TERM=xterm-color
42
43log_info "检测到未知终端类型,已设置为xterm-color"
44
45fi
46
47
48
49# 设置脚本使用的基本终端类型(避免颜色问题)
50
51export TERM=xterm-color
52
53
54
55# 禁用一些可能引起终端问题的选项
56
57set +H # 禁用历史扩展
58
59set +e # 暂时禁用错误退出
60
61
62
63set -e # 遇到错误立即退出
64
65trap 'echo "错误发生在第 $LINENO 行"' ERR
66
67
68
69# 颜色定义(使用更兼容的方式)
70
71if command -v tput &> /dev/null && [[ -n "$TERM" ]]; then
72
73RED=$(tput setaf 1 2>/dev/null || echo '\033[0;31m')
74
75GREEN=$(tput setaf 2 2>/dev/null || echo '\033[0;32m')
76
77YELLOW=$(tput setaf 3 2>/dev/null || echo '\033[1;33m')
78
79BLUE=$(tput setaf 4 2>/dev/null || echo '\033[0;34m')
80
81PURPLE=$(tput setaf 5 2>/dev/null || echo '\033[0;35m')
82
83CYAN=$(tput setaf 6 2>/dev/null || echo '\033[0;36m')
84
85NC=$(tput sgr0 2>/dev/null || echo '\033[0m')
86
87else
88
89# 回退到简单颜色
90
91RED='\033[0;31m'
92
93GREEN='\033[0;32m'
94
95YELLOW='\033[1;33m'
96
97BLUE='\033[0;34m'
98
99PURPLE='\033[0;35m'
100
101CYAN='\033[0;36m'
102
103NC='\033[0m'
104
105fi
106
107
108
109# 日志文件
110
111LOG_FILE="/var/log/server_hardening_$(date +%Y%m%d_%H%M%S).log"
112
113BACKUP_DIR="/root/security_backup_$(date +%Y%m%d_%H%M%S)"
114
115
116
117# 配置变量
118
119SSH_PORT=22
120
121ADMIN_USERNAME="admin"
122
123ENABLE_AUTO_REBOOT=true
124
125
126
127################################################################################
128
129# 工具函数
130
131################################################################################
132
133
134
135log() {
136
137echo -e "${GREEN}[$(date +'%Y-%m-%d %H:%M:%S')]${NC} $1" | tee -a "$LOG_FILE"
138
139}
140
141
142
143log_info() {
144
145echo -e "${BLUE}[INFO]${NC} $1" | tee -a "$LOG_FILE"
146
147}
148
149
150
151log_warning() {
152
153echo -e "${YELLOW}[WARNING]${NC} $1" | tee -a "$LOG_FILE"
154
155}
156
157
158
159log_error() {
160
161echo -e "${RED}[ERROR]${NC} $1" | tee -a "$LOG_FILE"
162
163}
164
165
166
167log_success() {
168
169echo -e "${GREEN}[SUCCESS]${NC} $1" | tee -a "$LOG_FILE"
170
171}
172
173
174
175log_section() {
176
177echo -e "\n${BLUE}========================================${NC}" | tee -a "$LOG_FILE"
178
179echo -e "${BLUE}$1${NC}" | tee -a "$LOG_FILE"
180
181echo -e "${BLUE}========================================${NC}\n" | tee -a "$LOG_FILE"
182
183}
184
185
186
187check_root() {
188
189if [[ $EUID -ne 0 ]]; then
190
191log_error "此脚本必须以root权限运行"
192
193exit 1
194
195fi
196
197}
198
199
200
201backup_file() {
202
203local file=$1
204
205if [[ -f "$file" ]]; then
206
207mkdir -p "$BACKUP_DIR"
208
209cp -p "$file" "$BACKUP_DIR/$(basename $file).bak" 2>/dev/null
210
211log_info "备份文件: $file -> $BACKUP_DIR/$(basename $file).bak"
212
213fi
214
215}
216
217
218
219safe_execute() {
220
221local cmd="$1"
222
223local description="$2"
224
225log_info "执行: $description"
226
227if eval "$cmd" >> "$LOG_FILE" 2>&1; then
228
229log_info "成功: $description"
230
231return 0
232
233else
234
235local exit_code=$?
236
237log_warning "警告: $description 失败 (退出码: $exit_code)"
238
239return $exit_code
240
241fi
242
243}
244
245
246
247# 菜单选择函数
248
249show_menu() {
250
251clear
252
253echo -e "${BLUE}"
254
255cat << "EOF"
256
257╔══════════════════════════════════════════════════════════════╗
258
259║ Ubuntu 22.04 服务器安全加固脚本 ║
260
261║ 多选项菜单版 (v1.4)
262
263║ 简化操作 • 模块选择 • 快速加固 ║
264
265╚══════════════════════════════════════════════════════════════╝
266
267EOF
268
269echo -e "${NC}"
270
271}
272
273
274
275show_main_menu() {
276
277show_menu
278
279echo -e "${CYAN}请选择加固模式:${NC}"
280
281echo ""
282
283echo -e "${GREEN}1)${NC} 快速加固 (推荐) - 关键安全工具 + 核心加固"
284
285echo -e "${GREEN}2)${NC} 自定义加固 - 逐项选择要应用的设置"
286
287echo -e "${GREEN}3)${NC} 系统更新 - 仅更新系统包"
288
289echo -e "${GREEN}4)${NC} 查看当前安全状态"
290
291echo -e "${GREEN}5)${NC} 退出"
292
293echo ""
294
295echo -e "${YELLOW}请输入选择 [1-5]: ${NC}\c"
296
297}
298
299
300
301get_menu_choice() {
302
303local min_choice=$1
304
305local max_choice=$2
306
307local choice
308
309while true; do
310
311read -p "" choice
312
313if [[ "$choice" =~ ^[0-9]+$ ]] && [[ "$choice" -ge "$min_choice" ]] && [[ "$choice" -le "$max_choice" ]]; then
314
315echo "$choice"
316
317return 0
318
319else
320
321echo -e "${RED}无效选择,请输入 $min_choice-$max_choice 之间的数字: ${NC}\c"
322
323fi
324
325done
326
327}
328
329
330
331show_custom_menu() {
332
333show_menu
334
335echo -e "${CYAN}自定义加固选项 (可多选):${NC}"
336
337echo ""
338
339echo -e "${GREEN}1)${NC} 系统更新和包管理"
340
341echo -e "${GREEN}2)${NC} SSH安全加固"
342
343echo -e "${GREEN}3)${NC} 创建管理用户和SSH密钥"
344
345echo -e "${GREEN}4)${NC} 配置防火墙 (UFW)"
346
347echo -e "${GREEN}5)${NC} 安装和配置Fail2ban"
348
349echo -e "${GREEN}6)${NC} 用户和权限管理"
350
351echo -e "${GREEN}7)${NC} 禁用不必要服务"
352
353echo -e "${GREEN}8)${NC} 内核参数安全配置"
354
355echo -e "${GREEN}9)${NC} 文件系统权限加固"
356
357echo -e "${GREEN}10)${NC} 配置自动安全更新"
358
359echo -e "${GREEN}11)${NC} 安装完整安全工具套件 (AIDE+Rkhunter+Logwatch+Auditd+Chkrootkit)"
360
361echo -e "${GREEN}12)${NC} 生成安全加固报告"
362
363echo -e "${GREEN}13)${NC} 返回主菜单"
364
365echo ""
366
367echo -e "${YELLOW}请输入要执行的项目编号 (多个用逗号分隔,如: 1,2,3): ${NC}\c"
368
369}
370
371
372
373show_security_status() {
374
375show_menu
376
377echo -e "${CYAN}当前系统安全状态检查:${NC}"
378
379echo ""
380
381# SSH状态
382
383echo -e "${YELLOW}SSH配置状态:${NC}"
384
385if [[ -f "/etc/ssh/sshd_config" ]]; then
386
387echo -e "${GREEN}${NC} SSH配置文件存在"
388
389echo " 端口: $(grep "^Port" /etc/ssh/sshd_config | awk '{print $2}' || echo "22 (默认)")"
390
391echo " Root登录: $(grep "^PermitRootLogin" /etc/ssh/sshd_config | awk '{print $2}' || echo "未明确配置")"
392
393echo " 密码认证: $(grep "^PasswordAuthentication" /etc/ssh/sshd_config | awk '{print $2}' || echo "未明确配置")"
394
395else
396
397echo -e "${RED}${NC} SSH配置文件不存在"
398
399fi
400
401echo ""
402
403# 防火墙状态
404
405echo -e "${YELLOW}防火墙状态:${NC}"
406
407if command -v ufw &> /dev/null; then
408
409if ufw status | grep -q "Status: active"; then
410
411echo -e "${GREEN}${NC} UFW防火墙已启用"
412
413ufw status | head -10
414
415else
416
417echo -e "${YELLOW}!${NC} UFW防火墙已安装但未启用"
418
419fi
420
421else
422
423echo -e "${RED}${NC} UFW防火墙未安装"
424
425fi
426
427echo ""
428
429# Fail2ban状态
430
431echo -e "${YELLOW}Fail2ban状态:${NC}"
432
433if command -v fail2ban-client &> /dev/null; then
434
435if systemctl is-active --quiet fail2ban; then
436
437echo -e "${GREEN}${NC} Fail2ban服务正在运行"
438
439fail2ban-client status 2>/dev/null | head -5
440
441else
442
443echo -e "${YELLOW}!${NC} Fail2ban已安装但未运行"
444
445fi
446
447else
448
449echo -e "${RED}${NC} Fail2ban未安装"
450
451fi
452
453echo ""
454
455# 系统用户
456
457echo -e "${YELLOW}系统用户管理:${NC}"
458
459local admin_users=$(grep -E ":(sudo|admin)" /etc/group | cut -d: -f4 | head -5)
460
461if [[ -n "$admin_users" ]]; then
462
463echo -e "${GREEN}${NC} 管理员用户: $admin_users"
464
465else
466
467echo -e "${YELLOW}!${NC} 未检测到管理用户组"
468
469fi
470
471echo ""
472
473echo -e "${CYAN}按回车键返回主菜单...${NC}"
474
475read
476
477}
478
479
480
481################################################################################
482
483# 主要加固功能
484
485################################################################################
486
487
488
489# 1. 系统信息收集
490
491collect_system_info() {
492
493log_section "收集系统信息"
494
495log_info "操作系统: $(lsb_release -d 2>/dev/null | cut -f2 || echo "Unknown")"
496
497log_info "内核版本: $(uname -r)"
498
499log_info "主机名: $(hostname)"
500
501# 安全获取IP地址
502
503local ip=$(hostname -I 2>/dev/null | awk '{print $1}' || echo "无法获取")
504
505log_info "IP地址: $ip"
506
507log_info "开始加固时间: $(date)"
508
509echo "系统信息收集完成" >> "$LOG_FILE"
510
511}
512
513
514
515# 2. 系统更新
516
517update_system() {
518
519log_section "系统更新与安全补丁"
520
521log_info "开始系统更新..."
522
523safe_execute "apt update -y" "更新软件包列表"
524
525safe_execute "apt upgrade -y" "升级已安装的软件包"
526
527safe_execute "apt dist-upgrade -y" "安装安全更新"
528
529safe_execute "apt autoremove -y" "清理不需要的软件包"
530
531safe_execute "apt autoclean -y" "清理缓存"
532
533log_success "系统更新完成"
534
535}
536
537
538
539# 3. SSH安全加固
540
541harden_ssh() {
542
543log_section "SSH安全加固"
544
545local ssh_config="/etc/ssh/sshd_config"
546
547if [[ -f "$ssh_config" ]]; then
548
549backup_file "$ssh_config"
550
551log_info "配置SSH安全参数..."
552
553# 应用预设配置
554
555safe_execute "sed -i 's/^#*PermitRootLogin.*/PermitRootLogin no/' '$ssh_config'" "禁用root登录"
556
557safe_execute "sed -i 's/^#*PasswordAuthentication.*/PasswordAuthentication no/' '$ssh_config'" "禁用密码认证"
558
559safe_execute "sed -i 's/^#*Port.*/Port $SSH_PORT/' '$ssh_config'" "设置SSH端口为$SSH_PORT"
560
561# 其他SSH安全配置
562
563local ssh_config_addition='
564
565# 安全加固配置
566
567Protocol 2
568
569MaxAuthTries 3
570
571MaxSessions 2
572
573LoginGraceTime 60
574
575ClientAliveInterval 300
576
577ClientAliveCountMax 2
578
579PermitEmptyPasswords no
580
581X11Forwarding no
582
583UseDNS no
584
585'
586
587echo "$ssh_config_addition" >> "$ssh_config"
588
589# 重启SSH服务
590
591safe_execute "systemctl restart sshd" "重启SSH服务"
592
593log_success "SSH加固完成 - 端口: $SSH_PORT, Root登录: 禁用, 密码认证: 禁用"
594
595log_warning "请确保已在防火墙中开放端口 $SSH_PORT"
596
597log_warning "请确保已配置SSH密钥认证"
598
599else
600
601log_error "SSH配置文件不存在: $ssh_config"
602
603fi
604
605}
606
607
608
609# 4. 用户管理和SSH密钥配置
610
611manage_users() {
612
613log_section "创建管理用户和配置SSH密钥"
614
615local username=$ADMIN_USERNAME
616
617local user_home=$(eval echo "~$username")
618
619# 检查用户是否已存在
620
621if id "$username" &>/dev/null 2>&1; then
622
623log_info "用户 $username 已存在,跳过创建"
624
625else
626
627# 创建用户
628
629log_info "创建用户: $username"
630
631safe_execute "useradd -m -s /bin/bash '$username'" "创建用户 $username"
632
633# 设置随机密码
634
635local temp_password=$(openssl rand -base64 32)
636
637echo "$username:$temp_password" | chpasswd
638
639log_success "用户 $username 创建成功"
640
641log_info "临时密码: $temp_password (建议首次登录后修改)"
642
643# 将用户添加到sudo组
644
645safe_execute "usermod -aG sudo '$username'" "$username 添加到sudo组"
646
647fi
648
649# 配置SSH密钥
650
651local ssh_dir="$user_home/.ssh"
652
653local authorized_keys="$ssh_dir/authorized_keys"
654
655# 确保用户有.ssh目录
656
657mkdir -p "$ssh_dir"
658
659chown "$username:$username" "$ssh_dir"
660
661# 生成SSH密钥对
662
663log_info "生成SSH密钥对..."
664
665cd "$user_home"
666
667if [[ ! -f "$ssh_dir/id_rsa" ]]; then
668
669su - "$username" -c "ssh-keygen -t rsa -b 4096 -f $ssh_dir/id_rsa -N '' -C '$username@$(hostname)'"
670
671if [[ -f "$ssh_dir/id_rsa" ]]; then
672
673log_success "SSH密钥对生成成功"
674
675log_info "私钥文件: $ssh_dir/id_rsa"
676
677log_info "公钥文件: $ssh_dir/id_rsa.pub"
678
679log_warning "请妥善保管私钥文件,不要上传到公共服务器"
680
681# 设置公钥到authorized_keys
682
683cat "$ssh_dir/id_rsa.pub" > "$authorized_keys"
684
685else
686
687log_error "SSH密钥生成失败"
688
689return 1
690
691fi
692
693else
694
695log_info "SSH密钥已存在"
696
697fi
698
699# 设置sudo无密码
700
701local sudoers_file="/etc/sudoers.d/$username"
702
703echo "$username ALL=(ALL) NOPASSWD:ALL" > "$sudoers_file"
704
705chmod 440 "$sudoers_file"
706
707log_success "已配置 $username sudo无密码权限"
708
709# 设置文件权限
710
711safe_execute "chown -R $username:$username '$ssh_dir'" "设置SSH目录权限"
712
713safe_execute "chmod 700 '$ssh_dir'" "设置SSH目录权限为700"
714
715safe_execute "chmod 600 '$authorized_keys'" "设置公钥文件权限为600"
716
717log_success "用户管理完成 - 用户: $username"
718
719}
720
721
722
723# 5. 防火墙配置
724
725configure_firewall() {
726
727log_section "配置UFW防火墙"
728
729if ! command -v ufw &> /dev/null; then
730
731safe_execute "apt install ufw -y" "安装UFW"
732
733fi
734
735log_info "配置UFW规则..."
736
737# 默认策略
738
739safe_execute "ufw default deny incoming" "设置默认入站策略:拒绝"
740
741safe_execute "ufw default allow outgoing" "设置默认出站策略:允许"
742
743# 允许SSH
744
745safe_execute "ufw allow $SSH_PORT/tcp comment 'SSH'" "允许SSH端口: $SSH_PORT"
746
747# 允许常用端口
748
749local common_ports=("80/tcp" "443/tcp" "53/udp" "123/udp")
750
751local port_comments=("HTTP" "HTTPS" "DNS" "NTP")
752
753for i in "${!common_ports[@]}"; do
754
755log_info "开放端口 ${common_ports[$i]} (${port_comments[$i]})"
756
757safe_execute "ufw allow ${common_ports[$i]} comment '${port_comments[$i]}'" "开放${port_comments[$i]}端口"
758
759done
760
761# 启用UFW
762
763log_info "启用UFW防火墙..."
764
765safe_execute "ufw --force enable" "强制启用UFW"
766
767# 显示状态
768
769log_success "防火墙配置完成"
770
771ufw status | head -15
772
773}
774
775
776
777# 6. 安装和配置Fail2ban
778
779install_fail2ban() {
780
781log_section "安装和配置Fail2ban"
782
783if ! command -v fail2ban-client &> /dev/null; then
784
785safe_execute "apt install fail2ban -y" "安装Fail2ban"
786
787else
788
789log_info "Fail2ban已安装"
790
791fi
792
793# 配置fail2ban
794
795local jail_local="/etc/fail2ban/jail.local"
796
797backup_file "$jail_local" 2>/dev/null || true
798
799log_info "创建Fail2ban配置..."
800
801cat > "$jail_local" << EOF
802
803[DEFAULT]
804
805# 封禁时间(秒)
806
807bantime = 3600
808
809
810
811# 查找时间窗口(秒)
812
813findtime = 600
814
815
816
817# 最大尝试次数
818
819maxretry = 5
820
821
822
823[sshd]
824
825enabled = true
826
827port = $SSH_PORT
828
829filter = sshd
830
831logpath = /var/log/auth.log
832
833maxretry = 3
834
835bantime = 7200
836
837
838
839[sshd-ddos]
840
841enabled = true
842
843port = $SSH_PORT
844
845filter = sshd-ddos
846
847logpath = /var/log/auth.log
848
849maxretry = 2
850
851bantime = 7200
852
853EOF
854
855safe_execute "systemctl enable fail2ban" "启用Fail2ban服务"
856
857safe_execute "systemctl restart fail2ban" "重启Fail2ban服务"
858
859sleep 2
860
861if command -v fail2ban-client &> /dev/null; then
862
863log_success "Fail2ban配置完成"
864
865fail2ban-client status 2>/dev/null | head -5
866
867fi
868
869}
870
871
872
873# 7. 用户和权限管理
874
875harden_users() {
876
877log_section "用户和权限加固"
878
879# 密码策略
880
881log_info "配置密码策略..."
882
883if ! dpkg -l | grep -q libpam-pwquality; then
884
885safe_execute "apt install libpam-pwquality -y" "安装密码质量检查工具"
886
887fi
888
889local pwquality_file="/etc/security/pwquality.conf"
890
891backup_file "$pwquality_file"
892
893cat >> "$pwquality_file" << 'EOF'
894
895
896
897# 密码安全策略
898
899minlen = 12
900
901dcredit = -1
902
903ucredit = -1
904
905lcredit = -1
906
907ocredit = -1
908
909maxrepeat = 3
910
911EOF
912
913# 密码过期策略
914
915local login_defs="/etc/login.defs"
916
917if [[ -f "$login_defs" ]]; then
918
919backup_file "$login_defs"
920
921safe_execute "sed -i 's/^PASS_MAX_DAYS.*/PASS_MAX_DAYS 90/' '$login_defs'" "设置密码最大有效期"
922
923safe_execute "sed -i 's/^PASS_MIN_DAYS.*/PASS_MIN_DAYS 1/' '$login_defs'" "设置密码最小间隔"
924
925safe_execute "sed -i 's/^PASS_WARN_AGE.*/PASS_WARN_AGE 14/' '$login_defs'" "设置密码警告时间"
926
927fi
928
929log_success "密码策略配置完成"
930
931# 锁定不必要的系统账户
932
933log_info "锁定系统账户..."
934
935local system_users=("bin" "daemon" "adm" "lp" "sync" "shutdown" "halt" "mail" "news" "uucp" "operator" "games" "gopher" "ftp")
936
937for user in "${system_users[@]}"; do
938
939if id "$user" &>/dev/null 2>&1; then
940
941usermod -L -s /usr/sbin/nologin "$user" 2>/dev/null || true
942
943fi
944
945done
946
947log_success "用户加固完成"
948
949}
950
951
952
953# 8. 禁用不必要的服务
954
955disable_services() {
956
957log_section "禁用不必要的服务"
958
959local services_to_disable=("avahi-daemon" "cups" "isc-dhcp-server" "isc-dhcp-server6" "bluetooth")
960
961for service in "${services_to_disable[@]}"; do
962
963if systemctl is-enabled "$service" &>/dev/null 2>&1; then
964
965safe_execute "systemctl stop '$service'" "停止服务: $service"
966
967safe_execute "systemctl disable '$service'" "禁用服务: $service"
968
969log_info "已禁用服务: $service"
970
971fi
972
973done
974
975log_success "不必要服务禁用完成"
976
977}
978
979
980
981# 9. 内核参数安全配置
982
983harden_kernel() {
984
985log_section "内核参数安全配置"
986
987local sysctl_conf="/etc/sysctl.d/99-security.conf"
988
989backup_file "$sysctl_conf" 2>/dev/null || true
990
991log_info "配置内核安全参数..."
992
993cat > "$sysctl_conf" << 'EOF'
994
995# IP转发禁用
996
997net.ipv4.ip_forward = 0
998
999net.ipv6.conf.all.forwarding = 0
1000
1001
1002
1003# SYN cookies保护
1004
1005net.ipv4.tcp_syncookies = 1
1006
1007
1008
1009# 忽略ICMP重定向
1010
1011net.ipv4.conf.all.accept_redirects = 0
1012
1013net.ipv6.conf.all.accept_redirects = 0
1014
1015net.ipv4.conf.default.accept_redirects = 0
1016
1017net.ipv6.conf.default.accept_redirects = 0
1018
1019
1020
1021# 忽略安全ICMP重定向
1022
1023net.ipv4.conf.all.secure_redirects = 0
1024
1025net.ipv4.conf.default.secure_redirects = 0
1026
1027
1028
1029# 禁用源路由
1030
1031net.ipv4.conf.all.accept_source_route = 0
1032
1033net.ipv6.conf.all.accept_source_route = 0
1034
1035net.ipv4.conf.default.accept_source_route = 0
1036
1037net.ipv6.conf.default.accept_source_route = 0
1038
1039
1040
1041# 记录可疑包
1042
1043net.ipv4.conf.all.log_martians = 1
1044
1045net.ipv4.conf.default.log_martians = 1
1046
1047
1048
1049# 忽略ICMP ping请求
1050
1051net.ipv4.icmp_echo_ignore_broadcasts = 1
1052
1053
1054
1055# 反向路径过滤
1056
1057net.ipv4.conf.all.rp_filter = 1
1058
1059net.ipv4.conf.default.rp_filter = 1
1060
1061
1062
1063# 保护系统免受SYN flood攻击
1064
1065net.ipv4.tcp_max_syn_backlog = 2048
1066
1067net.ipv4.tcp_synack_retries = 2
1068
1069net.ipv4.tcp_syn_retries = 5
1070
1071EOF
1072
1073if command -v sysctl &> /dev/null; then
1074
1075safe_execute "sysctl -p '$sysctl_conf'" "应用内核参数配置"
1076
1077fi
1078
1079log_success "内核参数配置完成"
1080
1081}
1082
1083
1084
1085# 10. 文件系统和权限加固
1086
1087harden_filesystem() {
1088
1089log_section "文件系统权限加固"
1090
1091log_info "设置重要文件权限..."
1092
1093# 关键配置文件权限
1094
1095local files_to_protect=(
1096
1097"/etc/ssh/sshd_config:600"
1098
1099"/etc/passwd:644"
1100
1101"/etc/shadow:640"
1102
1103"/etc/group:644"
1104
1105"/etc/gshadow:600"
1106
1107)
1108
1109for file_perm in "${files_to_protect[@]}"; do
1110
1111local file="${file_perm%:*}"
1112
1113local perm="${file_perm#*:}"
1114
1115if [[ -f "$file" ]]; then
1116
1117safe_execute "chmod $perm '$file'" "设置文件权限: $file -> $perm"
1118
1119fi
1120
1121done
1122
1123log_success "重要文件权限已加固"
1124
1125# 查找并报告可疑权限文件
1126
1127log_info "查找具有SUID/SGID权限的文件(记录到日志)..."
1128
1129if command -v find &> /dev/null; then
1130
1131find / -perm /6000 -type f 2>/dev/null >> "$LOG_FILE" || true
1132
1133fi
1134
1135}
1136
1137
1138
1139# 11. 配置自动安全更新
1140
1141configure_auto_updates() {
1142
1143log_section "配置自动安全更新"
1144
1145if ! dpkg -l | grep -q unattended-upgrades; then
1146
1147safe_execute "apt install unattended-upgrades apt-listchanges -y" "安装自动更新工具"
1148
1149fi
1150
1151if command -v dpkg-reconfigure &> /dev/null; then
1152
1153safe_execute "echo unattended-upgrades unattended-upgrades/enable_auto_updates boolean true | debconf-set-selections && debconf-show unattended-upgrades" "配置自动更新"
1154
1155fi
1156
1157log_success "自动安全更新已启用"
1158
1159}
1160
1161
1162
1163# 12. 安装其他安全工具
1164
1165install_security_tools() {
1166
1167log_section "安装额外安全工具"
1168
1169# 优先级安全工具 - 快速加固中最重要的
1170
1171local priority_tools=("aide" "rkhunter")
1172
1173# 完整的工具列表 - 自定义模式中可选择
1174
1175local all_tools=("aide" "rkhunter" "logwatch" "auditd" "chkrootkit")
1176
1177# 智能选择 - 根据加固模式选择工具
1178
1179local tools=()
1180
1181if [[ "${INSTALL_MODE:-full}" == "priority" ]]; then
1182
1183tools=("${priority_tools[@]}")
1184
1185log_info "快速加固模式: 安装关键安全工具"
1186
1187else
1188
1189tools=("${all_tools[@]}")
1190
1191log_info "完整安装模式: 安装所有推荐安全工具"
1192
1193fi
1194
1195for tool in "${tools[@]}"; do
1196
1197if apt list --installed 2>/dev/null | grep -q "^$tool/"; then
1198
1199log_info "$tool 已安装"
1200
1201continue
1202
1203fi
1204
1205# 智能安装 - 跳过可能的不可用工具
1206
1207case "$tool" in
1208
1209"auditd")
1210
1211if ! dpkg -l | grep -q "auditd"; then
1212
1213if safe_execute "apt install '$tool' -y" "安装安全工具: $tool"; then
1214
1215safe_execute "systemctl enable auditd" "启用auditd服务"
1216
1217safe_execute "systemctl start auditd" "启动auditd服务"
1218
1219log_success "已安装并启用: $tool"
1220
1221else
1222
1223log_warning "跳过 $tool 安装"
1224
1225fi
1226
1227fi
1228
1229;;
1230
1231"chkrootkit")
1232
1233if safe_execute "apt install '$tool' -y" "安装安全工具: $tool"; then
1234
1235log_success "已安装: $tool"
1236
1237else
1238
1239log_warning "跳过 $tool 安装"
1240
1241fi
1242
1243;;
1244
1245*)
1246
1247if safe_execute "apt install '$tool' -y" "安装安全工具: $tool"; then
1248
1249# 特殊配置
1250
1251case "$tool" in
1252
1253"rkhunter")
1254
1255if command -v rkhunter &> /dev/null; then
1256
1257safe_execute "rkhunter --update" "更新rkhunter数据库"
1258
1259safe_execute "rkhunter --propupd" "更新rkhunter属性"
1260
1261fi
1262
1263;;
1264
1265esac
1266
1267log_success "已安装: $tool"
1268
1269else
1270
1271log_warning "跳过 $tool 安装"
1272
1273fi
1274
1275;;
1276
1277esac
1278
1279done
1280
1281# 显示安装总结
1282
1283log_info "安全工具安装总结:"
1284
1285for tool in "${tools[@]}"; do
1286
1287if command -v "$tool" &>/dev/null; then
1288
1289log_success "$tool - 已安装"
1290
1291else
1292
1293log_info "- $tool - 跳过或安装失败"
1294
1295fi
1296
1297done
1298
1299}
1300
1301
1302
1303# 13. 生成加固报告
1304
1305generate_report() {
1306
1307log_section "生成安全加固报告"
1308
1309local report_file="/root/security_hardening_report_$(date +%Y%m%d_%H%M%S).txt"
1310
1311# 安全获取系统信息
1312
1313local os_info=$(lsb_release -d 2>/dev/null | cut -f2 || echo "Unknown")
1314
1315local kernel_info=$(uname -r)
1316
1317local hostname_info=$(hostname)
1318
1319cat > "$report_file" << EOF
1320
1321================================================================================
1322
1323服务器安全加固报告
1324
1325================================================================================
1326
1327生成时间: $(date)
1328
1329主机名: $hostname_info
1330
1331操作系统: $os_info
1332
1333内核版本: $kernel_info
1334
1335
1336
1337--------------------------------------------------------------------------------
1338
13391. SSH配置
1340
1341--------------------------------------------------------------------------------
1342
1343$(grep -E "^(Port|PermitRootLogin|PasswordAuthentication)" /etc/ssh/sshd_config 2>/dev/null || echo "SSH配置不可读")
1344
1345
1346
1347--------------------------------------------------------------------------------
1348
13492. 防火墙状态
1350
1351--------------------------------------------------------------------------------
1352
1353$(ufw status verbose 2>/dev/null || echo "UFW不可用")
1354
1355
1356
1357--------------------------------------------------------------------------------
1358
13593. Fail2ban状态
1360
1361--------------------------------------------------------------------------------
1362
1363$(fail2ban-client status 2>/dev/null || echo "Fail2ban未运行")
1364
1365
1366
1367--------------------------------------------------------------------------------
1368
13694. 已安装的安全工具
1370
1371--------------------------------------------------------------------------------
1372
1373$(dpkg -l 2>/dev/null | grep -E "fail2ban|ufw|aide|rkhunter|logwatch|unattended-upgrades" | awk '{print $2 " " $3}' | column -t || echo "无法获取包信息")
1374
1375
1376
1377--------------------------------------------------------------------------------
1378
13795. 活动监听端口
1380
1381--------------------------------------------------------------------------------
1382
1383$(ss -tunlp 2>/dev/null || netstat -tunlp 2>/dev/null || echo "端口信息不可用")
1384
1385
1386
1387--------------------------------------------------------------------------------
1388
13896. 管理用户
1390
1391--------------------------------------------------------------------------------
1392
1393$(grep -E ":(sudo|admin)" /etc/group 2>/dev/null | head -5 || echo "无管理用户组")
1394
1395
1396
1397--------------------------------------------------------------------------------
1398
1399备份目录: $BACKUP_DIR
1400
1401日志文件: $LOG_FILE
1402
1403配置完成时间: $(date)
1404
1405--------------------------------------------------------------------------------
1406
1407EOF
1408
1409log_success "安全加固报告已生成: $report_file"
1410
1411# 显示报告摘要
1412
1413echo -e "${CYAN}报告摘要:${NC}"
1414
1415echo "- 操作系统: $os_info"
1416
1417echo "- SSH端口: $SSH_PORT"
1418
1419echo "- 管理员用户: $ADMIN_USERNAME"
1420
1421echo "- 防火墙: $(ufw status 2>/dev/null | grep -q "active" && echo "已启用" || echo "未启用")"
1422
1423echo "- Fail2ban: $(systemctl is-active fail2ban 2>/dev/null || echo "未运行")"
1424
1425echo ""
1426
1427echo -e "${YELLOW}完整报告请查看: $report_file${NC}"
1428
1429}
1430
1431
1432
1433################################################################################
1434
1435# 快速加固流程
1436
1437################################################################################
1438
1439
1440
1441quick_hardening() {
1442
1443log_section "开始快速加固"
1444
1445log_warning "这将应用所有推荐的安全设置"
1446
1447# 设置快速加固模式 - 优先安装关键安全工具
1448
1449export INSTALL_MODE="priority"
1450
1451# 执行所有加固步骤
1452
1453collect_system_info
1454
1455update_system
1456
1457harden_ssh
1458
1459manage_users
1460
1461configure_firewall
1462
1463install_fail2ban
1464
1465harden_users
1466
1467disable_services
1468
1469harden_kernel
1470
1471harden_filesystem
1472
1473configure_auto_updates
1474
1475install_security_tools
1476
1477generate_report
1478
1479log_section "快速加固完成"
1480
1481show_completion_message
1482
1483}
1484
1485
1486
1487################################################################################
1488
1489# 自定义加固流程
1490
1491################################################################################
1492
1493
1494
1495custom_hardening() {
1496
1497while true; do
1498
1499show_custom_menu
1500
1501local choice=$(get_menu_choice 1 13)
1502
1503case $choice in
1504
15051)
1506
1507collect_system_info
1508
1509update_system
1510
1511;;
1512
15132)
1514
1515show_ssh_config_menu
1516
1517;;
1518
15193)
1520
1521show_user_config_menu
1522
1523;;
1524
15254)
1526
1527configure_firewall
1528
1529;;
1530
15315)
1532
1533install_fail2ban
1534
1535;;
1536
15376)
1538
1539harden_users
1540
1541;;
1542
15437)
1544
1545disable_services
1546
1547;;
1548
15498)
1550
1551harden_kernel
1552
1553;;
1554
15559)
1556
1557harden_filesystem
1558
1559;;
1560
156110)
1562
1563configure_auto_updates
1564
1565;;
1566
156711)
1568
1569export INSTALL_MODE="full"
1570
1571install_security_tools
1572
1573;;
1574
157512)
1576
1577generate_report
1578
1579;;
1580
158113)
1582
1583return 0
1584
1585;;
1586
1587esac
1588
1589echo ""
1590
1591echo -e "${YELLOW}按回车键继续...${NC}"
1592
1593read
1594
1595done
1596
1597}
1598
1599
1600
1601show_ssh_config_menu() {
1602
1603show_menu
1604
1605echo -e "${CYAN}SSH配置选项:${NC}"
1606
1607echo ""
1608
1609echo -e "${GREEN}1)${NC} 标准配置 (端口2222, 禁用root, 禁用密码)"
1610
1611echo -e "${GREEN}2)${NC} 安全配置 (端口22, 禁用root, 禁用密码)"
1612
1613echo -e "${GREEN}3)${NC} 自定义端口 (输入端口号)"
1614
1615echo -e "${GREEN}4)${NC} 返回"
1616
1617echo ""
1618
1619echo -e "${YELLOW}请选择SSH配置 [1-4]: ${NC}\c"
1620
1621local ssh_choice=$(get_menu_choice 1 4)
1622
1623case $ssh_choice in
1624
16251)
1626
1627SSH_PORT=2222
1628
1629harden_ssh
1630
1631;;
1632
16332)
1634
1635SSH_PORT=22
1636
1637harden_ssh
1638
1639;;
1640
16413)
1642
1643echo -e "${YELLOW}请输入SSH端口号 (1024-65535): ${NC}\c"
1644
1645read -p "" custom_port
1646
1647if [[ "$custom_port" =~ ^[0-9]+$ ]] && [[ "$custom_port" -gt 1024 ]] && [[ "$custom_port" -lt 65536 ]]; then
1648
1649SSH_PORT=$custom_port
1650
1651harden_ssh
1652
1653else
1654
1655log_error "无效的端口号"
1656
1657fi
1658
1659;;
1660
16614)
1662
1663return 0
1664
1665;;
1666
1667esac
1668
1669}
1670
1671
1672
1673show_user_config_menu() {
1674
1675show_menu
1676
1677echo -e "${CYAN}用户管理配置选项:${NC}"
1678
1679echo ""
1680
1681echo -e "${GREEN}1)${NC} 创建admin用户 (推荐)"
1682
1683echo -e "${GREEN}2)${NC} 创建operator用户"
1684
1685echo -e "${GREEN}3)${NC} 自定义用户名"
1686
1687echo -e "${GREEN}4)${NC} 跳过用户创建"
1688
1689echo ""
1690
1691echo -e "${YELLOW}请选择用户配置 [1-4]: ${NC}\c"
1692
1693local user_choice=$(get_menu_choice 1 4)
1694
1695case $user_choice in
1696
16971)
1698
1699ADMIN_USERNAME="admin"
1700
1701manage_users
1702
1703;;
1704
17052)
1706
1707ADMIN_USERNAME="operator"
1708
1709manage_users
1710
1711;;
1712
17133)
1714
1715echo -e "${YELLOW}请输入用户名: ${NC}\c"
1716
1717read -p "" ADMIN_USERNAME
1718
1719if [[ -n "$ADMIN_USERNAME" ]] && [[ "$ADMIN_USERNAME" =~ ^[a-z_][a-z0-9_-]*$ ]]; then
1720
1721manage_users
1722
1723else
1724
1725log_error "无效的用户名"
1726
1727fi
1728
1729;;
1730
17314)
1732
1733log_info "跳过用户创建"
1734
1735;;
1736
1737esac
1738
1739}
1740
1741
1742
1743################################################################################
1744
1745# 完成消息
1746
1747################################################################################
1748
1749
1750
1751show_completion_message() {
1752
1753echo -e "${GREEN}"
1754
1755cat << EOF
1756
1757╔══════════════════════════════════════════════════════════════╗
1758
1759║ 安全加固已完成! ║
1760
1761╚══════════════════════════════════════════════════════════════╝
1762
1763
1764
1765重要提醒:
1766
17671. SSH访问信息:
1768
1769- 端口: $SSH_PORT
1770
1771- 用户: $ADMIN_USERNAME
1772
1773- 认证方式: SSH密钥 (推荐)
1774
17752. 文件位置:
1776
1777- 配置备份: $BACKUP_DIR
1778
1779- 详细日志: $LOG_FILE
1780
1781- 安全报告: /root/security_hardening_report_*.txt
1782
1783
1784
17853. 后续步骤:
1786
1787- 使用SSH密钥登录新用户账户
1788
1789- 验证防火墙规则: ufw status
1790
1791- 检查Fail2ban状态: fail2ban-client status
1792
1793- 重启服务器以确保所有更改生效
1794
1795
1796
17974. 安全检查:
1798
1799- 定期检查 /var/log/auth.log
1800
1801- 运行: rkhunter --check (如已安装)
1802
1803- 监控fail2ban日志: tail -f /var/log/fail2ban.log
1804
1805
1806
1807EOF
1808
1809echo -e "${NC}"
1810
1811if [[ "$ENABLE_AUTO_REBOOT" == "true" ]]; then
1812
1813echo -e "${YELLOW}是否重启服务器以确保所有更改生效?${NC}"
1814
1815echo -e "${GREEN}1)${NC} 是,立即重启"
1816
1817echo -e "${GREEN}2)${NC} 否,稍后手动重启"
1818
1819echo ""
1820
1821echo -e "${YELLOW}请选择 [1-2]: ${NC}\c"
1822
1823local reboot_choice=$(get_menu_choice 1 2)
1824
1825case $reboot_choice in
1826
18271)
1828
1829log "系统将在10秒后重启..."
1830
1831sleep 10
1832
1833if command -v reboot &> /dev/null; then
1834
1835reboot
1836
1837else
1838
1839shutdown -r now
1840
1841fi
1842
1843;;
1844
18452)
1846
1847log_info "请记得稍后手动重启服务器"
1848
1849;;
1850
1851esac
1852
1853fi
1854
1855}
1856
1857
1858
1859################################################################################
1860
1861# 主程序
1862
1863################################################################################
1864
1865
1866
1867main() {
1868
1869# 检查root权限
1870
1871check_root
1872
1873while true; do
1874
1875show_main_menu
1876
1877local choice=$(get_menu_choice 1 5)
1878
1879case $choice in
1880
18811)
1882
1883log "开始快速加固流程..."
1884
1885quick_hardening
1886
1887break
1888
1889;;
1890
18912)
1892
1893log "开始自定义加固流程..."
1894
1895custom_hardening
1896
1897;;
1898
18993)
1900
1901log "开始系统更新..."
1902
1903collect_system_info
1904
1905update_system
1906
1907echo ""
1908
1909echo -e "${YELLOW}按回车键返回主菜单...${NC}"
1910
1911read
1912
1913;;
1914
19154)
1916
1917show_security_status
1918
1919;;
1920
19215)
1922
1923log "退出脚本"
1924
1925exit 0
1926
1927;;
1928
1929esac
1930
1931done
1932
1933}
1934
1935
1936
1937# 运行主程序
1938
1939main "$@"
1940