June 8, 2026

After Installation, How WP Panel Protects Your Server Through Multiple Layers

Responding to "Will the panel secretly change passwords or inject trojans?" and "Is the panel secure when the server is not compromised?"

I. Introduction

In the first article, we proved that WP Panel's installation script is transparent, it will not tamper with your server password, hack WordPress, or delete Nginx. But after installation, new questions naturally arise:

  • After the panel is running, will it secretly change my password?
  • The panel has automatic updates; could it be hijacked to inject trojans?
  • My SSH password hasn't been leaked. Is the panel itself secure enough?

This article willfrom the source code leveldissect all runtime behaviors of WP Panel after installation, explaining how itslayers of protectionwork, and why, without a server password leak, it is nearly impossible for attackers to compromise your server through the panel.


2. Can the panel secretly change passwords?

2.1 Password Storage: Even the Panel Cannot See Plaintext

WP Panel uses a two-layer authentication system:

LayerPurposeStorage method
Layer 1 — BasicAuthBrowser popup, intercepts first-layer scansbcrypt hash stored in config.json
Layer 2 — Web LoginPanel form loginbcrypt hash stored in SQLite database

What is bcrypt?It is aone-way password hashing algorithm. The password you input is computed into a string starting with $2a$12$, a process that isirreversible— even if someone obtains the database and configuration files, theycannot reverse-engineer your original password。

When verifying login, the panel does only one thing:

bcrypt.CompareHashAndPassword([]byte(存着的哈希), []byte(你输入的密码))

Match and pass, or mismatch and reject.The panel never saves, never prints, and never transmits your plaintext password.

2.2 Under what circumstances can the password be changed?

The only path in the code that can modify the password is as followsThree, all requireyou to manually trigger:

methodsTrigger conditionWho can execute
Panel settings page modificationLog in to panel → Settings → Change passwordAdministrator who knows the current password
CLI one-click resetExecute via SSH on the serverwp passwordServer root user
CLI only changes password, keeps usernameExecute via SSH on the serverwp-panel --passwd="新密码"Server root user

Why inputwp password, but the actual command executed is different?

wp is acommand wrapper script(stored in/usr/local/bin/wp), which wraps complex underlying commands into easy-to-remember daily instructions. The mapping is as follows:

Command you inputActual underlying command executedDifference in effect
wp passwordwp-panel --reset-adminReset both username and password(username restored towpadmin, password randomly generated)
wp-panel --passwd="xxx"wp-panel --passwd="xxx"Only change password, keep current username

In other words,wp password is more suitable for emergency situations like "I'm locked out, one-click recovery"; whilewp-panel --passwd="xxx" is suitable for scenarios like "I know the current username, just want to change the password". Both are real, but one is a shortcut for humans, and the other is a low-level interface for those who need fine-grained control.

Key conclusion:

  • No scheduled tasks will automatically change passwords in the middle of the night.
  • No remote commands can modify your password remotely.
  • There is no "backdoor password" or "universal key."
  • PanelDoes not send to any serveryour password or password hash.

2.3 If the password is indeed changed, the more likely reasons are...

If your server password is changed after installing the panel, the troubleshooting sequence should be:

  1. SSH key leakage — Check ~/.ssh/authorized_keys for unknown public keys
  2. Use of weak passwords — Whether the server root password is in a dictionary
  3. Installation of other software — Suspicious processes outside the panel
  4. Is the cloud service provider console compromised — Reset password without leaving traces via VNC/console

In the panel codenot a single lineinvolves modifying/etc/shadow、/etc/passwd or SSH configuration. This can be verified through a full-text search.


3. Will the panel implant viruses or trojans?

This is the most critical and reasonable concern. A program that runs in the background with auto-update capability theoretically does pose a risk of being exploited. We need to analyze fromupdate mechanism和runtime constraintstwo dimensions.

3.1 Auto-update mechanism: Triple independent verification

WP Panel's update functionality is implemented inhandlers/update.go, with the following process:

用户点击"更新面板" → 下载新二进制 → SHA256校验 → Ed25519签名校验 → 预检执行 → 备份旧版 → 替换 → 重启

First layer: SHA256 integrity check

After download completes, the panel simultaneously downloads a.sha256 file that records the correct hash value. The panel recalculates the SHA256 of the downloaded file,terminates immediately if mismatch。

if err := verifySHA256(newBinary, shaFile); err != nil {
    fail(http.StatusInternalServerError, "校验失败")
    return
}

This ensures the file has not been tampered with or corrupted during transmission by a man-in-the-middle.

Second layer: Ed25519 digital signature

SHA256 can only ensure file integrity, but cannot prove the file source. Therefore, the panel also introduces Ed25519 asymmetric signature:

  • public keyhardcoded in the panel source code (releasePubKeyHex = "ee8ec641...")
  • private keyis kept offline by the author, not on GitHub, CI, or any server
  • Each release, the author uses the private key to sign the .sha256 file, generating .sha256.sig
  • The panel uses the built-in public key to verify the signature. If verification fails, the update is terminated.
if err := verifyEd25519(shaFile, sigFile); err != nil {
    fail(http.StatusInternalServerError, "签名校验失败")
    return
}

What does this mean? Even if an attacker hijacks GitHub Releases and uploads a malicious binary, without the author's private key, they cannot generate a valid Ed25519 signature, and the panel will refuse to install it.

Third layer: Preflight

Even after passing the first two layers of verification, the panel executes a preflight:

if err := preflightBinary(newBinary); err != nil {
    fail(http.StatusInternalServerError, "新版本预检失败")
    return
}

The preflight runs the --info parameter attached to the new binary to confirm it can start normally and will not crash immediately. If the new binary has been tampered into a non-executable junk file, this step will intercept it.

Backup and Rollback

After all the above verifications pass, the panel performs the replacement, and before replacement, a backup is always made:

backupPath := versionedBackupPath(h.CurrentVersion)  // /usr/local/bin/wp-panel.bak.v1.2.3.20240101-120000
if err := copyFile(installPath, backupPath, 0755); err != nil {
    fail(http.StatusInternalServerError, "备份旧版本失败")
    return
}

If permission setting fails after replacement, the panel will automatically roll back:

if err := os.Chmod(installPath, 0755); err != nil {
    if rbErr := copyFile(backupPath, installPath, 0755); rbErr != nil {
        fail(http.StatusInternalServerError, "替换后权限设置失败,且自动回滚失败")
        return
    }
    fail(http.StatusInternalServerError, "替换后权限设置失败,已回滚")
    return
}

3.2 The panel does not have "remote code execution" capability

WP Panel is written in Goand compiled into a statically linked binary, which means:

  • It does not depend on a runtime interpreter (such as PHP, Python, Node.js) and cannot be "injected with scripts".
  • It has no eval()、system()functions that can execute arbitrary strings
  • All system command calls go through a executor/commander.gowhitelist mechanismwhitelist mechanism

How strict is the whitelist mechanism? Below are some representative commands (the full whitelist contains 20+ system commands):

Allowed commandsAllowed parameters
systemctlstart, stop, reload, restart, enable, disable…
nginx-t, -s, -c
mysql-u, -p, -e, -h, -P
wget-q, -O, -T, -t (and URL must be HTTPS + whitelisted domain)
curl-s, -o, -f, -L, -X, -H, -d (and URL must be HTTPS + whitelisted domain)
unzip-o, -q, -d
fail2ban-clientset, unban, status, banip…

Dangerous characters are globally filtered:;, |, &, `, $, <, >any characters that could be used to construct a shell injection will be directly rejected.

func hasUnsafeArgs(binary string, args []string) bool {
    for _, arg := range args {
        if strings.ContainsAny(arg, ";|&`$<>") {
            return true
        }
        // wget/curl 的 URL 必须是 HTTPS 且来自白名单域名
    }
}

3.3 File management has a "cage"

The panel provides a file manager, but all file operations are restricted to the website root directory:

func isPathWithin(basePath, targetPath string) bool {
    // 解析符号链接,防止用软链接跳出目录
    base, _ := filepath.EvalSymlinks(filepath.Clean(basePath))
    target, _ := resolvePathForAccess(targetPath)
    
    // 计算相对路径,确保目标在 base 之内
    rel, _ := filepath.Rel(base, target)
    return rel == "." || (rel != ".." && !strings.HasPrefix(rel, ".."+string(filepath.Separator)))
}

Security Points:

  • Even if you log in through the panel, you cannot access /etc/shadow、/root/.ssh/、/www/server/panel/config.jsonsensitive paths such as
  • operations such as upload, download, delete, and decompress will first go throughisPathWithin()check,unauthorized access directly returns 403
  • symbolic links will beEvalSymlinksresolved to the real path,cannot bypass directory restrictions using soft links

3.3.1 File Lock

File Lock is a „file write protection enhancement“ enabled at the site level. It requires the WordPress site to meet site_type = wordpress, and write websites table file_lock_enabled and file_lock_enabled_at。

Write scope when locked (runtime)

After enabling the lock, path writing must not only pass the isPathWithin() root directory check, but also satisfy additional rules:

  • Allowed writes:/www/wwwroot/<site>/wp-content/... runtime directory data under
  • Forbidden writes:
    • wp-content/plugins
    • wp-content/themes
    • wp-content/mu-plugins
    • wp-content/upgrade
    • wp-content/upgrade-temp-backup
  • Forbidden to modify configuration files:wp-config.php、.user.ini、.htaccess (site root directory) and php.ini、wordfence-waf.php
  • By default, creating/modifying PHP executable files is prohibited (.php、.phtml、.phar)
  • When file locking is enabled, manual configuration of wp-config.php existing DISALLOW_FILE_MODS = false sites is denied to avoid conflicts with panel behavior.

Direct interception of file lock on interfaces

After locking, the maintenance entry for 423 (Locked) is denied, including:

  • POST /websites/:id/db-password
  • POST /websites/:id/fix-wp-config
  • POST /websites/:id/install-plugin
  • POST /websites/:id/wp-optimizations
  • POST /websites/:id/reinstall
  • POST /api/cache/helper/optimizer-settings

The return text is consistent with the frontend text:

This site has file locking enabled. Please disable file locking before performing this maintenance operation.

Integration with file management

When locked, file management write actions (upload, upload chunk completion, delete, rename, create directory, compress, decompress, copy, move, archive import, etc.) will uniformly go through checkFileLockWrite。

When the target write path does not meet the rules, return:

This site has file locking enabled. Only writing to the runtime data directory under wp-content is allowed, and writing PHP executable files is prohibited.

This means: file locking is an additional restriction on write behavior beyond path isolation, not a replacement.

Code-level implementation

  • When enabled, wp-config.php write managed block (WP Panel File Lock)
    • define('DISALLOW_FILE_MODS', true);
    • define('FS_METHOD', 'direct');
  • When disabled, remove the managed block and restore the normal permission model.
  • Enabling/disabling triggers a site permission refresh and checks that critical paths (such as wp-config.php、wp-content/{plugins,themes,mu-plugins}) do not contain suspicious symbolic links.

3.4 Download Sources Locked Down

All download URLs in the panel (WordPress core, plugins, themes, update packages) are restricted towhitelist domains:

func isAllowedDownloadURL(raw string) bool {
    u, err := url.Parse(raw)
    if err != nil || u.Scheme != "https" || u.User != nil {
        return false
    }
    switch strings.ToLower(u.Hostname()) {
    case "wordpress.org", "downloads.wordpress.org", "api.wordpress.org",
         "www.cloudflare.com", "developers.google.com", "www.bing.com":
        return true
    default:
        return false
    }
}
  • must useHTTPS
  • embedding username and password in URL is not allowed (u.User != nil)
  • domains not in the whitelistare all rejected

4. How secure is the panel when the server password is not leaked?

Assuming your SSH root password, key, and cloud service provider console are not leaked, the attacker can only access your server through the network. WP Panel buildssix layers of defense in depth。

4.1 Stealth Layer: Make Attackers Unable to Find the Door

Random Entry Path

During installation, the panel generates a8-character random suffix(e.g.,a3b9c2d1), and the panel address becomes:

https://你的IP:8443/a3b9c2d1/login

Accessing without this suffix returns 404 directly. Attackers trying to brute-force this path:

  • The suffix is generated by SHA256 hash, each character is 0-9 a-f, 16 possibilities
  • Total combinations for 8 characters = 16^8 ≈4.3 billion
  • Purely mathematically, 10,000 scans per second would take about 5 days to exhaust—but the scan defense blocks the IP for 30 days on the first non-browser request, making actual attacks infeasible.

8443 Non-Standard Port

The panel uses port 8443 instead of the common 80/443/8080/8888, which alone filters out 99% of internet mass scanners.

Scan Defense: Non-browser direct ban for 30 days

If someone tries to scan port 8443 with a script, the panel's first line of defense is not login verification, but middleware/scan_defense.go:

func ScanDefense(db *sql.DB, randomSuffix string) gin.HandlerFunc {
    return func(c *gin.Context) {
        path := c.Request.URL.Path
        // 如果路径不是以随机后缀开头
        if !strings.HasPrefix(path, legitPrefix) {
            // 检查 User-Agent 是否是浏览器
            if !isBrowserLike(c) {
                // 不是浏览器?直接封禁 IP 720 小时(30 天)
                banScanIP(db, c.ClientIP(), "高危扫描: 非浏览器特征探测面板端口", 720)
                c.AbortWithStatus(http.StatusForbidden)
                return
            }
        }
        c.Next()
    }
}

What does this mean?An attacker scans your panel port with Nmap, Dirbuster, or Python scripts, and the User-Agent lacks Mozilla、Chrome、Safaribrowser identifiers such as The IP will be immediately written to the firewall blacklist and banned for 30 days.。

4.2 Authentication Layer: Two Password Gates

Even if an attacker knows your random entry point, they still need to break through two layers of authentication:

Layer 1 — BasicAuth (browser popup)

  • Username/Password verified using bcrypt
  • 5 consecutive failures, IP banned for 24 hours
  • Failure records are written to the database and synchronized to the system firewall by fail2ban

Layer 2 — Web Login (panel form)

  • A separate set of username/password
  • Also verified using bcrypt
  • Also has a 5-failure ban mechanism
  • Session is granted only after passing

Why two layers?Even if the BasicAuth password is leaked for some reason (e.g., the browser saved the password and someone else saw it), the attacker still needs the second-layer password to enter the panel. This is not over-engineering, but defense in depth。

After successful login, the panel issues a Session Cookie:

http.SetCookie(c.Writer, &http.Cookie{
    Name:     "wp_session",
    Value:    session.Token,     // UUID 随机字符串
    MaxAge:   1800,              // 30 分钟
    Path:     "/",
    HttpOnly: true,              // JavaScript 无法读取
    Secure:   true,              // 仅 HTTPS 传输
    SameSite: http.SameSiteLaxMode,
})

Security Features:

  • HttpOnly: Even if the website has an XSS vulnerability, JavaScript cannot read this cookie
  • Secure: Only transmitted over HTTPS encryption, not intercepted in plaintext by a man-in-the-middle
  • Sliding Renewal: Each time a valid page is accessed, the validity period is automatically extended by 30 minutes
  • Server-side storage: Sessions are stored in the panel's memory,not persisted to disk.After a restart, all sessions become invalid and require re-login.

Additionally, allwrite operations(modifying configurations, deleting files, creating sites, etc.) must also carry aCSRF Token:

func CSRF() gin.HandlerFunc {
    return func(c *gin.Context) {
        // 读取 Header 中的 X-CSRF-Token
        headerToken := c.GetHeader("X-CSRF-Token")
        // 读取 Cookie 中的 csrf_token
        cookieToken, _ := c.Cookie("csrf_token")
        // 两者必须一致
        if headerToken != cookieToken {
            c.AbortWithStatusJSON(http.StatusForbidden, ...)
            return
        }
        c.Next()
    }
}

This preventsCross-Site Request Forgery attacks— attackers may trick you into clicking malicious links, but they cannot forge a valid CSRF Token.

4.4 Transport Layer: Encryption + Security Response Headers

The panel enforces the use ofHTTPS(port 8443) and sends the following security response headers:

Response HeaderPurpose
Strict-Transport-Security: max-age=31536000; includeSubDomainsTells browsers to only use HTTPS connections for the next year
X-Frame-Options: DENYPrevents the page from being embedded in an iframe, mitigating clickjacking
X-Content-Type-Options: nosniffPrevents browsers from guessing file types
Referrer-Policy: no-referrerDoes not leak the source page URL

4.5 Operation Layer: Even Inside the Panel, No Harm Can Be Done

Assume an extreme scenario: an attacker passes all authentication and enters the panel. What can they do?

File Management: Can only operate website files under/www/wwwroot/and backup directories under/www/server/panel/backups, and cannotaccess beyond authorizationsystem configuration files, other user data, or the panel's own configuration.

Command Execution: The panel has no "terminal" feature; all system operations are executed through encapsulated APIs, running on the underlyingexecutor/commander.gowhitelist.No entry point for entering any command。

Database: The panel itself uses SQLite to store configuration and logs; management of MariaDB is performed via the command line mysql client (with MYSQL_PWD environment variables), and the MariaDB root password only exists in config.json (permissions 600). Attackers can only manage databases corresponding to the website through the panel, and cannot directly obtain the MariaDB root password.

4.6 Network Layer: Firewall + Rate Limiting + Intrusion Detection

Nginx Rate Limiting:

  • Rate limit for unauthenticated WordPress users 60 requests/minute
  • No rate limit for authenticated users (to avoid false positives for normal users)

fail2ban Integration:

  • SSH brute force → automatic ban
  • Panel login failure → automatic ban
  • 404 scanning → automatic ban

nftables Firewall:

  • The panel's own scan defense and manual bans are directly written to nftables, blocking connections at the system level.

5. Is the software installed by the panel itself secure? — Software-level security protection

The previous chapters have proven that the panel itself does no harm. But another reasonable concern is:The software installed by the panel (Nginx, MariaDB, Redis, PHP-FPM, etc.) may have vulnerabilities. What has the panel done?

To answer this question, we first need to understand a core concept —

5.1 Let's put it plainly: Why does "updating software" equal "fixing vulnerabilities"?

You can think of your server as a house, and each running software (Nginx, PHP, database, etc.) is a door or window of the house.Software vulnerabilities are the cracks in the windows that are not closed tightly— hackers enter your house through these cracks.

The key point is:

The vulnerabilities known to hackers are also known to software vendors. Every "update" released by vendors is patching these discovered doors and windows.

For example:

Daily scenarioServer scenario
A security flaw has been discovered in a smart lock brand you installed at home.A remote code execution vulnerability (CVE) has been found in Nginx running on your server.
The vendor released a new firmware to fix the flaw.Debian/Nginx officially released a new version to fix the vulnerability.
You update the lock firmware → the door is secure again.You run apt upgrade nginx → the vulnerability is patched.
You never update → thieves know this model has a flaw and specifically target your lock.You don't update → hackers scan the entire internet for this Nginx version and easily break in.

The truth is: most hacked websites are not because hackers are skilled, but because site owners fail to update software in time.In 2023, a Wordfence report showed that over 60% of compromised sites in the WordPress ecosystem were due to unpatched known vulnerabilities—in other words, they wouldn't have been hacked if updates were applied on time.

Once you understand this basic logic, it becomes very clear what WP Panel does.

5.2 What exactly is the "System Update" in the panel?

When you open the "System Update" page in WP Panel, the panel performs the following check in the background:

问系统:"我们装的所有软件(nginx、php、mariadb、redis...),有没有新版本?"

System response:

  • No new version → displays "System is up to date"
  • New version available → lists updatable software and version numbers, for example:
    • nginx 1.24.0 → 1.26.0 (2 security issues fixed)
    • php8.3-fpm 8.3.6 → 8.3.8 (1 security issue fixed)
    • mariadb-server 10.11.6 → 10.11.8

Technically, the panel calls the Debian system's apt list --upgradable command (source code handlers/system_update.go), which queries the Debian official software repository for the latest version of each package—exactly the same principle as checking app updates on your phone's App Store.

5.3 One-click update: no need to learn command line, just click.

The traditional approach is: SSH into the server → type apt update → type apt upgrade -y → watch the screen and wait for results.

WP Panel turns these three steps intoone button (source code handlers/system_update.go:56-80). You just need to open the panel, click "System Update", and the panel will complete all operations automatically. For site owners who don't understand the command line,No need to learn any Linux knowledge to keep the server secure。

5.4 Automatic Alerts: You forget, but the panel remembers for you

This is the most critical and easily overlooked capability. People forget, but the panel doesn't.

WP Panel's alert system (executor/alert_monitor.go) automatically checks every 24 hours:

  • System Software Update Alerts: Are there new versions of nginx, php, mariadb, redis, etc. on the current server? If so, it reminds you.
  • Panel Update Alerts: Is there a new version of WP Panel itself? If so, it also reminds you.

If you have configured email notifications, you will receive an email like this:

⚠️ Your server has 12 available security updates: nginx, mariadb-server, php8.3-fpm, php8.3-cli, redis-server, openssl, libssl3…

This means: You don't need to proactively check the CVE database for "Is there a vulnerability in the nginx version I'm using?" — The Debian security team has already checked for you. They put the fix into the apt update, and the panel tells you "There's an update", you just click it.

5.5 Real Case: If a Log4j-level vulnerability occurs in your server components

At the end of 2021, the Log4j vulnerability (Log4Shell) was exposed, affecting millions of servers worldwide. Affected companies had towithin hoursfind all affected systems and update them — a day late could mean being compromised.

If a vulnerability of equal severity occurs in your server components (such as Nginx or PHP), WP Panel's process is as follows:

漏洞公开 → Debian 安全团队发布修复包 → 面板告警系统检测到可更新 →
→ 发送邮件/Webhook 通知你 → 你打开面板 → 点"系统更新" → 漏洞修复完成

Comparison with the situation without a panel:

漏洞公开 → 你完全不知道 → 几周后你的站被黑了 → 你才发现

The difference lies in "knowing whether there is an update" and "how simple the update operation is".

5.6 ProcessGuard: Automatically restart software if it crashes

In addition to vulnerabilities, software also hasoperational stabilityissues. The panel's ProcessGuard (executor/process_guard.go) checks every 30 seconds whether the following six key services are alive:

ServiceIf it crashes
NginxWebsite inaccessible → ProcessGuard automatically restarts
PHP-FPMWebsite white screen/error → ProcessGuard auto-restart
MariaDBDatabase unavailable → ProcessGuard auto-restart
RedisCache failure, website slows down → ProcessGuard auto-restart
nftablesFirewall failure → ProcessGuard auto-restart
Fail2banBrute force protection failure → ProcessGuard auto-restart

For beginners,you don't even need to know the names of these services—the panel silently guards them in the background. You can see the status of each service on the panel's "System Guard" page: green light = normal, red light = auto-restarted.

5.7 Software versions transparently visible

The panel displays the exact version number of each installed software on the "Software Management" page (handlers/software.go). If a critical vulnerability is disclosed one day, you can immediately confirm whether your server is affected:

  • CVE announcement says "Nginx versions before 1.24.0 affected" → You check the panel: mine is 1.26.0 → not affected, rest assured
  • CVE announcement says "PHP 8.3.0-8.3.7 affected" → You check the panel: mine is 8.3.1 → affected → one-click update immediately

No need to type commands to check versions, no need to remember software paths. Everything is visible on one page.

5.8 Are these software sources reliable?

All software installed by WP Panel comes from the Debian official repository or the Ondřej Surý PHP official source (source code install.sh:549-568), not packaged by the panel itself:

apt-get install -y nginx mariadb-server redis-server fail2ban nftables php8.3-fpm ...
  • Debian official repositoryMaintained by the Debian security team, each package has a GPG digital signature to ensure it hasn't been tampered with
  • Ondřej Surý PHP sourceis the most authoritative third-party source for PHP in the Debian ecosystem, also with GPG signature verification

The panel's role is not to "provide software" but to "help you manage these official software and notify you immediately when security updates are released."

5.9 One-sentence summary

Your concernActual situation
„What if the Nginx installed by the panel has a vulnerability?“Vulnerability exists → Debian official releases update → Panel automatically detects → Sends email/Webhook notification → You click one-click update → Vulnerability fixed. You don't need to know the technical details.
„I don“t know when to update„The panel helps you know. It automatically checks every 24 hours and notifies you of updates.
„I don“t know how to update„The panel helps you do it. One button, no command line needed.
„What if the software crashes?“The panel helps you restart. It automatically recovers within 30 seconds, and you might not even notice.

WP Panel does not introduce new vulnerabilities to the software—it installs software from official sources, and every package has signature verification. What the panel does islet you know about vulnerabilities faster and fix them more easily than manual management.。


6. Common Attack Scenario Simulation

To understand security more intuitively, we simulate several common attack methods:

Scenario 1: Brute Force Attack on Panel Login

Attacker's approach: Dictionary attack https://IP:8443/随机后缀/login

Result:

  • Unknown random suffix → Access / returns 404 directly, triggering scan defense and IP banned for 30 days
  • Known random suffix but unknown BasicAuth password → 5 failed attempts, IP banned for 24 hours
  • Bypassed BasicAuth but unknown web password → another 5 failed attempts, IP banned for another 24 hours
  • At 1 attempt per second, cracking a 16-character random password takeshundreds of millions of years

Conclusion: Pure network brute force attack isinfeasible。

Scenario 2: SQL Injection

Attacker's approach: Enter in the login box ' OR '1'='1

Result: The panel uses parameterized queries:

db.QueryRow("SELECT password_hash FROM admin_users WHERE username = ?", req.Username)

User input is treated asplain text parametersand will not be parsed as SQL statements.

Conclusion: SQL injectioninfeasible。

Scenario 3: Path Traversal (Download /etc/passwd)

Attacker's approach: Access via File Management API ../../../etc/passwd

Result:isPathWithin() function calculates the relative path, detects it jumps out of the website root directory, directly returns 403 Path Unauthorized。

Conclusion: Path Traversalinfeasible。

Scenario 4: Command Injection (Write in the domain input box ; rm -rf /)

Attacker's approach: Enter a malicious domain when creating a website

Result: All operations involving system commands go through executor/commander.go filtering:

  • Commands must be in the whitelist
  • Parameters cannot contain ;|&\$<>`
  • bash -c patterns that can execute arbitrary stringsDoes not exist at all

Conclusion: Command Injectioninfeasible。

Scenario 5: XSS (Cross-Site Scripting)

Attacker's approach: In "Panel Settings", change the panel title to <script>alert(1)</script>

Result:

  • The backend template uses Go's html/template,auto-escaping for HTML special characters, <script> will be rendered as plain text instead of executable scripts
  • Frontend data is transmitted via API JSON, and the browser renders it as text
  • Even if the frontend is bypassed, the Cookie is HttpOnly, so JS cannot read the Session

Conclusion: XSS cannot steal login credentials.


7. Will the panel really not "secretly contact external"?

7.1 Telemetry Reporting: Transparent Content, Can Be Disabled

The panel sends a "heartbeat" to stats.wp-panel.org every 24 hours, but the content only includes:

{
  "anonymous_id": "a1b2c3d4e5f67890",  // /etc/machine-id 的 SHA256 前 16 字节
  "version": "1.0.0"                     // 面板版本号
}

Does not include: IP address, domain name, number of websites, passwords, any business data.

Can be disabled: Disable "Anonymous Statistics" in the panel's "Security Settings", or in the database set telemetry_enabled to false。

7.2 Alert Notifications: Only Sent to You

Panel alerts (high CPU, SSL expiration, backup failure, etc.) are only sent to the actively configured email or Webhook. If you haven't configured SMTP or Webhook, alerts are only recorded in the local database and will not be sent out。

7.3 Update Check: Only Access GitHub

When checking for updates, the panel only accesses api.github.com to retrieve Release information. It will not download any update files unless you manually click "Update Now"。


8. What You Can Verify

If you are still concerned, you can audit it yourself using the following methods:

8.1 Check the panel's network connections

# 查看 wp-panel 进程建立了哪些网络连接
ss -tpn | grep wp-panel

# 或查看实时网络活动
lsof -i -a -c wp-panel

Under normal circumstances, you should only see:

  • HTTPS listening on local port 8443
  • Occasional connections to api.github.com(checking for updates)
  • If telemetry is enabled, once daily to stats.wp-panel.org

You should not see: connections to unfamiliar IPs, uploading large amounts of data, or persistent abnormal connections.

8.2 Check system scheduled tasks

# 查看面板创建的 cron 任务
cat /etc/cron.d/wp_panel_cron

# 查看系统级定时任务
crontab -l
ls /etc/cron.d/

The panel only writes cron files when youactively create scheduled tasks, and the content is completely transparent and readable.

8.3 Verify if binary files have been tampered with

# 计算当前面板的 SHA256
sha256sum /usr/local/bin/wp-panel

# 与 GitHub Release 上的校验值对比
# https://github.com/naibabiji/wp-panel/releases

8.4 View panel operation logs

The panel'sbackground task queue(backups, SSL renewal, firewall bans, scheduled task execution, etc.) is recorded in the operation_logs table. You can view it in "Panel Settings → Operation Logs". Additionally, login attempts, system alerts, etc., have their own separate record tables.

8.5 Disable telemetry

# 进入 SQLite 数据库
sqlite3 /www/server/panel/panel.db

# 关闭遥测
UPDATE security_settings SET svalue = 'false' WHERE skey = 'telemetry_enabled';
.quit

# 重启面板
systemctl restart wp-panel

IX. Summary

ConcernsFact
Will the panel secretly change passwords?❌ No. Password changes can only be made through the panel settings page (requires known password) or server CLI (requires root). There is no automatic password change mechanism.
Will automatic updates implant malware?❌ cannot. Updates require SHA256 + Ed25519 signature + pre-check triple verification, and the source must be GitHub Releases.
Is it safe when the server is not compromised?✅ Very safe. Six layers of defense in depth: concealment layer + two-factor authentication + Session/CSRF + HTTPS + operation isolation + firewall.
Will the panel secretly send data externally?❌ No. Telemetry only includes anonymous ID + version number, can be disabled; no other hidden network behavior.

WP Panel's security design follows a core principle:Defense in Depth. There is no single line of defense, but multiple layers stacked—attackers need to continuously breach random paths, browser detection, BasicAuth, web login, Session, CSRF, path isolation, command whitelist, firewall... Each layer is extremely difficult to bypass, and combined they form a very high security threshold.

More importantly, all code isopen source and auditable. Any claim that "the panel is insecure" should be specific to a line of code, a function, or a network connection. Vague "feeling insecure" cannot stand in the face of verifiable source code.


This article is based on the Go source code of the WP Panel open source repository. All referenced code snippets and file paths are publicly verifiable.

Host your WordPress site with WP Panel

Lightweight, secure, and always free. Already0serversare using WP Panel to manage WordPress sites. One-click site setup, multi-layer security, FastCGI full-page caching—only the features WordPress admins truly need.

Learn about WP Panel