blueprints: add default Password policy (#11793) * add password policy to default password change flow This change complies with the minimal compositional requirements by NIST SP 800-63 Digital Identity Guidelines. See https://pages.nist.gov/800-63-4/sp800-63b.html#password More work is needed to comply with other parts of the Guidelines, specifically > If the chosen password is found on the blocklist, the CSP or verifier > [...] SHALL provide the reason for rejection. and > Verifiers SHALL offer guidance to the subscriber to assist the user in > choosing a strong password. This is particularly important following > the rejection of a password on the blocklist as it discourages trivial > modification of listed weak passwords. * add docs for default Password policy * remove HIBP from default Password policy * add zxcvbn to default Password policy * add fallback password error message to password policy, fix validation policy * reword docs * add HIBP caveat * separate policy into separate blueprint * use password policy for oobe flow * kiss --------- Signed-off-by: Jens Langhammer <jens@goauthentik.io> Signed-off-by: Simonyi Gergő <28359278+gergosimonyi@users.noreply.github.com> Co-authored-by: Simonyi Gergő <28359278+gergosimonyi@users.noreply.github.com> Co-authored-by: Jens Langhammer <jens@goauthentik.io> Co-authored-by: Tana M Berry <tanamarieberry@yahoo.com>
This commit is contained in:
committed by
GitHub
parent
7ed268fef4
commit
64676819ec
@ -27,7 +27,8 @@ def blueprint_tester(file_name: Path) -> Callable:
|
|||||||
base = Path("blueprints/")
|
base = Path("blueprints/")
|
||||||
rel_path = Path(file_name).relative_to(base)
|
rel_path = Path(file_name).relative_to(base)
|
||||||
importer = Importer.from_string(BlueprintInstance(path=str(rel_path)).retrieve())
|
importer = Importer.from_string(BlueprintInstance(path=str(rel_path)).retrieve())
|
||||||
self.assertTrue(importer.validate()[0])
|
validation, logs = importer.validate()
|
||||||
|
self.assertTrue(validation, logs)
|
||||||
self.assertTrue(importer.apply())
|
self.assertTrue(importer.apply())
|
||||||
|
|
||||||
return tester
|
return tester
|
||||||
|
|||||||
@ -89,6 +89,10 @@ class PasswordPolicy(Policy):
|
|||||||
|
|
||||||
def passes_static(self, password: str, request: PolicyRequest) -> PolicyResult:
|
def passes_static(self, password: str, request: PolicyRequest) -> PolicyResult:
|
||||||
"""Check static rules"""
|
"""Check static rules"""
|
||||||
|
error_message = self.error_message
|
||||||
|
if error_message == "":
|
||||||
|
error_message = _("Invalid password.")
|
||||||
|
|
||||||
if len(password) < self.length_min:
|
if len(password) < self.length_min:
|
||||||
LOGGER.debug("password failed", check="static", reason="length")
|
LOGGER.debug("password failed", check="static", reason="length")
|
||||||
return PolicyResult(False, self.error_message)
|
return PolicyResult(False, self.error_message)
|
||||||
|
|||||||
@ -101,7 +101,6 @@ entries:
|
|||||||
- !KeyOf prompt-field-email
|
- !KeyOf prompt-field-email
|
||||||
- !KeyOf prompt-field-password
|
- !KeyOf prompt-field-password
|
||||||
- !KeyOf prompt-field-password-repeat
|
- !KeyOf prompt-field-password-repeat
|
||||||
validation_policies: []
|
|
||||||
id: stage-default-oobe-password
|
id: stage-default-oobe-password
|
||||||
identifiers:
|
identifiers:
|
||||||
name: stage-default-oobe-password
|
name: stage-default-oobe-password
|
||||||
|
|||||||
@ -2,6 +2,17 @@ version: 1
|
|||||||
metadata:
|
metadata:
|
||||||
name: Default - Password change flow
|
name: Default - Password change flow
|
||||||
entries:
|
entries:
|
||||||
|
- attrs:
|
||||||
|
check_static_rules: true
|
||||||
|
check_zxcvbn: true
|
||||||
|
length_min: 8
|
||||||
|
password_field: password
|
||||||
|
zxcvbn_score_threshold: 2
|
||||||
|
error_message: Password needs to be 8 characters or longer.
|
||||||
|
identifiers:
|
||||||
|
name: default-password-change-password-policy
|
||||||
|
model: authentik_policies_password.passwordpolicy
|
||||||
|
id: default-password-change-password-policy
|
||||||
- attrs:
|
- attrs:
|
||||||
designation: stage_configuration
|
designation: stage_configuration
|
||||||
name: Change Password
|
name: Change Password
|
||||||
@ -39,6 +50,8 @@ entries:
|
|||||||
fields:
|
fields:
|
||||||
- !KeyOf prompt-field-password
|
- !KeyOf prompt-field-password
|
||||||
- !KeyOf prompt-field-password-repeat
|
- !KeyOf prompt-field-password-repeat
|
||||||
|
validation_policies:
|
||||||
|
- !KeyOf default-password-change-password-policy
|
||||||
identifiers:
|
identifiers:
|
||||||
name: default-password-change-prompt
|
name: default-password-change-prompt
|
||||||
id: default-password-change-prompt
|
id: default-password-change-prompt
|
||||||
|
|||||||
@ -32,6 +32,10 @@ This policy can enforce regular password rotation by expiring set passwords afte
|
|||||||
|
|
||||||
### Password Policy
|
### Password Policy
|
||||||
|
|
||||||
|
:::warning
|
||||||
|
By default, authentik's Password policy is compliant with [NIST's recommendations](https://pages.nist.gov/800-63-4/sp800-63b.html#password) for passwords. To remain compliant with NIST, be cautious when editing the default values. For additional hardening configuration settings, refer to [Hardening authentik](../../security/security-hardening.md#password-policy).
|
||||||
|
:::
|
||||||
|
|
||||||
This policy allows you to specify password rules, such as length and required characters.
|
This policy allows you to specify password rules, such as length and required characters.
|
||||||
The following rules can be set:
|
The following rules can be set:
|
||||||
|
|
||||||
|
|||||||
@ -4,6 +4,17 @@ title: Hardening authentik
|
|||||||
|
|
||||||
While authentik is secure out of the box, you can take steps to further increase the security of an authentik instance. As everyone knows, there is a consequential tradeoff between security and convenience. All of these hardening practices have an impact on the user experience and should only be applied knowing this tradeoff.
|
While authentik is secure out of the box, you can take steps to further increase the security of an authentik instance. As everyone knows, there is a consequential tradeoff between security and convenience. All of these hardening practices have an impact on the user experience and should only be applied knowing this tradeoff.
|
||||||
|
|
||||||
|
### Password policy
|
||||||
|
|
||||||
|
authentik's default Password policy complies with the [NIST SP 800-63 Digital Identity Guidelines](https://pages.nist.gov/800-63-4/sp800-63b.html#password).
|
||||||
|
|
||||||
|
However, for further hardening compliant to the NIST Guidelines, consider
|
||||||
|
|
||||||
|
- setting the length of the password to a minimum of 15 characters, and
|
||||||
|
- enabling the "Check haveibeenpwned.com" blocklist comparison (note that this cannot be used on Air-gapped instances)
|
||||||
|
|
||||||
|
For further options, see [Password policy](../customize/policies/index.md#password-policy).
|
||||||
|
|
||||||
### Expressions
|
### Expressions
|
||||||
|
|
||||||
[Expressions](../customize/policies/expression.mdx) allow super-users and other highly privileged users to create custom logic within authentik to modify its behaviour. Editing/creating these expressions is, by default, limited to super-users and any related events are fully logged.
|
[Expressions](../customize/policies/expression.mdx) allow super-users and other highly privileged users to create custom logic within authentik to modify its behaviour. Editing/creating these expressions is, by default, limited to super-users and any related events are fully logged.
|
||||||
|
|||||||
Reference in New Issue
Block a user