[태그:] brute-force

  • 24시간 안에 봇이 온다 — 도메인 공개 전 보안 P0

    24시간 안에 봇이 온다 — 도메인 공개 전 보안 P0

    24시간 안에 봇이 온다 — 도메인 공개 전 보안 P0

    셀프호스팅 구축기 8편. 도메인 띄우기 전에 반드시 끝내야 하는 25분.


    TL;DR

    • WordPress 도메인 공개 = 24시간 안에 brute force 봇이 옴. 통계적 사실
    • 25분 작업으로 99% 차단: ① 사용자명 admin 회피 ② xmlrpc 차단 ③ wp-login 슬러그 변경
    • 이 셋이 보안 P0. 도메인 띄우기 전에 끝낸다
    • Wordfence·2FA는 P1 (도메인 띄운 후 추가)

    1. 첫 24시간의 진실

    WordPress 사이트가 인터넷에 노출되면 첫 24시간 안에:

    공격 빈도 대상
    /wp-login.php brute force 시간당 수천 회 관리자 비번
    /xmlrpc.php pingback amp 끊임없음 DDoS 증폭
    알려진 플러그인 취약점 스캔 끊임없음 옛 버전 플러그인
    SQL injection 시도 자동 봇 ?id=1 OR 1=1 URL
    User enum (?author=1) 자동 봇 사용자명 알아내기

    이걸 막을 게 아니라 표면 자체를 없애는 게 P0.


    2. P0 — 보안 3종 셋업

    

    3. ① 사용자명 admin 회피

    WordPress 설치 마법사가 첫 사용자 만들 때 admin이라고 입력하지 마세요. 봇 brute force 1순위 타겟.

    좋은 예: jamjam, sailor904, 본인 닉
    나쁜 예: admin, administrator, root, wpadmin
    

    이미 admin으로 만들었으면 wp-cli로 새 사용자 생성 후 admin 권한 박탈 또는 삭제:

    wp user create newname [email protected] --role=administrator --user_pass=$(openssl rand -base64 24) --allow-root
    wp user delete admin --reassign=newname --allow-root
    

    4. ② xmlrpc.php 차단 — mu-plugin

    /xmlrpc.php는 WordPress 옛 API. 거의 안 쓰임 (Jetpack 사용자만). 봇이 brute force amplification (한 번 요청으로 비번 1000개 시도)에 악용.

    /var/www/html/wp-content/mu-plugins/disable-xmlrpc.php:

    <?php
    /**
     * Plugin Name: Disable XML-RPC
     * Description: Block xmlrpc.php to reduce attack surface.
     */
    if (!defined('ABSPATH')) exit;
    
    add_filter('xmlrpc_enabled', '__return_false');
    add_filter('wp_headers', function ($headers) {
        unset($headers['X-Pingback']);
        return $headers;
    });
    add_filter('xmlrpc_methods', function ($methods) {
        unset($methods['pingback.ping']);
        unset($methods['pingback.extensions.getPingbacks']);
        return $methods;
    });
    add_action('init', function () {
        $uri = $_SERVER['REQUEST_URI'] ?? '';
        if (stripos($uri, '/xmlrpc.php') !== false) {
            status_header(403);
            exit('xmlrpc disabled');
        }
    });
    

    검증:

    curl -I http://localhost:8090/xmlrpc.php
    # HTTP/1.1 403  ← 성공
    

    5. ③ wp-login 슬러그 변경

    /wp-login.php는 모든 WordPress 사이트가 똑같이 갖는 로그인 URL. 봇이 처음 들어와서 자동으로 칠 URL. 이걸 다른 슬러그로 숨김.

    플러그인 wps-hide-login 설치:

    wp plugin install wps-hide-login --activate --allow-root
    wp option update whl_page starport --allow-root
    

    starport는 사장님이 정한 비밀 슬러그. 추측 어려운 단어 + 본인 기억하기 쉬운 거. 예: byeolgorae-gate, secret-door-2026, starport.

    검증:

    curl -I -L http://localhost:8090/wp-login.php
    # 301 redirect → 가짜 URL (봇 헛걸음)
    
    curl -I -L http://localhost:8090/wp-admin/
    # 404 (로그아웃 상태에선 admin 페이지 자체가 없는 척)
    
    curl -I -L http://localhost:8090/starport/
    # 200 (사장님만 아는 로그인 페이지)
    

    사장님이 슬러그 잊으면 본인도 못 들어옴. 즐겨찾기·메모 필수.


    6. 결과 — 봇 입장에서

    공격 차단 후 응답
    GET /wp-login.php 301 → 가짜 URL → 봇이 거기서 시도 → 영원히 실패
    POST /xmlrpc.php 403 즉시 차단. amplification 불가
    GET /wp-admin/ 404. 관리 페이지 자체가 없는 척
    사용자명 brute force admin 시도 → 우리 사이트엔 admin 없음
    ?author=1 user enum Rank Math가 자동 차단 (Disable Author Archives)

    봇이 들이는 자원 = 사장님 사이트에서 얻는 게 0.


    7. P0 vs P1 vs P2 — 우선순위

    단계 작업 시점
    P0 (필수, 도메인 공개 전) 사용자명·xmlrpc·wp-login 슬러그 이번 25분
    P1 (도메인 띄운 직후) Wordfence 위자드 + 2FA 사장님 GUI 작업
    P2 (월 1회) 플러그인 보안 업데이트 + WPA(취약점 스캔) 운영 단계

    P0 안 끝내고 도메인 띄우면 — 봇이 24시간 안에 와서 brute force 시작. 셋업 안 됐어도 어차피 못 뚫지만, 로그에 brute force 시도가 쌓이고 미니PC CPU 잡아먹음. 미리 막는 게 정신 위생.


    8. 함정

    함정 1. mu-plugin 자동 활성

    mu-plugins는 일반 플러그인 위에서 강제 실행 (mu = Must Use). 따라서 xmlrpc 차단처럼 절대 비활성되면 안 되는 보안 정책은 mu-plugin이 맞는 곳.

    함정 2. WPS Hide Login slug 잊기

    whl_page 옵션을 DB에 직접 박아두기 때문에, 사장님이 슬러그 잊으면 본인도 못 들어옴. 복구 방법: wp option get whl_page --allow-root (미니PC SSH로) 또는 mu-plugin 임시 비활성.

    함정 3. 인증 후 자동 우회

    WPS Hide Login은 슬러그를 모르는 사람만 차단. 로그인된 세션은 그대로 /wp-admin/ 사용. 사장님이 한 번 로그인하면 그 이후 30분 동안 admin 페이지 자유.

    함정 4. 로그아웃 시 새 슬러그로 진입

    사장님이 로그아웃하면 다음 로그인은 /starport로. 즐겨찾기 갱신 필수.


    FAQ

    Q. 이미 도메인 공개해버렸는데 P0 안 했으면?
    지금 즉시 cloudflared 끄거나 Tailscale Funnel 해제 → P0 셋업 → 다시 공개. 5분.

    Q. Wordfence 위자드(P1)는 왜 P0 아닌가?
    P0는 표면 자체를 없애는 것. Wordfence는 표면이 있는 상태에서 공격을 탐지·차단. 보완재.

    Q. 슬러그를 /admin 으로 바꿔도 되나?
    /admin도 봇이 시도하는 흔한 슬러그. 추천 X. 본인만 떠올릴 수 있는 + 추측 어려운 단어.

    Q. 2FA 없어도 P0면 충분한가?
    충분 + 충분. 2FA는 비번 노출됐을 때 마지막 방패. P0 + 2FA = 사실상 무적.

    Q. xmlrpc 차단하면 Jetpack 못 쓰나?
    Jetpack 일부 기능 X. Jetpack 자체가 없으면 무관. 우리 별고래는 Jetpack 안 씀.


    다음 편 예고

    9편 — 보이지 않는 다리: Cloudflare Tunnel. 드디어 도메인을 미니PC에 연결. 공유기 포트 안 열고, 미니PC IP 안 들키고, WAF·DDoS·CDN까지 무료로.


    한 줄 정리

    WordPress 도메인 공개 = 24시간 안에 봇이 옴. 25분 P0 셋업(사용자명·xmlrpc·wp-login 슬러그)으로 99% 차단. 도메인 띄우기 전에 끝낸다.