기능

WardPane 2.0이 하는 일

WardPane 2.0은 정적, PHP, Node.js 사이트를 호스팅하며 인증서 자동 발급과 Cloudflare를 지원합니다. 보호와 트래픽 제어는 사이트별로 웹 서버 안에서 실행됩니다. 비교 페이지의 패널 여덟 개 중 대부분은 이 기능을 ModSecurity나 유료 애드온으로 제공합니다.

초보자와 숙련된 관리자 모두를 위해

초보자는 명령어 하나로 설치하고, 인증서는 스스로 발급되며, 사이트는 샌드박스에서 실행되고, 설정은 쉬운 말로 설명됩니다. 숙련된 관리자는 모든 옵션, 브라우저 안의 터미널, 소유자별 PM2, .htaccess, 알려진 순서로 실행되는 사이트별 규칙, Cloudflare API, 내보내기와 가져오기, 릴리스 체크섬, 그리고 소스 코드를 얻습니다.

호스팅

사이트는 ISPmanager 방식의 구조로 배치되고, Linux 사용자가 소유하며, WardPane이 80번과 443번 포트에서 직접 제공합니다.

사이트와 별칭
사이트는 도메인 하나와 최대 99개의 별칭으로 이루어집니다(Let's Encrypt 인증서 하나에는 최대 100개의 이름이 들어갑니다). 별칭은 기본 사이트를 제공하거나, 자신만의 폴더가 있으면 그 폴더를 제공합니다. 사이트에 표시 이름을 붙일 수 있습니다.
소유자 구조
파일은 /var/www/<owner>/data/www/<domain>에 있고, 로그와 임시 파일은 그 옆에 있습니다. 기본 소유자는 WardPane이 만드는 Linux 사용자인 www-root입니다. 1.x의 사이트는 기존 폴더를 그대로 유지합니다.
세 가지 핸들러
핸들러 없음(정적 호스팅), PHP, Node.js 중에서 사이트마다 선택하며 언제든지 전환할 수 있습니다. 다른 핸들러의 설정은 유지되므로 다시 전환하면 그대로 복원됩니다.
정적 파일
SPA 모드(알 수 없는 경로는 index.html로), 직접 만든 404.html, 이어받기를 지원하는 강한 ETag, HTTP에서 HTTPS로의 리디렉션, 그리고 절대 사이트 폴더 밖으로 나갈 수 없는 심볼릭 링크.
런타임
패널은 서버에 설치된 PHP 버전과 지원하는 Node.js 메이저 버전 20, 22, 24, 26을 표시하며 기본값은 24입니다(20은 2026년 4월에 지원이 종료되었습니다). Node.js 빌드는 nodejs.org에서 받으며 공개된 SHA256 합계와 대조해 확인합니다.
모든 사이트에 메뉴
사이트 표의 각 행에는 그 사이트의 모든 작업이 담긴 메뉴가 있으며, 스위치로 아무것도 삭제하지 않고 사이트를 껐다가 다시 켤 수 있습니다.
브라우저 안의 셸
패널 안에 바로 있는 터미널: root 세션에서는 root 셸, 그 외에는 사이트 폴더에서 사이트 소유자의 셸입니다. Node.js 사이트에서는 pm2 list와 pm2 restart를 그곳에서 사용할 수 있습니다.
내보내기와 가져오기
모든 사이트와 모든 설정, 그리고 전역 차단 목록이 JSON 파일 하나에 담깁니다. 가져오기는 병합 또는 교체 방식으로 이루어지며, 먼저 파일 전체를 확인하고 /var/www의 파일은 절대 건드리지 않습니다.
핸들러, 인증서 기간, 활성 보호 기능이 표시된 사이트 표

PHP와 Node.js

동적 사이트는 각각 전용 Linux 사용자로 systemd 샌드박스 안에서 실행됩니다. 고장 나거나 해킹된 사이트도 이웃 사이트를 읽을 수 없습니다.

사이트마다 php-fpm 풀
공유 풀도, 공유 opcache나 세션도 없습니다. 코드는 PHP에 읽기 전용이며, PHP는 tmp/, logs/, data/와 지정한 폴더에만 쓸 수 있고, 그 폴더에서는 PHP가 절대 실행되지 않습니다.
엄격한 PHP 샌드박스
php-fpm 자체를 제외한 파일 시스템 전체가 읽기 전용이자 noexec이고, open_basedir가 설정되며, exec, system, shell_exec, proc_open, popen, putenv가 비활성화되고, 시스템 호출이 필터링됩니다.
Apache 없는 .htaccess
실제 사이트에서 쓰는 rewrite 규칙, 리디렉션, 접근 규칙, Basic auth, 헤더, 캐싱이 그대로 작동합니다. WordPress, Laravel, 흔히 쓰는 HTTPS 및 www 리디렉션도 마찬가지입니다. 적용할 수 없는 줄은 추측하지 않고 표시합니다.
PM2 기반 Node.js
Node.js 메이저 버전, npm 스크립트 또는 진입 파일, 환경 변수, 제한을 선택하십시오. 소유자마다 PM2 데몬 하나가 앱을 실행하므로 소유자의 셸에서 pm2를 사용할 수 있습니다.
앱 앞단의 프록시
원하면 public/의 파일을 직접 제공하고, 나머지는 X-Forwarded-For와 X-Real-IP에 실제 방문자 IP를 담아 앱으로 전달합니다. WebSocket도 같은 보호 검사를 거친 뒤 통과합니다.
재시작, npm install, 로그
핸들러 탭에는 재시작과 npm install(lockfile이 있으면 npm ci) 버튼, 출력, 오류, 설치 로그, 그리고 선택할 수 있는 package.json 스크립트가 있습니다.
사이트의 핸들러 탭: Node.js 버전, 시작 스크립트, 환경 변수, 제한

인증서와 Cloudflare

인증서는 수동 작업 없이 발급되고 갱신되며, Cloudflare 뒤에 있는 사이트도 마찬가지입니다.

완전 자동 Let's Encrypt
사이트마다 모든 별칭을 포함한 인증서 하나를 발급하며, 유효 기간이 3분의 1 남으면 갱신합니다. DNS가 서버를 가리키지 않는 이름은 건너뛰었다가 가리키게 되면 추가하며, 패널에 그 이유가 표시됩니다.
IPv6까지 확인
Let's Encrypt는 IPv6를 먼저 시도하므로 모든 AAAA 레코드가 서버를 가리켜야 합니다. WardPane은 인증서를 요청하기 전에 이를 확인합니다.
IP용 인증서
서버 IP는 며칠마다 갱신되는 단기 인증서를 받습니다. https://<ip>:1500의 패널이 경고 없이 열립니다.
Let's Encrypt 요청 한도
패널은 중복 인증서를 요청하지 않고, 한 주문에서 실패한 이름을 한꺼번에 보고하며, 실패할 때마다 더 오래 기다리고, 비활성화된 ACME 계정을 교체합니다.
클릭 한 번으로 Cloudflare 토큰
Cloudflare 토큰 만들기 버튼을 누르면 필요한 권한이 미리 채워진 상태로 Cloudflare가 열립니다. 토큰을 다시 붙여 넣으면 패널이 사이트의 영역을 확인하고 수정할 수 있습니다.

보호

각 사이트에는 고유한 검사가 있으며, PHP나 Node.js가 요청을 보기 전에 웹 서버 안에서 실행됩니다. 주소는 명백한 공격을 했을 때만 차단됩니다.

지역 규칙: 국가 그룹, 예외, 최종 국가 목록
Bot Fight 설정: 봇 범주, IP로 검증된 크롤러, 공개 IP 피드, 탐색 요청, 페이로드, 스캔 탐지
요청 속도 제한과 차단
각 주소는 기본적으로 10초에 요청 150개까지 보낼 수 있습니다. 제한을 넘으면 404를 받고 설정한 시간(분)만큼 차단됩니다. IPv6 방문자는 /64 단위로 집계하고 차단하므로 주소를 바꿔도 소용이 없습니다. 사이트마다 허용 목록이 있습니다.
Bot Fight
AI 크롤러, SEO 크롤러, 취약점 스캐너, 스크립트와 헤드리스 브라우저, 빈 User-Agent, 직접 만든 목록을 차단합니다. 검색 엔진과 링크 미리보기는 선택한 경우에만 차단합니다. 모니터링 서비스와 RSS 리더는 건드리지 않습니다.
탐색 요청과 공격 페이로드
사이트에 존재하지 않는 /.env, /.git, /wp-login.php 같은 이름을 요청하면 그 주소를 차단합니다. URL 안의 명백한 SQL 인젝션, XSS, 경로 탐색, Log4Shell 페이로드는 차단으로 이어지고, 애매한 경우에는 해당 요청만 거부합니다.
스캔 탐지
연속된 다수의 실패 요청(기본값은 60초에 25회)은 gobuster나 ffuf처럼 보이므로 그 주소를 차단합니다. 없는 이미지는 실패 1회의 10분의 1로 계산하므로, 깨진 그림이 있는 오래된 페이지는 스캔으로 보지 않습니다.
검증된 크롤러
Google, Bing, DuckDuckGo, Apple, OpenAI, Anthropic, Perplexity, Ahrefs는 자신의 IP 대역을 공개합니다. WardPane은 이를 매일 내려받아, 다른 주소에서 이들 중 하나라고 주장하는 요청을 차단합니다. 이 크롤러들이 브라우저 User-Agent로 위장하더라도 IP로 차단할 수 있습니다.
공개 IP 피드
매일 갱신되는 Spamhaus DROP, FireHOL level 1, blocklist.de를 스위치 하나로 사이트별로 적용합니다.
그룹 단위 지역 규칙
국가를 하나씩 또는 그룹으로 허용하거나 거부합니다: 구소련, CIS, EAEU, EU, EEA, 솅겐, NATO, G7, G20, OECD, BRICS, SCO, ASEAN, 아랍연맹, 메르코수르, 대륙 등. 예외를 추가하고 최종 국가 목록을 확인할 수 있습니다.
호스팅 네트워크와 AS number
대부분의 자동화 트래픽이 나오는 AWS, Azure, Google Cloud, Hetzner, OVH, DigitalOcean, Vultr 및 기타 클라우드의 요청이나, 지정한 AS number의 요청을 차단합니다.
언어 필터
브라우저 언어에 따라 허용하거나 거부하며, 언어 정보를 전혀 보내지 않는 요청을 위한 별도 스위치가 있습니다. 예를 들어 VPN 뒤에 있는 경우처럼, 국가와 함께 쓰면 유용한 추가 신호가 됩니다.
기기
Windows, macOS, Linux, Android, iOS 또는 기타 기기만 허용하여 일반 브라우저를 위한 필터로 사용합니다.
링크 전용
필수 URL 매개변수: 광고에서 온 ?ref=metaads처럼 내 링크로 들어온 사람에게만 사이트가 열립니다. 서명된 쿠키와, 선택적으로 방문자 IP가 접근을 유지합니다. 웹훅과 결제 콜백 경로는 열려 있습니다.
비밀번호
초안과 사이트 테스트 사본용 HTTP Basic 로그인. 비밀번호는 scrypt 해시로 저장되며, 다른 모든 필터를 거친 뒤 메인 스레드 밖에서 확인합니다.
핫링크 방지
다른 사이트가 내 이미지와 파일을 삽입할 수 없습니다. 확장자, 허용 사이트(와일드카드 사용 가능), Referer가 없는 요청의 처리 방법을 선택하십시오.
보안 헤더
사이트별 X-Frame-Options, Referrer-Policy, includeSubDomains와 preload를 포함한 HSTS, Content-Security-Policy, Permissions-Policy.
허니팟
robots.txt가 금지하는 경로입니다. 사람은 이 경로를 열지 않으므로, 이를 요청한 쪽은 즉시 차단됩니다.
사용자 지정 차단 페이지
기기, 봇, 지역, 링크 전용 차단에 대해 직접 만든 페이지와 상태 코드(404, 403 또는 200)를 no-store로 제공합니다.
전역 차단 목록
모든 사이트에서 차단되는 주소와 네트워크로, 디스크에 저장되어 재시작 후에도 유지됩니다. 보호가 꺼진 사이트에도 적용됩니다.

트래픽 제어

각 사이트에 누가 접근할 수 있는지, 규칙이 어떤 순서로 적용되는지, 차단된 방문자가 무엇을 보는지 정합니다.

모든 요청에 적용되는 검사 순서

  1. Cloudflare: 실제 방문자 IP, Cloudflare를 통해서만
  2. 전역 차단 목록, 그다음 사이트 허용 목록
  3. 요청 속도 제한과 활성 차단
  4. Bot Fight: User-Agent, 검증된 크롤러, IP 피드, 탐색 요청, 페이로드, 스캔, 허니팟
  5. 지역: 국가와 그룹, 호스팅 네트워크, AS number, 브라우저 언어
  6. 기기
  7. 보안 헤더와 핫링크 방지
  8. 링크 전용
  9. 비밀번호
  10. .htaccess 규칙, 그다음 핸들러: 파일, PHP 또는 Node.js
Cloudflare를 인식하는 실제 IP
방문자 주소는 연결이 실제로 Cloudflare에서 온 경우에만 CF-Connecting-IP에서 가져옵니다. 네트워크 목록은 cloudflare.com에서 매일 갱신됩니다.
Cloudflare를 통해서만
서버 IP로 직접 들어온 요청은 404를 받으므로 누구도 CDN과 그 규칙을 건너뛸 수 없습니다.
스위치를 끈 경우
Cloudflare 뒤에 있지만 그렇게 표시되지 않은 사이트도 Cloudflare 주소를 절대 차단하지 않으며, Cloudflare 서버마다 10배 높은 제한을 적용합니다. 해결 방법은 로그에서 제안합니다.
Cloudflare Workers
Worker에서 온 요청은 해당 영역 단위로 일반적인 제한과 차단을 적용해 집계하며, 내 영역의 Worker는 Cloudflare로 취급합니다.
차단 페이지 코드
빈 주소처럼 보이려면 404, 요청을 거부했다고 알리려면 403, 직접 만든 페이지를 보여 주려면 200을 사용하십시오. 요청 속도 제한에 걸리거나 차단된 클라이언트는 항상 단순한 404를 받습니다.
캐시에 안전한 응답
링크 통과 여부에 따라 달라지는 응답에는 Cache-Control: private와 Vary: Cookie가 붙으므로, CDN이 링크 없는 사람에게 이를 넘겨주는 일이 없습니다.

패널 보안

패널은 권한 없는 사용자 wardpane으로 실행되며, 로그인 페이지에는 무차별 대입 공격에 대한 자체 제한이 있습니다.

root 로그인
원하면 서버의 root 비밀번호로 root로 로그인할 수 있습니다. 비밀번호는 패널만 열 수 있는 소켓의 작은 root 도우미를 통해 unix_chkpwd가 확인합니다. 기본적으로 꺼져 있습니다.
무차별 대입 제한
5회 실패하면 해당 주소(IPv6는 그 /64)를 15분간 차단하고, 50회 실패하면 그 /48을 차단합니다. 여러 주소에서 실패가 몰려오면 알 수 없는 주소의 로그인을 5분간 막습니다. 최근 30일 안에 로그인한 주소는 계속 사용할 수 있습니다.
IP 허용 목록
PANEL_ALLOW_IPS가 설정되어 있으면 패널은 다른 주소에 전혀 응답하지 않습니다. 현재 사용 중인 주소를 차단하게 되는 목록은 거부합니다.
root 도우미 격리
패널은 원하는 상태를 기록하고, systemd가 시작한 root 도우미가 사용자, 폴더, 유닛을 만들기 전에 모든 값을 다시 확인합니다.
샌드박스로 격리된 PHP와 Node.js
사이트별 Linux 사용자, 읽기 전용 시스템, 전용 /tmp, 새 권한 획득 금지, 메모리 및 CPU 제한, 선택적으로 외부로 나가는 연결 차단.
릴리스 체크섬
모든 아카이브는 SHA-256 체크섬과 함께 공개되며, 전체 소스 코드를 담고 있습니다. 설치 프로그램은 HTTPS로 내려받은 뒤 무엇이든 실행하기 전에 SHA-256을 확인합니다.
되돌릴 수 있는 업데이트
업데이트할 때마다 복원 스크립트가 포함된 백업을 만들고, 새 버전이 시작되는지 확인하며, 시작되지 않으면 스스로 롤백합니다.
접근 복구
스스로 접근이 막혔다면 서버에서 명령어 하나로 패널 로그인과 IP 허용 목록을 초기화하고 로그인 차단을 해제할 수 있습니다.
보안 섹션: 전역 차단 목록, 업데이트 날짜가 표시된 크롤러 IP 목록, IP 조회

다음 계획

이 기능들은 2.0 이후 릴리스에 계획되어 있으며 2.0에는 포함되어 있지 않습니다.

전체 로드맵 보기
  1. 2.1데이터베이스와 사이트 설정 파일MySQL과 MariaDB: 데이터베이스, 사용자, 권한 · nginx 스타일 구문의 사이트별 설정 파일, 양식과 동기화 · gzip과 brotli, 로테이션되는 접근 로그, location 블록
  2. 2.2사용자OS 비밀번호로 로그인 · 자신의 사이트만 보는 사용자 · root가 정하는 권한, 도움을 위해 사용자로 로그인
  3. 2.3초보자를 위해첫 로그인 시 설정 마법사 · 간단 모드와 전문가 모드 · 클릭 한 번으로 적용하는 보호 프리셋 · 수정 버튼이 있는 상태 점검과 더 풍부한 대시보드
  4. 2.4인증서와 DNSSSL 인증서 섹션 · 자체 DNS 서버와 네임 서버 · Cloudflare DNS 동기화 · Cloudflare로 로그인
  5. 2.5메일메일 도메인, 메일함, 별칭 · Postfix, Dovecot, Rspamd, DKIM · Roundcube 웹메일

여분의 서버에서 사용해 보십시오

깨끗한 Ubuntu 24.04에서 설치는 몇 분이면 끝납니다.