As part of my ongoing focus on MySQL 8 user and password management, I’ve covered how the new dual passwords feature can reduce the overall DBA workload and streamline the management process (see MySQL 8: Dual Passwords). This wasn’t the only change to user/password management in MySQL 8; one of the more security-focused changes was the implementation of temporary account locking, first introduced in MySQL 8.0.19. With this feature, database administrators can now configure user accounts so that too many consecutive login failures can temporarily lock the account.
The account locking feature only applies to the failure of a client to provide a correct password during the connection attempt. It does not apply to failure to connect for other reasons (network issues, unknown user account, etc.). In the case of dual passwords, either of the account passwords that have been set would count as correct during successful authentication.
Configurable options are FAILED_LOGIN_ATTEMPTS and PASSWORD_LOCK_TIME, both used with the CREATE USER and ALTER USER statements. A couple of usage examples are:
|
1 |
CREATE USER 'percona'@'localhost' IDENTIFIED BY 'password' FAILED_LOGIN_ATTEMPTS 4 PASSWORD_LOCK_TIME 3;<br>ALTER USER 'percona'@'localhost' FAILED_LOGIN_ATTEMPTS 3 PASSWORD_LOCK_TIME UNBOUNDED;<br> |
Once a user has been set up with these options, too many consecutive login failures will result in an error:
|
1 |
ERROR 3957 (HY000) : Access denied for user percona.<br>Account is blocked for D day(s) (R day(s) remaining) due to N consecutive failed logins. <br> |
FAILED_LOGIN_ATTEMPTS N
This option determines whether or not to track account login attempts with an incorrect password. The number N specifies how many consecutive wrong password attempts will lock the account.
PASSWORD_LOCK_TIME (N | UNBOUNDED)
This option indicates how long an account will remain locked after too many consecutive incorrect password attempts. The number N specifies the number of days the account will remain locked. For a more permanent account lockout, setting this to UNBOUNDED stipulates that the duration of the locked state is now unbounded and does not end until the account is manually unlocked.
State information for each account regarding failed login tracking, and account lock status, happens every time the server reads the grant tables. An account’s state information can be reset, resetting the failed-login count and unlocking the account if it is already locked. Account resets can be global for all accounts or limited to a single account.
Global Reset
Single Account Reset
The account locking state is recorded in the ‘account_locked’ column of the mysql.user system table. The output from SHOW CREATE USER indicates whether an account is locked or unlocked.
If a client attempts to connect to an account that is locked, the attempt will fail. In this case, the server also increments the ‘Locked_connects’ status variable that indicates the number of attempts to connect to a locked account, an error message is displayed, and the attempt is logged to the MySQL error log:
|
1 |
Access denied for user 'percona'@'localhost'.<br>Account is locked.<br> |
Locking an account does not affect connecting using a proxy user that assumes the identity of the locked account. It also does not affect the ability to execute stored procedures or views with the DEFINER attribute set to the locked account.
While this is another relatively simple feature, it can significantly impact how your company manages the security aspects of failed login attempts. This leads to a more secure database environment and better client management overall. Having this ability has also proven helpful during maintenance operations to disable access from specific accounts or as a security measure to lock privileged accounts and unlock them only during application maintenance.
Not running MySQL 8 yet? A colleague pointed out that a similar functionality was available in earlier versions of MySQL by utilizing the Connection-Control Plugin. With this plugin, too many consecutive failed attempts would increase the delay in the server response to help avoid or minimize brute force attacks. If there is interest, I may cover this plugin in more detail in a future blog post. Let me know!
Complete the 2021 Percona Open Source Data Management Software Survey