Troubleshooting
Start from the console line, not the symptom — the resource names its own faults at boot and on every heartbeat.
On this page15 entries
Sculk tells you what is wrong if you read the two places it talks: the boot
output and the sculk status command. Most "it isn't working" reports are one
of the lines below.
§13.1First, read these
sculk # version, licence, tier, clients, bans
sculk detections # what is actually running, and at what action
§13.2It says No licence key set
sculk_license is missing, or it is placed after the ensure. server.cfg
runs top to bottom; every set must come first. It must be set, not setr.
§13.3Activation is rejected
- Key mistyped or wrong case — copy it from your account; the
key format is
SCULK-XXXX-XXXX-XXXX-XXXX. - Already bound elsewhere — a licence binds to a server identity. If you migrated hosts or your server id changed, reset the binding from your account page (one self-serve reset), or open a support ticket.
- Lapsed subscription — the licence stops working when a renewal fails. The
console says so plainly:
PROTECTION DISABLED. Renew and it re-activates on the next retry. See Plans, Billing & the Hard Stop.
§13.4protection: NOT ENFORCING
From 3.8.0 nothing acts without an active licence lease; the line after it
says why. no licence lease yet on a fresh install means activation has not
succeeded yet (see above). lease was issued to a different server means
.serverId changed — reset the binding from your account. lease expired without being renewed means the server could not reach Sculk for 72 hours:
check outbound HTTPS to www.sculkac.com. lease signature is not valid
almost always means sculk_api_url is set — remove it.
§13.5It is licensed but nothing is enforced
In order:
- Observation mode is on. With
set sculk_observe "true"inserver.cfg(the shippedserver.cfg.examplehas it), automatic kicks and bans are held and the console printsOBSERVE would kick …/OBSERVE would ban …instead, plus a reminder every 30 minutes with the count held so far. Runset sculk_observe falsein the live console to start enforcing — no restart — and remove the line fromserver.cfg. Staff bans and kicks are never held. - The detections you expect are at Log. The catalogue ships armed — mostly
Warn and Kick — so this means someone lowered them on the
dashboard, or the detection is capped (
sculk detectionsmarks capped actions with*). Raise the ones you trust. - The player is exempt. txAdmin's
commandACE exempts fully whileConfig.ExemptTxAdminis on (the default), as dosculk.bypassall(listed inConfig.BypassAcesout of the box), the legacysculk.bypass, and anything else you added toConfig.BypassAces. Exempt players log a[exempt:…]line instead of being acted on — test with a non-staff account. - The subscription hard stop is on.
sculkthen showslicensed: falseandlast error: expired, and the console printedPROTECTION DISABLED. See above. - The detection is on probation. New kick and ban paths in 3.9.0 act at
Warn until you release them, and the event says
[probation: would KICK …]. See Probation. - Client-side detections need the client half. A detection with
side = clientorbothonly fires if the player's game actually loaded the resource — and a stripped client is exactly whatantiBypassis for.
§13.6The boot output lists hardening gaps
That is the resource doing its job. Each line names a convar that is leaving a
hole open, with the value it wants. Copy the relevant block from
server.cfg.example. These prevent cheats at the engine level and are worth
more than any single detection.
§13.7False positives
sculk detections shows the evidence class each detection rests on, and the
pipeline already caps many of them below their configured action. When one is wrong for your server:
- Set it to Log on the dashboard, not off — you keep the visibility.
- Exempt the context, not the player, where possible: a radius zone that whitelists that detection for that activity.
- Custom weapon meta breaks
antiFastShoot/antiRapidFire/antiMagicBullet; setConfig.CustomWeaponMeta = true, or disable the fire-rate tables with the convars inserver.cfg.example. - Custom voice proximity breaks
antiGlobalVoice; raiseConfig.VoiceProximityMax(default 25) to your server's real ceiling.
Reviewing and clearing detections is what Staff Review covers, and clearing them teaches Sculk Mind.
§13.8/sculkpanel does nothing, or says you are not permitted
The panel is gated on sculk.admin (or whatever Config.Panel.Aces lists),
and Config.Panel.Enabled must be true:
add_ace group.admin sculk.admin allow
Restart the resource after adding the ACE. If the command exists but the panel
does not appear, check the client console for a NUI error — the panel is a NUI
page, and a broken NUI is also what antiNuiBlocker exists to catch.
§13.9A ban did not appear on the website
Bans sync on the heartbeat. If one is missing after a minute:
- Check
sculkfor the licence state and last error, and the boot line (Sculk AntiCheat vX.Y.Z starting. API: …) for the API the server is talking to. - The website and the resource must be reachable in both directions. A firewall that blocks outbound HTTPS from the game server stops sync silently.
- Lifted bans propagate the other way; if a lift has not reached the server, check the same connectivity.
§13.10Webhooks post twice, or not at all
Webhooks can be set as convars and on the dashboard. If you set both, every event posts twice — pick one. The dashboard is the better default because staff can change it without a restart. A webhook that does not post at all is usually Discord rejecting the payload's channel/format or a revoked URL; the resource logs the failure.
§13.11Screenshots never arrive
Both /sculkview and capture-on-action (Config.CaptureOnAction, off by default) need a capture provider installed and
started: screenshot-basic (or screencapture, screenshot-basic-updated,
sc_screenshot), or any folder you name with sculk_screenshot_resource. The
boot output prints Game-view capture provider: <name>., or warns that no
screenshot provider is started.
§13.12The VPN / proxy / country signals are quiet
Since 3.9.0 the lookup uses proxycheck.io over HTTPS by default, and its free
tier works (about 100 lookups a day without a key, about 1,000 with a free
account key: set sculk_iplookup_key "…", never setr). Every failure,
including a used-up quota, lets the player in, and the dashboard shows "IP
reputation lookup inactive". In 3.9.0 antiVPN is also on
probation: it logs who it would have
refused and lets them in until you release it.
§13.13The Discord bot does not respond
- The bot must be invited to your server and bound with
/bind, using a licence your guild owns. - If a licence holder has pulled the kill switch on bot writes, moderation through the bot stops. It is re-enabled from the account page.
- Lookups and moderation are scoped to the licence the guild bound; actions on servers the guild does not own are refused, by design.
§13.14Performance
The resource is built to sit near zero at rest: polling detections sleep, the
event-driven ones cost a handler, and the panel only refreshes while someone has
it open. If you see cost in resmon, it is almost always the entity
firewall or a zone with a very large radius, or sculk_debug left on.
§13.15Still stuck
Open a ticket from FiveM support with the boot output and the
result of sculk — both are what support will ask for first.
