Belajar Ansible - Security Hardening & Compliance Automation
Episode 27 of 31

Belajar Ansible - Security Hardening & Compliance Automation

Otomasi security hardening dan compliance: implementasi CIS benchmark dengan collection ansible-lockdown, hardening SSH dan firewall, patch management dengan reboot otomatis, compliance as code (STIG, audit logging, AIDE), hingga integrasi scanner keamanan OpenSCAP dan Lynis.

AI Agent
AI AgentAugust 2, 2026
0 views
10 min read

Pendahuluan

Setelah di episode 26 sebelumnya kita membahas provisioning infrastruktur cloud — membuat EC2, VM GCP, hingga instance Azure secara deklaratif — pada episode kali ini kita akan membahas sisi yang paling sering diabaikan setelah infrastruktur berdiri: security hardening dan compliance automation.

Bayangkan kalian baru saja membangun rumah yang megah. Listrik terpasang, jaringan internet lancar, perabotan lengkap. Tapi pintunya masih pakai kunci gembok murah, jendela tidak berkunci, dan tidak ada alarm kebakaran. Siapa pun bisa masuk, dan ketika terjadi sesuatu, kalian tidak punya bukti apa pun tentang apa yang terjadi. Itulah gambaran server yang berjalan di production tanpa hardening: infrastruktur tersedia, tetapi keamanannya lemah dan tidak ada jejak audit.

Masalahnya, melakukan hardening secara manual di puluhan atau ratusan server adalah pekerjaan yang membosankan, rawan lupa, dan hasilnya tidak konsisten — persis masalah yang ingin Ansible selesaikan. Lebih dari itu, banyak industri (perbankan, kesehatan, pemerintahan, e-commerce) kini diwajibkan memenuhi standar compliance seperti CIS Benchmark, STIG, PCI-DSS, atau ISO 27001. Mengelola kepatuhan ini "as code" — bukan dengan checklist Excel — adalah cara satu-satunya yang scalable.

Pada episode ini kita akan membahas implementasi CIS benchmark menggunakan collection ansible-lockdown, hardening SSH dan firewall (UFW, firewalld), otomasi patch management lengkap dengan manajemen reboot, compliance as code untuk STIG dan file integrity monitoring (AIDE), serta integrasi scanner keamanan seperti OpenSCAP dan Lynis.

Pembahasan Utama

Mengapa Hardening Itu Penting

Hardening adalah proses memperkecil attack surface (permukaan serangan) sebuah sistem: menutup service yang tidak perlu, memperkuat autentikasi, menerapkan prinsip least privilege, dan mengunci konfigurasi default yang lemah. Default instalasi Linux biasanya "nyaman tapi rapuh": SSH dengan password, root login diizinkan, banyak port terbuka, dan update keamanan tidak otomatis.

Kuncinya: Ansible membuat hardening menjadi repeatable dan verifiable. Playbook yang sama bisa dijalankan ke server baru dalam hitungan menit, hasilnya identik, dan idempotent — dijalankan ulang tidak mengubah apa-apa yang sudah benar. Inilah yang membedakan hardening as code dari checklist manual.

OS Security Hardening: Implementasi CIS Benchmark

CIS (Center for Internet Security) Benchmark adalah kumpulan rekomendasi hardening berbasis konsensus industri untuk berbagai sistem operasi — mulai dari konfigurasi kernel, file permission, sshd, hingga policy audit. Setiap rekomendasi diberi level: Level 1 (praktik dasar yang disarankan) dan Level 2 (defense-in-depth untuk environment yang sangat sensitif).

Menulis ribuan kontrol CIS secara manual adalah pekerjaan besar. Di sinilah komunitas ansible-lockdown berperan. Collection ini menyediakan role hardening siap pakai yang sudah mengimplementasikan CIS Benchmark untuk berbagai sistem operasi:

Collection RoleTarget OSBenchmark
ansible-lockdown.redhatcis_rhel9RHEL 9 / Rocky 9 / AlmaLinux 9CIS RHEL 9 Benchmark
ansible-lockdown.redhatcis_rhel8RHEL 8 / Rocky 8 / AlmaLinux 8CIS RHEL 8 Benchmark
ansible-lockdown.ubuntu_cisUbuntu 22.04 / 24.04CIS Ubuntu Benchmark
ansible-lockdown.windows_cisWindows Server 2019 / 2022CIS Windows Server Benchmark
ansible-lockdown.stig_rhel9RHEL 9DISA STIG for RHEL 9

Cara kerjanya: role mendaftarkan daftar rule CIS sebagai variabel boolean, lalu kalian mengaktifkan/menonaktifkan rule sesuai kebutuhan. Role membaca variabel tersebut dan menyesuaikan konfigurasi sistem secara idempotent.

Install collection-nya:

Install ansible-lockdown
ansible-galaxy collection install ansible-lockdown.ubuntu_cis
ansible-galaxy collection install ansible-lockdown.redhatcis_rhel9

Setelah itu, gunakan role dalam playbook. Contoh berikut meng-hardening server Ubuntu 24.04 terhadap CIS Level 2:

hardening-ubuntu-cis.yml
- name: Hardening Ubuntu dengan CIS Benchmark
  hosts: ubuntu_servers
  become: true
  vars:
    ubtu20cis_rule_6_1_2: false
    ubtu20cis_auditd_enabled: true
    ubtu20cis_system_audit_rules:
      - "-w /etc/passwd -p wa -k identity"
      - "-w /etc/shadow -p wa -k identity"
    ubtu20cis_sysctl_rules:
      net.ipv4.ip_forward: 0
      net.ipv4.conf.all.send_redirects: 0
  roles:
    - ansible-lockdown.ubuntu_cis

Important

Role dari ansible-lockdown sangat agresif — beberapa rule mengubah permission, mematikan service, atau mengunci user. Selalu jalankan dengan mode --check terlebih dahulu, uji di staging environment, dan pastikan kalian memahami setiap rule yang diaktifkan. Menjalankan CIS role penuh di production tanpa testing adalah cara tercepat membuat production down. Nama prefix variabel mengikuti versi role (misalnya ubtu20cis_* untuk Ubuntu 20.04/22.04), jadi periksa dokumentasi role untuk versi yang kalian pakai.

Untuk role hardening SSH yang lebih ringan dan terkontrol, kita bisa menulisnya sendiri. Contoh berikut memanfaatkan modul ansible.builtin.lineinfile dan template sshd_config:

ssh-hardening.yml
- name: Hardening konfigurasi SSH server
  hosts: all
  become: true
  tasks:
    - name: Template sshd_config yang aman
      ansible.builtin.template:
        src: sshd_config.j2
        dest: /etc/ssh/sshd_config
        owner: root
        group: root
        mode: "0600"
        validate: "/usr/sbin/sshd -t -f %s"
      notify: Restart SSH
  handlers:
    - name: Restart SSH
      ansible.builtin.service:
        name: sshd
        state: restarted

Template sshd_config.j2-nya:

templates/sshd_config.j2
# Managed by Ansible - perubahan manual akan ditimpa
Port {{ ssh_port | default(22) }}
Protocol 2
PermitRootLogin no
PasswordAuthentication no
PubkeyAuthentication yes
MaxAuthTries 3
LoginGraceTime 30
ClientAliveInterval 300
ClientAliveCountMax 2
AllowUsers {{ ssh_allowed_users | default([]) | join(' ') }}
AllowTcpForwarding no
X11Forwarding no

Warning

Perhatikan atribut validate: "/usr/sbin/sshd -t -f %s". Ini memvalidasi syntax config sebelum mengganti file asli — menyelamatkan kalian dari lockout fatal jika template salah. Dan selalu pastikan key SSH kalian sudah terpasang (authorized_key) sebelum menonaktifkan PasswordAuthentication, atau kalian akan terkunci di luar server sendiri.

Firewall Configuration: UFW, firewalld, iptables

Firewall adalah pagar pertama dari sebuah server. Ansible menyediakan modul khusus untuk masing-masing backend, dan keputusan terbaik adalah memilih satu firewall per host dan konsisten — jangan mencampur UFW dan firewalld pada sistem yang sama.

Contoh code group berikut menunjukkan pendekatan yang setara di tiga dunia berbeda — satu untuk Debian/Ubuntu (UFW), satu untuk RHEL/Rocky (firewalld), dan satu yang low-level (iptables) untuk kasus yang sangat spesifik:

- name: Konfigurasi firewall UFW (Debian/Ubuntu)
  hosts: ubuntu_servers
  become: true
  tasks:
    - name: Default policy deny incoming
      community.general.ufw:
        policy: deny
        direction: incoming
 
    - name: Izinkan SSH dari subnet internal
      community.general.ufw:
        rule: allow
        proto: tcp
        port: "22"
        src: 10.0.0.0/8
 
    - name: Izinkan HTTP/HTTPS publik
      community.general.ufw:
        rule: allow
        port: "80,443"
        proto: tcp
 
    - name: Aktifkan UFW
      community.general.ufw:
        state: enabled

Note

Untuk managed node yang berada di balik security group cloud (AWS, GCP, Azure), ingat bahwa security group cloud tidak menggantikan firewall OS — keduanya harus saling melengkapi. Security group melindungi dari luar VPC, sedangkan firewall OS melindungi dari host lain di dalam network yang sama. Buat aturan firewalld dengan immediate: true agar perubahan berlaku tanpa menunggu reload service — mencegah lockout saat menerapkan policy deny secara live.

Patch Management: Automasi Security Update

Patch management adalah salah satu kontrol keamanan paling murah namun paling efektif — sebagian besar serangan ransomware dan zero-day exploitation memanfaatkan kerentanan yang sebenarnya sudah ditambal berbulan-bulan lalu. Masalahnya, manual patching di banyak server hampir mustahil dilakukan konsisten.

Ansible menawarkan dua pendekatan: automated security updates (patch kecil berjalan otomatis) dan scheduled patch cycles (patch besar dengan jadwal dan reboot terkontrol).

Untuk Ubuntu/Debian, unattended-upgrades menginstal patch keamanan secara otomatis di latar belakang. Konfigurasinya bisa di-template oleh Ansible:

unattended-upgrades.yml
- name: Aktifkan automated security updates
  hosts: ubuntu_servers
  become: true
  tasks:
    - name: Install unattended-upgrades
      ansible.builtin.apt:
        name: unattended-upgrades
        state: present
        update_cache: true
 
    - name: Template konfigurasi auto-upgrade
      ansible.builtin.template:
        src: 50unattended-upgrades.j2
        dest: /etc/apt/apt.conf.d/50unattended-upgrades
        mode: "0644"
 
    - name: Aktifkan interval upgrade otomatis
      ansible.builtin.copy:
        dest: /etc/apt/apt.conf.d/20auto-upgrades
        content: |
          APT::Periodic::Update-Package-Lists "1";
          APT::Periodic::Unattended-Upgrade "1";
          APT::Periodic::AutocleanInterval "7";

Untuk RHEL, dnf-automatic memainkan peran yang sama:

Aktifkan dnf-automatic
dnf install -y dnf-automatic
sed -i 's/apply_updates = no/apply_updates = yes/' /etc/dnf/automatic.conf
systemctl enable --now dnf-automatic.timer

Caution

Automated security update adalah pedang bermata dua. Di satu sisi ia menutup lubang keamanan dengan cepat; di sisi lain ia bisa memasang update yang merusak aplikasi di jam 3 pagi tanpa sepengetahuan siapa pun. Praktik terbaik: aktifkan automated update hanya untuk patch keamanan, lakukan pinning versi untuk service kritis, dan pantau hasilnya lewat log serta monitoring (ingat episode 25).

Patch Management: Reboot dengan Manajemen yang Aman

Update kernel selalu membutuhkan reboot — dan reboot adalah momen paling menegangkan dalam operasional. Di sinilah modul ansible.builtin.reboot berperan. Modul ini tidak sekadar me-reboot; ia bisa menunggu koneksi SSH turun, menunggu service kembali, dan menunda reboot agar tidak terjadi secara tiba-tiba.

Contoh playbook patch + reboot yang aman untuk fleet production — memanfaatkan serial agar hanya sebagian server yang dipatch bersamaan:

patch-reboot-drain.yml
- name: Patch dan reboot aman
  hosts: app_servers
  become: true
  serial: 1
  order: sorted
  tasks:
    - name: Update semua paket (termasuk kernel)
      ansible.builtin.dnf:
        name: "*"
        state: latest
        update_cache: true
 
    - name: Cek apakah reboot dibutuhkan
      ansible.builtin.command: /usr/bin/needs-restarting -r
      register: needs_reboot
      failed_when: needs_reboot.rc not in [0, 1]
      changed_when: false
 
    - name: Reboot dengan grace period
      ansible.builtin.reboot:
        reboot_timeout: 600
        pre_reboot_delay: 30
        post_reboot_delay: 15
        connect_timeout: 30
      when: needs_reboot.rc == 1

Tip

Beberapa parameter penting modul reboot: pre_reboot_delay memberi waktu 30 detik agar aplikasi drain graceful, post_reboot_delay menunggu sistem benar-benar stabil setelah boot, dan reboot_timeout membatasi waktu tunggu maksimal. Untuk service yang tidak boleh drop, tambahkan task pre-check kesehatan aplikasi (misalnya cek HTTP endpoint) setelah reboot — Ansible punya wait_for yang bisa menunggu port/URL kembali sehat. Kombinasi serial: 1 + drain + health check adalah resep rolling reboot tanpa downtime.

Compliance as Code: STIG dan Audit Logging

STIG (Security Technical Implementation Guide) adalah standar hardening yang dikeluarkan oleh DISA (Defense Information Systems Agency) Amerika Serikat, diwajibkan untuk semua sistem di lingkungan militer dan pemerintahan, dan banyak diadopsi industri sebagai acuan "hardening tingkat lanjut". Di episode ini cukup kita pahami pola dasarnya: STIG dikategorikan per control (misalnya SV-XXXXX untuk aturan tertentu), dan role seperti ansible-lockdown.stig_rhel9 mengotomasi implementasinya.

Pilar compliance yang kedua adalah audit logging — tanpa log yang baik, kalian tidak bisa membuktikan kepatuhan (atau menemukan jejak serangan). Contoh berikut mengkonfigurasi rsyslog agar log di-forward ke log server terpusat, plus mengaktifkan auditd untuk memantau perubahan file penting:

audit-logging.yml
- name: Konfigurasi audit logging terpusat
  hosts: all
  become: true
  vars:
    central_log_host: 10.0.0.50
  tasks:
    - name: Forward log auth ke server terpusat
      ansible.builtin.copy:
        dest: /etc/rsyslog.d/60-central.conf
        content: |
          auth.*          @@{{ central_log_host }}:514
          kern.*          @@{{ central_log_host }}:514
          mail.*          @@{{ central_log_host }}:514
      notify: Restart rsyslog
 
    - name: Pantau integritas file penting dengan auditd
      ansible.builtin.copy:
        dest: /etc/audit/rules.d/audit.rules
        content: |
          -w /etc/passwd -p wa -k identity
          -w /etc/shadow -p wa -k identity
          -w /etc/sudoers -p wa -k identity
          -w /var/log/auth.log -p wa -k authlog
          -a always,exit -F arch=b64 -S execve -k process_execution
      notify: Restart auditd
 
  handlers:
    - name: Restart rsyslog
      ansible.builtin.service:
        name: rsyslog
        state: restarted
 
    - name: Restart auditd
      ansible.builtin.service:
        name: auditd
        state: restarted

File integrity monitoring (FIM) melengkapi audit logging: ia mendeteksi perubahan pada file penting yang seharusnya tidak pernah berubah. AIDE (Advanced Intrusion Detection Environment) adalah pilihan FIM open source yang populer. Alurnya: inisialisasi database baseline → bandingkan berkala → laporkan perbedaan.

aide-fim.yml
- name: Setup AIDE file integrity monitoring
  hosts: all
  become: true
  tasks:
    - name: Install AIDE
      ansible.builtin.apt:
        name: aide
        state: present
 
    - name: Inisialisasi database baseline AIDE
      ansible.builtin.command: aideinit
      args:
        creates: /var/lib/aide/aide.db
      changed_when: false
 
    - name: Jadwalkan scan harian via cron
      ansible.builtin.cron:
        name: "AIDE daily integrity check"
        minute: "0"
        hour: "3"
        job: "/usr/bin/aide.wrapper --check | mail -s 'AIDE report' security@example.com"

Warning

Prinsip emas FIM: database baseline harus dibuat di sistem yang sudah bersih dan ter-verified, bukan setelah sistem berjalan berbulan-bulan dengan kemungkinan sudah ter-compromise. Setelah inisialisasi, update database baseline secara manual hanya saat perubahan memang disengaja (misalnya deploy baru), dan simpan hash database di lokasi yang sulit diakali penyerang. Kalau tidak, kalian akan tenggelam dalam ratusan false-positive alert setiap hari.

Security Scanning Integration: OpenSCAP dan Lynis

Hardening tanpa verifikasi hanyalah klaim. Scanner keamanan mengubah klaim menjadi bukti: berapa banyak kontrol yang lolos, mana yang gagal, dan mana yang masih rawan. Ansible adalah kendaraan sempurna untuk menjalankan scanner, mengumpulkan hasil, dan membuat laporan di seluruh fleet secara berkala.

OpenSCAP adalah scanner compliance berbasis standar (menjalankan profil seperti CIS, STIG, PCI-DSS) dan menghasilkan laporan dalam format HTML/XML. Lynis adalah scanner audit keamanan yang memberikan hardening index dan rekomendasi berbasis heuristik. Contoh code group berikut menunjukkan keduanya:

- name: Scan compliance dengan OpenSCAP
  hosts: rhel_servers
  become: true
  tasks:
    - name: Install openscap-scanner
      ansible.builtin.dnf:
        name: openscap-scanner
        state: present
 
    - name: Jalankan scan profil STIG RHEL 9
      ansible.builtin.command:
        cmd: >-
          oscap xccdf eval
          --profile stig
          --results /root/scap-results.xml
          --report /root/scap-report.html
          /usr/share/xml/scap/ssg/content/ssg-rhel9-ds.xml
      register: scan_result
      changed_when: scan_result.rc != 0
 
    - name: Tarik laporan scan ke control node
      ansible.builtin.fetch:
        src: /root/scap-report.html
        dest: "reports/{{ inventory_hostname }}-scap.html"
        flat: true

Tip

Keluarkan scan secara berkala (misalnya via cron atau pipeline CI/CD pada episode 19) dan jadikan laporannya source of truth untuk audit. Integrasikan nilai kerentanan ke sistem ticketing atau dashboard — misalnya community.general punya modul grafana_dashboard jika kalian ingin memvisualisasikan skor compliance. Yang lebih penting: scan harus di-remediate, bukan sekadar disimpan. Pasangkan hasil scan dengan playbook hardening agar kontrol yang gagal otomatis diperbaiki pada run berikutnya.

Kesalahan Umum (Common Pitfalls)

1. Hardening langsung di production tanpa staging

Role CIS dan STIG agresif; satu rule bisa mengunci user, mematikan service yang dipakai aplikasi, atau memblokir network. Selalu --check, uji di staging, lalu promote ke production.

2. Lupa menyisakan jalur pemulihan

Sebelum menonaktifkan PasswordAuthentication, pastikan key SSH sudah terpasang di semua host. Sebelum mematikan firewall default policy, pastikan ada akses out-of-band (misalnya IPMI atau console cloud). Satu kesalahan dan kalian terkunci — dan Ansible tidak bisa menolong kalian lagi.

3. Reboot tanpa drain

Reboot semua server sekaligus (serial: 1 diabaikan) menjamin everything down. Selalu batasi batch, beri pre_reboot_delay, dan tunggu health check sebelum melanjutkan ke batch berikutnya.

4. Automated update tanpa monitoring

unattended-upgrades yang berjalan diam-diam tanpa alert sama berbahayanya dengan tidak pernah update. Selalu pantau log update dan verifikasi bahwa service tetap sehat setelah patch.

5. Baseline AIDE dibuat saat sistem sudah "tercemar"

Database FIM hanya berguna jika dibuat dari sistem yang bersih. Dan jangan lupa update baseline saat perubahan disengaja — kalau tidak, noise alert akan membuat kalian mematikan alert-nya (yang jauh lebih berbahaya).

6. Mengandalkan scanner sebagai pengganti hardening

OpenSCAP/Lynis menemukan masalah, bukan memperbaiki masalah. Scanning harus dipasangkan dengan playbook remediation, kalau tidak skor compliance hanyalah angka di dashboard.

Penutup

Pada episode ini kita telah membahas security hardening dan compliance automation secara menyeluruh: implementasi CIS Benchmark dengan collection ansible-lockdown, hardening SSH dan konfigurasi firewall (UFW, firewalld, iptables), patch management dengan automated security updates dan reboot yang aman, compliance as code untuk STIG, audit logging, dan file integrity monitoring dengan AIDE, serta integrasi scanner keamanan OpenSCAP dan Lynis dengan laporan otomatis. Kita juga menutup dengan kesalahan umum yang sering membuat tim terjebak.

Intinya, keamanan bukanlah produk yang dibeli, melainkan proses yang dijaga terus-menerus — dan Ansible mengubah proses itu dari aktivitas manual yang rawan lupa menjadi sistem deklaratif yang terverifikasi dan bisa diaudit. Dengan kemampuan ini, kalian bisa mengklaim tidak hanya bahwa infrastruktur kalian tersedia, tapi juga terjamin.

Di episode 28 selanjutnya, kita akan membahas topik yang menantang anggapan "Ansible hanya untuk Linux": Windows Automation dengan Ansible — mengelola WinRM, modul ansible.windows dan community.windows, automasi IIS, Windows Update, hingga Active Directory dari control node Linux yang sama. Pastikan tetap semangat!

Belajar Ansible - Security Hardening & Compliance Automation | Belajar Ansible