RISE CRM Security: Stopping Brute Force Login Attacks
Stock RISE CRM security throttles nothing at the login screen. The five policy numbers to set, what an IP blacklist cannot do, and how to lock the API down.
Open your web server access log and grep for POST requests to the sign-in path. On a RISE install that has been publicly reachable for a few weeks you will find them: a few hundred an hour, sometimes a few thousand, each carrying a username like admin, info@yourdomain, or the email address printed on your contact page. Nothing in the CRM tells you this is happening. No email arrives. The attempts just fail, one after another, and keep failing until one of them does not. That is the practical starting point for RISE CRM security on a self-hosted box: the login form answers every request it is given, forever, and counts nothing.
We build and sell RiseGuard and the REST API plugin for RISE CRM, both named below, so weigh this accordingly. The reasoning about thresholds, blacklists and API exposure holds whatever you use to enforce it.
What a stock login screen does and does not count
A login form with no throttle is not a lock. It is a question the server answers as many times as you like. A single script at ten requests per second gets 864,000 attempts a day against one account; from forty hosts, thirty-four million. Against a genuinely random 16-character password that is still nowhere near enough, which is the reassurance most hardening guides stop at. Against Summer2024!, a password reused from a breach dump, or the credentials of the freelancer who left in March, it is more than enough.
Two details make the untuned case worse than the raw numbers suggest.
- Credential stuffing is not brute force. Modern attacks do not guess. They replay email and password pairs harvested from unrelated breaches, usually one or two attempts per account before moving on. None of that looks like hammering, so a naive “block after 100 failures from one IP” rule never triggers.
- The password reset form is a second, quieter door. It takes an email address, decides whether an account exists, and sends mail. Left uncapped it is both an enumeration oracle and a free outbound mailer anyone can point at anyone. A few thousand reset emails from your domain in an afternoon do more lasting damage to your deliverability than the login attempts ever do to your database.
The five numbers RISE CRM brute force protection actually needs
“Use a strong password” is advice for the person choosing the password, not for the administrator running the install. What an administrator decides is a policy expressed in numbers. RiseGuard exposes them as configurable Brute Force Settings and enforces them automatically, so the decision stays yours and the enforcement stops being your problem:
| Setting | Sensible starting value | Why that number |
|---|---|---|
| Max login retries | 5 | Survives a fat-fingered password and a stale saved credential in one sitting. Below 4, real staff get locked out weekly. |
| Lockout period | 15 minutes | Long enough to cut an automated run from thousands of attempts an hour to twenty. Short enough that nobody phones you. |
| Max lockouts | 3 | Three separate lockouts is no longer a forgetful human. It is a pattern. |
| Extended lockout | 24 hours | The response to that pattern. Cheap for you, expensive for the attacker’s throughput. |
| Password reset retries | 3 | Caps enumeration attempts against a single address before the form stops answering. |
The sixth control is the one people leave until after they have been burned: max email sendings. Capping outbound volume means that even with every other threshold set too loosely, an attacker cannot turn your CRM into a spam cannon and get your sending domain blocklisted. If you change one setting today, change that one - it is the failure whose consequences outlive the attack by months.
The trade-off nobody mentions
Per-account lockout is weaponisable. Someone who knows your sales director’s email address can deliberately fail five logins every fifteen minutes and keep that account permanently locked without coming close to guessing the password. That is why the numbers above are moderate rather than aggressive. Set max retries to 2 with a 24-hour lockout and you have not built a fortress - you have built a denial-of-service button and handed it to the internet. Keep the retry counter tight, the lockout period short, and let the max-lockouts-plus-extended-lockout pair do the escalating.
IP and user blacklists: surgical, not a firewall
Beyond login throttling, RiseGuard supports IP, IP range and user blacklists that keep specific addresses and accounts away from the installation entirely. They are excellent at three jobs and poor at everything else:
- A single persistent source. One address generating thousands of attempts over several days is worth blocking outright rather than repeatedly locking whichever accounts it targets.
- A hosting or scanner range. When the reports show a
/24belonging to a bulk VPS provider no staff member or client will ever legitimately use, the range blacklist strips that noise out of your logs so real signal becomes visible. - A user you have already offboarded. The user blacklist is the fastest way to be certain a specific account cannot authenticate at all while you work out what else that person still reaches.
Where a RISE CRM IP blacklist will not save you: a credential-stuffing run spread across residential proxies, where every request arrives from a different address that also serves real broadband customers. You cannot block your way out of that, and trying eventually blocks a client. Distributed attacks are what the retry and lockout counters exist for.
Read the reports before you tune anything
Do not pick thresholds on day one and walk away. RiseGuard’s Reports section records login attempts, lockouts and password resets - the only honest basis for a policy. Give it a week of real traffic, then read it with two questions in mind:
- Are the lockouts happening to names you recognise? If your own staff appear repeatedly, either the retry counter is too tight or somebody has a stale password saved in a mail client retrying in the background. Fix the client. Do not loosen the policy to accommodate a misconfiguration.
- Are the failed attempts clustered or spread? Clustered by address means blacklist candidates. Spread thinly across hundreds of addresses means credential stuffing, and your defence is the account-level counter plus password hygiene, not blocking.
Restrict who can change these settings while you are in there. RiseGuard’s permissions limit the security configuration to trusted staff, which matters more than it sounds: a policy anyone can relax is a suggestion.
One server prerequisite before you install anything: RiseGuard requires PHP’s allow_url_fopen to be enabled, and most hosts enable it by default. Worth being straight about the tension - that is a setting general PHP hardening guides often tell you to switch off, because it widens the blast radius of a remote-file-inclusion bug anywhere on the box. If yours is already on, as most are, this changes nothing. If you deliberately disabled it during a hardening pass, treat turning it back on as a decision rather than a checkbox.
The other half: what an authenticated integration can read
Login hardening protects the front door. It does nothing about the keys you have already handed out, and this is where otherwise careful installs quietly lose ground. An API key is a credential that never expires, never gets a lockout, and usually lives in plaintext inside somebody’s automation tool.
The REST API plugin for RISE CRM is built with that asymmetry in mind. Four behaviours are worth knowing whether you are auditing an install or planning one:
- Key management is administrator-only, so keys cannot be minted by a staff member who happened to get curious.
- Sensitive fields are withheld at the source. As of 2.1.0, password hashes, payment gateway credentials and staff personal data such as SSN or salary fields are not exposed through the API at all. That is a real reduction in what a leaked key is worth - the worst case stops well short of “attacker now has your gateway credentials”.
- The MCP server ships off. It lives at
/api/mcp, is disabled by default, and is switched on from the API settings screen that only administrators can open. Every tool it publishes is permission-filtered, so an AI assistant reaches only what its key allows. Confirm yours is still off if nothing you run needs it. - Webhook payloads are HMAC-SHA256 signed, with per-webhook delivery logs for auditing. Verify the signature on your side: an endpoint that accepts anything shaped like JSON is a way into your systems, not a way out of the CRM.
Read-only activity log endpoints round it out, letting your monitoring pull CRM-side audit data into whatever you use for alerting. The rule that follows from all of it: one key per integration, never a shared master key. When the accounting sync gets replaced next year you revoke one key and nothing else breaks. When a laptop holding a saved credential goes missing, you know precisely what it could reach.
One measure belongs in front of all of this: rate limit the sign-in path at the reverse proxy. Application counters act per account, a proxy limit acts per connection and blunts the volume before PHP is invoked at all. Complementary, not redundant.
Your first hour, in order
- Grep the access log for POST requests to the sign-in path over the last seven days and count them. That number is your baseline.
- Set max login retries to 5 and the lockout period to 15 minutes. Do not go tighter yet.
- Set max lockouts to 3 with a 24-hour extended lockout, and cap password reset retries at 3.
- Set the outbound email cap. This is the one protecting your sending domain.
- Leave it for seven days, then read the reports and adjust once, based on whether real staff appear in the lockout list.
- Blacklist only what the reports name - persistent individual addresses and obvious hosting ranges. Nothing speculative.
- List every API key and the integration it belongs to. Any key you cannot attribute gets revoked today, not investigated later.
If step 7 turns up a key nobody can account for, do that one first. An unattributed credential already inside the building beats any number of failed logins at the door.