/op and /deop — no password, no privilege changessecurity.password.pbkdf2_iterations)/op to a predefined set of player namesblocked_commands)blocked_op_commands)blocked_command_prefixes)minecraft:op or plugin aliases are caughtopshield.bypass) for trusted staffsecurity.lockout.max-attempts)security.lockout.track_ip)security.lockout.count_decay_hours)/opshield unlock <player|ip>shadow_ban.auto_punish_level is reachedauto_punish_level: 99 to keep decoy behaviour without escalationkick, ban, ban-ip, firewall, customProcessBuilder with configurable timeout{player} and {ip} placeholdersen), Vietnamese (vn), Russian (ru)language: "en" in config.ymlFiles.write() with explicit charset (fixed in 1.6.0)audit.max_file_size_mb and audit.log_retention (up to N backup files)audit.console_output: trueplugins/OPShield/audit.log, audit.log.1 … audit.log.N| Component | Version |
|---|---|
| Java | 21+ |
| Paper | 1.21+ |
| Folia | ❌ Not supported |
.jarplugins/ folderplugins/OPShield/config.yml to customise behaviour/opshield reload in-game or restart to apply changes ✅Tip: If you already have an
op_passwordplaintext value from an older version, OPShield will automatically migrate it toop_password_hashand remove the plaintext entry.
| Command | Description |
|---|---|
/op <player> [password] |
Grant OP with password verification |
/deop <player> [password] |
Remove OP with password verification |
/opshield reload |
Reload configuration |
/opshield unlock <player|ip> |
Clear all tracking state for a player or IP |
| Permission | Default | Description |
|---|---|---|
opshield.admin |
op | Grants all child permissions |
opshield.reload |
op | Reload OPShield configuration |
opshield.unlock |
op | Unlock a tracked player or IP |
opshield.op |
op | Use password-protected /op |
opshield.deop |
op | Use password-protected /deop |
opshield.bypass |
false | Bypass non-OP restricted command blocking |
Files generated under plugins/OPShield/:
config.yml — main configurationdata.yml — persistent runtime state (lockouts, shadow-ban levels, IP windows)languages/en.yml — English messageslanguages/vn.yml — Vietnamese messageslanguages/ru.yml — Russian messages# Password security
security:
lockout:
enabled: true
max-attempts: 3
duration-minutes: 3
track_ip: true
count_decay_hours: 168
password:
pbkdf2_iterations: 120000 # range: 10000 – 1000000
# Auto-punishment
auto_punishment:
enabled: true
threshold: 5
window_seconds: 300
command: "kick" # kick | ban | ban-ip | firewall | custom
firewall_timeout_seconds: 10
# Shadow ban
shadow_ban:
enabled: true
auto_punish_level: 3
# Audit log
audit:
console_output: true
max_file_size_mb: 5
log_retention: 3
Small server (≤ 20 players)
security.lockout.max-attempts: 3
security.lockout.duration-minutes: 5
ip_limit.max_accounts: 2
auto_punishment.enabled: false
Medium server (20–100 players)
security.lockout.max-attempts: 3
security.lockout.duration-minutes: 3
ip_limit.max_accounts: 3
auto_punishment.enabled: true
auto_punishment.command: kick
auto_punishment.threshold: 5
shadow_ban.auto_punish_level: 3
Large server (100+ players)
security.lockout.max-attempts: 2
security.lockout.duration-minutes: 10
ip_limit.max_accounts: 2
auto_punishment.enabled: true
auto_punishment.command: ban-ip
auto_punishment.threshold: 3
shadow_ban.auto_punish_level: 2
Firewall mode executes an OS script asynchronously. To enable it:
auto_punishment:
command: "firewall"
allow_unsafe_firewall_exec: true
firewall_timeout_seconds: 10
# Linux:
firewall_script: "iptables -A INPUT -s {ip} -j DROP"
# Windows:
# firewall_script: "netsh advfirewall firewall add rule name=OPShield dir=in action=block remoteip={ip}"
If allow_unsafe_firewall_exec is false, firewall mode falls back to a safe kick.
<details> <summary>Cannot use /op — "Incorrect password"</summary>
The password is required. Run:
/op <yourname> <password>
If you forgot the password, clear op_password_hash in config.yml and restart — a new password will be generated and printed in the console.
</details>
<details> <summary>Player is locked out and cannot try again</summary>
An admin can manually clear the lockout:
/opshield unlock <playername>
/opshield unlock <ip-address>
</details>
<details> <summary>Auto-punishment is not triggering</summary>
Check the following:
auto_punishment.enabled: true in config.ymlauto_punishment.sensitive_commandsshadow_ban.enabled — if true, the player may be getting fake success messages instead/opshield reload after any config change
</details><details> <summary>Audit log is empty or not updating</summary>
audit.console_output: true to confirm logging is activeplugins/OPShield/ folderSEVERE — check console output
</details><details> <summary>Config changes are not taking effect</summary>
Run in-game or console:
/opshield reload
</details>
/op?No — it intercepts and wraps it. The original /op behaviour is preserved but gated behind a password.
Yes — passwords are hashed using PBKDF2-HMAC-SHA256 with a random salt and 120,000 iterations (configurable). The plaintext is never written to disk.
Paper 1.21+ only. Spigot may work but is not tested. Folia is explicitly not supported (folia-supported: false).
Yes — set auto_punishment.enabled: false. Shadow-ban fake messages will still work independently.
Lockout state is persisted to data.yml and restored on startup. Players cannot bypass lockouts by crashing or restarting the server.
Yes — all three bundled files (en, vn, ru) are always present. Switch via language: in config.yml. Missing keys automatically fall back to the bundled English defaults.
Author: Duong2012G
License: Apache 2.0
Website: https://legacy.curseforge.com/members/duong2012g/projects
Built for secure, professional Minecraft servers.