Category Archives: Logs, Tips, and Scripts

Bulk whois public IP address

Dari pantauan SOC, kantor tempat saya bekerja termasuk sering mengalami cyber threat. Ada banyak aplikasi yang public-facing, dan tentunya yang paling sering diserang adalah halaman website utama. Setiap serangan itu, dengan threshold tertentu kami akan melakukan automatic blocking terhadap IP addressnya menggunakan SOAR.

Dari sekian ratusan IP address yang diblok, setiap harinya, tentu ada aja false positive, atau IP ISP konsumer seperti Telkom(sel), Indosat, MyRepublic, dll yang ikut diblok. Tentu sebenarnya itu bukan best practice yang baik karena IP address tsb udah pasti NAT dan satu IP dapat digunakan oleh banyak pengguna.

Jadi secara berkala kami perlu melakukan cleansing dan release IP address tersebut. Nah untuk memudahkan identifikasi IP address ketika proses cleansing, saya coba manfaatkan untuk membuat bash script sederhana yang akan melakukan query whois seluruh IP address tsb menggunakan layanan ipapi.is. Cekidot..

#!/bin/bash

input_file="ip_list.txt"
output_file="ipapi_results.csv"
api_token="6671d06b2608be1f"  # Ganti dengan token API Anda

# Header untuk file CSV
echo "IP Address,Country,Country_Code,State,City,ORG,DESCR,is_crawler,is_datacenter,is_tor,is_proxy,is_vpn,is_abuser,abuser_score,type" > "$output_file"

counter=0
while IFS= read -r ip; do
    # Mengambil data dari ipapi.is
    location_info=$(curl -s "https://api.ipapi.is/?q=$ip&key=$api_token")

    if echo "$location_info" | grep -q "Please register"; then
        echo "Error: API key tidak valid atau kuota habis untuk IP: $ip"
        continue
    fi

    echo "Debug info untuk IP: $ip"
    echo "$location_info"

    # Parsing JSON untuk kolom yang diinginkan
    country=$(echo "$location_info" | jq -r '.location.country')
    country_code=$(echo "$location_info" | jq -r '.location.country_code')
    state=$(echo "$location_info" | jq -r '.location.state')
    city=$(echo "$location_info" | jq -r '.location.city')
    org=$(echo "$location_info" | jq -r '.asn.org')
    descr=$(echo "$location_info" | jq -r '.asn.descr')
    is_crawler=$(echo "$location_info" | jq -r '.is_crawler')
    is_datacenter=$(echo "$location_info" | jq -r '.is_datacenter')
    is_tor=$(echo "$location_info" | jq -r '.is_tor')
    is_proxy=$(echo "$location_info" | jq -r '.is_proxy')
    is_vpn=$(echo "$location_info" | jq -r '.is_vpn')
    is_abuser=$(echo "$location_info" | jq -r '.is_abuser')
    abuser_score=$(echo "$location_info" | jq -r '.company.abuser_score')
    type=$(echo "$location_info" | jq -r '.company.type')

    # Tulis hasil ke file CSV
    echo "\"$ip\",\"$country\",\"$country_code\",\"$state\",\"$city\",\"$org\",\"$descr\",\"$is_crawler\",\"$is_datacenter\",\"$is_tor\",\"$is_proxy\",\"$is_vpn\",\"$is_abuser\",\"$abuser_score\",\"$type\"" >> "$output_file"

    # Rate Limiting: Tunggu 5 detik setiap 5 permintaan
    ((counter++))
    if [ $((counter % 5)) -eq 0 ]; then
        sleep 5
    fi
done < "$input_file"

echo "Proses selesai! Lihat hasil di $output_file"

Outputnya nanti file CSV kurang lebih seperti ini;

Hope this helps!

transmission-daemon keep crashing

info="Failed name lookup - disconnected path" error=-13 profile="transmission-daemon"

kernel: audit: type=1400 audit(1727748381.320:280): apparmor="ALLOWED" operation="sendmsg" class="file" info="Failed name lookup - disconnected path" error=-13 profile="transmission-daemon" name="run/systemd/notify" pid=12363 comm="transmission-da" requested_mask="w" denied_mask="w" fsuid=113 ouid=0

The workaround is edit /etc/apparmor.d/transmission and;

- profile transmission-daemon /usr/bin/transmission-daemon flags=(complain) {
+ profile transmission-daemon /usr/bin/transmission-daemon flags=(complain,attach_disconnected) {

How to fix NGINX expired key (EXPKEYSIG ABF5BD827BD9BF62) on Debian Bookworm

apt update command giving error message something like this;

Err:8 https://nginx.org/packages/mainline/debian bookworm InRelease The following signatures were invalid: EXPKEYSIG ABF5BD827BD9BF62 nginx signing key <[email protected]>

Fix is simple;

sudo curl -s https://nginx.org/keys/nginx_signing.key | gpg --dearmor > /usr/share/keyrings/nginx-keyring.gpg

And then just do apt update as usual.

Membuat file PKCS#12/PFX

Karena kerja sebagai security analyst, udah jadi agenda tahunan saya untuk update SSL certificate seluruh aplikasi kantor. Certificate yang didapat dari penyedia sebenernya bisa ke semua format yang ada, kecuali PKCS#12/PFX karena mereka ngga punya file key nya. Sebagai pengingat juga untuk saya di tahun depan, ini dia cara convert file certs menjadi PKCS#12/PFX:

openssl pkcs12 -export -out domain.com.pfx -inkey domain.com.privateKey.key -in domain.com.crt -certfile Intermediate-CA.crt -certfile TrustedRoot.crt

Sedangkan untuk verifikasi bahwa csr, key, dan crt yang kita punya itu match, commands nya begini:

openssl pkey -in domain.com.key -pubout -outform pem | sha256sum
openssl x509 -in domain.com.crt -pubkey -noout -outform pem | sha256sum
openssl req -in domain.com.csr -pubkey -noout -outform pem | sha256sum