--- # Gitea fail2ban Configuration - Rick-Infra # Mode-aware: Only protects dedicated mode (port 2222) # In passthrough mode, system 'sshd' jail protects port 22 - name: Install fail2ban pacman: name: fail2ban state: present - name: Create Gitea fail2ban filter copy: content: | # Fail2ban filter for Gitea SSH authentication failures # Rick-Infra: Gitea role # Only used in dedicated mode (port {{ gitea_ssh_port }}) [Definition] # Match failed authentication attempts in Gitea logs failregex = .*(Failed authentication attempt|authentication failed|Invalid user|Failed login attempt).*from\s+ .*level=warning.*msg=.*authentication.*failed.*ip= ignoreregex = dest: /etc/fail2ban/filter.d/gitea-ssh.conf mode: '0644' backup: yes notify: restart fail2ban - name: Ensure fail2ban jail.local exists file: path: /etc/fail2ban/jail.local state: touch mode: '0644' modification_time: preserve access_time: preserve - name: Add Gitea SSH jail to fail2ban (mode-aware) blockinfile: path: /etc/fail2ban/jail.local marker: "# {mark} ANSIBLE MANAGED BLOCK - Gitea SSH" block: | # Gitea SSH Protection - Rick-Infra # Mode: {{ gitea_ssh_mode }} # - dedicated: Monitors Gitea logs on port {{ gitea_ssh_port }} # - passthrough: Disabled (system 'sshd' jail protects port 22) [gitea-ssh] enabled = {{ 'true' if gitea_ssh_mode == 'dedicated' else 'false' }} port = {{ gitea_ssh_port }} filter = gitea-ssh logpath = {{ gitea_home }}/log/gitea.log maxretry = 5 findtime = 600 bantime = 3600 banaction = nftables backup: yes notify: restart fail2ban - name: Enable and start fail2ban service systemd: name: fail2ban enabled: yes state: started - name: Flush handlers to ensure fail2ban restarts meta: flush_handlers - name: Wait for fail2ban to be ready pause: seconds: 2 - name: Verify gitea-ssh jail status (dedicated mode only) command: fail2ban-client status gitea-ssh register: gitea_jail_verify changed_when: false failed_when: false when: gitea_ssh_mode == 'dedicated' - name: Verify sshd jail status (passthrough mode) command: fail2ban-client status sshd register: sshd_jail_verify changed_when: false failed_when: false when: gitea_ssh_mode == 'passthrough' - name: Display fail2ban configuration status debug: msg: | 🛡️ fail2ban Protection for Gitea SSH ━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━ 📍 Mode: {{ gitea_ssh_mode | upper }} {% if gitea_ssh_mode == 'dedicated' %} 📍 Jail: gitea-ssh 📍 Port: {{ gitea_ssh_port }} 📍 Status: {{ 'Active ✅' if gitea_jail_verify.rc == 0 else 'Not Active ⚠️' }} 📍 Filter: /etc/fail2ban/filter.d/gitea-ssh.conf 📍 Logfile: {{ gitea_home }}/log/gitea.log Protection Settings: • Max retries: 5 attempts • Find time: 10 minutes (600 seconds) • Ban time: 1 hour (3600 seconds) Check status: fail2ban-client status gitea-ssh {% else %} 📍 Jail: sshd (system jail) 📍 Port: 22 📍 Status: {{ 'Active ✅' if sshd_jail_verify.rc == 0 else 'Not Active ⚠️' }} 📍 Coverage: All SSH traffic including Gitea Git operations Note: In passthrough mode, the system 'sshd' jail automatically protects all SSH traffic on port 22, including Gitea Git operations. No separate gitea-ssh jail is needed. Check status: fail2ban-client status sshd {% endif %} # Rick-Infra: Self-contained fail2ban protection per role