├── CODE_OF_CONDUCT.md ├── UPGRADE.md ├── LICENSE ├── src ├── Validator │ └── Constraints │ │ ├── PasswordStrength.php │ │ ├── PasswordRequirements.php │ │ ├── PasswordRequirementsValidator.php │ │ └── PasswordStrengthValidator.php └── Resources │ └── translations │ ├── validators.ja.xlf │ ├── validators.cs.xlf │ ├── validators.sk.xlf │ ├── validators.th.xlf │ ├── validators.pl.xlf │ ├── validators.bg.xlf │ ├── validators.en.xlf │ ├── validators.es.xlf │ ├── validators.pt_BR.xlf │ ├── validators.it.xlf │ ├── validators.fr.xlf │ ├── validators.nl.xlf │ ├── validators.de.xlf │ └── validators.ru.xlf ├── composer.json └── README.md /CODE_OF_CONDUCT.md: -------------------------------------------------------------------------------- 1 | This project's code-of-conduct can be found at https://github.com/rollerworks/contributing/blob/master/CODE_OF_CONDUCT.md 2 | -------------------------------------------------------------------------------- /UPGRADE.md: -------------------------------------------------------------------------------- 1 | UPGRADE 2 | ======= 3 | 4 | ## Upgrade from 2.x to 3.0 5 | 6 | * Support for Symfony 6 was removed, PHP 8.4 and Symfony 7.4 is now the minimum required version. 7 | 8 | * The constraints constructor was changed to better support the new Symfony validator. 9 | 10 | * The required options are now the first arguments, and must have a value. 11 | * Passing options as an array is no longer supported, use named arguments instead. 12 | 13 | ```diff 14 | - new PasswordRequirements(['minLength' => 8]); 15 | + new PasswordRequirements(minLength: 8); 16 | ``` 17 | 18 | ```diff 19 | - new PasswordStrength([minStrength' => 4]); 20 | + new PasswordStrength(minStrength: 4); 21 | ``` 22 | 23 | * Support for annotation mapping was removed. 24 | 25 | ```diff 26 | -/** 27 | - * @RollerworksPassword\PasswordStrength(minLength=7) 28 | - */ 29 | +#[PasswordStrength(minLength: 7)] 30 | ``` 31 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | Copyright (c) 2012-present Sebastiaan Stok 2 | 3 | Permission is hereby granted, free of charge, to any person obtaining a copy 4 | of this software and associated documentation files (the "Software"), to deal 5 | in the Software without restriction, including without limitation the rights 6 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 7 | copies of the Software, and to permit persons to whom the Software is furnished 8 | to do so, subject to the following conditions: 9 | 10 | The above copyright notice and this permission notice shall be included in all 11 | copies or substantial portions of the Software. 12 | 13 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 14 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 15 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 16 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 17 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 18 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 19 | THE SOFTWARE. 20 | -------------------------------------------------------------------------------- /src/Validator/Constraints/PasswordStrength.php: -------------------------------------------------------------------------------- 1 | 9 | * 10 | * This source file is subject to the MIT license that is bundled 11 | * with this source code in the file LICENSE. 12 | */ 13 | 14 | namespace Rollerworks\Component\PasswordStrength\Validator\Constraints; 15 | 16 | use Symfony\Component\Validator\Constraint; 17 | 18 | #[\Attribute(\Attribute::TARGET_PROPERTY | \Attribute::TARGET_METHOD | \Attribute::IS_REPEATABLE)] 19 | class PasswordStrength extends Constraint 20 | { 21 | public function __construct( 22 | public int $minStrength = 6, 23 | public ?int $minLength = null, 24 | public bool $unicodeEquality = false, 25 | public string $message = 'password_too_weak', 26 | public string $tooShortMessage = 'Your password must be at least {{length}} characters long.', 27 | ?array $groups = null, 28 | mixed $payload = null, 29 | ) { 30 | parent::__construct(null, $groups, $payload); 31 | } 32 | } 33 | -------------------------------------------------------------------------------- /src/Validator/Constraints/PasswordRequirements.php: -------------------------------------------------------------------------------- 1 | 9 | * 10 | * This source file is subject to the MIT license that is bundled 11 | * with this source code in the file LICENSE. 12 | */ 13 | 14 | namespace Rollerworks\Component\PasswordStrength\Validator\Constraints; 15 | 16 | use Symfony\Component\Validator\Constraint; 17 | 18 | #[\Attribute(\Attribute::TARGET_PROPERTY | \Attribute::TARGET_METHOD | \Attribute::IS_REPEATABLE)] 19 | class PasswordRequirements extends Constraint 20 | { 21 | public function __construct( 22 | public int $minLength = 6, 23 | public bool $requireLetters = true, 24 | public bool $requireCaseDiff = false, 25 | public bool $requireNumbers = false, 26 | public bool $requireSpecialCharacter = false, 27 | public string $tooShortMessage = 'Your password must be at least {{length}} characters long.', 28 | public string $missingLettersMessage = 'Your password must include at least one letter.', 29 | public string $requireCaseDiffMessage = 'Your password must include both upper and lower case letters.', 30 | public string $missingNumbersMessage = 'Your password must include at least one number.', 31 | public string $missingSpecialCharacterMessage = 'Your password must contain at least one special character.', 32 | ?array $groups = null, 33 | mixed $payload = null, 34 | ) { 35 | parent::__construct(null, $groups, $payload); 36 | } 37 | } 38 | -------------------------------------------------------------------------------- /composer.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "rollerworks/password-strength-validator", 3 | "description": "Password-strength validator for Symfony", 4 | "license": "MIT", 5 | "type": "library", 6 | "keywords": [ 7 | "password", 8 | "validator", 9 | "symfony" 10 | ], 11 | "authors": [ 12 | { 13 | "name": "Sebastiaan Stok", 14 | "email": "s.stok@rollercapes.net" 15 | }, 16 | { 17 | "name": "Community contributions", 18 | "homepage": "https://github.com/rollerworks/PasswordStrengthValidator/contributors" 19 | } 20 | ], 21 | "require": { 22 | "php": ">=8.4", 23 | "symfony/config": "^7.4 || ^8.0", 24 | "symfony/polyfill-mbstring": "^1.5.0", 25 | "symfony/translation": "^7.4 || ^8.0", 26 | "symfony/validator": "^7.4 || ^8.0" 27 | }, 28 | "require-dev": { 29 | "phpunit/phpunit": "^12.4", 30 | "symfony/phpunit-bridge": "^7.4 || ^8.0", 31 | "rollerscapes/standards": "^1.0" 32 | }, 33 | "minimum-stability": "dev", 34 | "prefer-stable": true, 35 | "autoload": { 36 | "psr-4": { 37 | "Rollerworks\\Component\\PasswordStrength\\": "src/" 38 | }, 39 | "exclude-from-classmap": [ 40 | "test/" 41 | ] 42 | }, 43 | "autoload-dev": { 44 | "psr-4": { 45 | "Rollerworks\\Component\\PasswordStrength\\Tests\\": "tests/" 46 | } 47 | }, 48 | "config": { 49 | "sort-packages": true 50 | }, 51 | "extra": { 52 | "branch-alias": { 53 | "dev-main": "3.0-dev" 54 | } 55 | } 56 | } 57 | -------------------------------------------------------------------------------- /src/Validator/Constraints/PasswordRequirementsValidator.php: -------------------------------------------------------------------------------- 1 | 9 | * 10 | * This source file is subject to the MIT license that is bundled 11 | * with this source code in the file LICENSE. 12 | */ 13 | 14 | namespace Rollerworks\Component\PasswordStrength\Validator\Constraints; 15 | 16 | use Symfony\Component\Validator\Constraint; 17 | use Symfony\Component\Validator\ConstraintValidator; 18 | use Symfony\Component\Validator\Exception\UnexpectedTypeException; 19 | 20 | class PasswordRequirementsValidator extends ConstraintValidator 21 | { 22 | public function validate(mixed $value, Constraint $constraint): void 23 | { 24 | if ($value === null || $value === '') { 25 | return; 26 | } 27 | 28 | if (! $constraint instanceof PasswordRequirements) { 29 | throw new UnexpectedTypeException($constraint, PasswordRequirements::class); 30 | } 31 | 32 | if (! \is_scalar($value) && ! (\is_object($value) && method_exists($value, '__toString'))) { 33 | throw new UnexpectedTypeException($value, 'string'); 34 | } 35 | 36 | $value = (string) $value; 37 | 38 | if ($constraint->minLength > 0 && (mb_strlen($value) < $constraint->minLength)) { 39 | $this->context->buildViolation($constraint->tooShortMessage) 40 | ->setParameters(['{{length}}' => $constraint->minLength]) 41 | ->setInvalidValue($value) 42 | ->addViolation() 43 | ; 44 | } 45 | 46 | if ($constraint->requireLetters && ! preg_match('/\pL/u', $value)) { 47 | $this->context->buildViolation($constraint->missingLettersMessage) 48 | ->setInvalidValue($value) 49 | ->addViolation() 50 | ; 51 | } 52 | 53 | if ($constraint->requireCaseDiff && ! preg_match('/(\p{Ll}+.*\p{Lu})|(\p{Lu}+.*\p{Ll})/u', $value)) { 54 | $this->context->buildViolation($constraint->requireCaseDiffMessage) 55 | ->setInvalidValue($value) 56 | ->addViolation() 57 | ; 58 | } 59 | 60 | if ($constraint->requireNumbers && ! preg_match('/\pN/u', $value)) { 61 | $this->context->buildViolation($constraint->missingNumbersMessage) 62 | ->setInvalidValue($value) 63 | ->addViolation() 64 | ; 65 | } 66 | 67 | if ($constraint->requireSpecialCharacter && ! preg_match('/[^\p{Ll}\p{Lu}\pL\pN]/u', $value)) { 68 | $this->context->buildViolation($constraint->missingSpecialCharacterMessage) 69 | ->setInvalidValue($value) 70 | ->addViolation() 71 | ; 72 | } 73 | } 74 | } 75 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | Rollerworks PasswordStrengthValidator 2 | ===================================== 3 | 4 | This package provides various password strength validators for the [Symfony Validator 5 | component](http://symfony.com/doc/current/components/validator.html). 6 | 7 | _To use this bundle with a Symfony application use the [RollerworksPasswordStrengthBundle][1]._ 8 | 9 | Passwords can be validated using either strength-levels (weak, medium, strong etc) 10 | or by configuring explicit requirements (needs letters, numbers etc). 11 | 12 | > This library provides the same level of functionality as the 13 | > [PasswordStrengthBundle](https://github.com/jbafford/PasswordStrengthBundle) created by John Bafford. 14 | 15 | ## Installation 16 | 17 | To install this package, add `rollerworks/password-strength-validator` to your composer.json: 18 | 19 | ```bash 20 | $ php composer.phar require rollerworks/password-strength-validator 21 | ``` 22 | 23 | Now, [Composer][2] will automatically download all required files, and install them 24 | for you. 25 | 26 | ## Requirements 27 | 28 | You need at least PHP 8.4 and Symfony 7.4, mbstring is recommended but not required. 29 | 30 | ## Basic Usage 31 | 32 | **Caution:** 33 | 34 | > The password validators do not enforce that the field must have a value! 35 | > To make a field "required" use the [NotBlank constraint](http://symfony.com/doc/current/reference/constraints/NotBlank.html) 36 | > in combination with the password validator(s). 37 | 38 | All examples assume you have the Composer autoloader already in your code, 39 | see also [How to Install and Use the Symfony Components](http://symfony.com/doc/current/components/using_components.html) 40 | for more information. 41 | 42 | ### [Strength validation](docs/strength-validation.md) 43 | 44 | Validates the passwords strength-level (weak, medium, strong etc). 45 | 46 | ### [Requirements validation](docs/requirements-validation.md) 47 | 48 | Validates the passwords using explicitly configured requirements (letters, caseDiff, numbers, requireSpecialCharacter). 49 | 50 | ## Versioning 51 | 52 | For transparency and insight into the release cycle, and for striving 53 | to maintain backward compatibility, this package is maintained under 54 | the Semantic Versioning guidelines as much as possible. 55 | 56 | Releases will be numbered with the following format: 57 | 58 | `..` 59 | 60 | And constructed with the following guidelines: 61 | 62 | * Breaking backward compatibility bumps the major (and resets the minor and patch) 63 | * New additions without breaking backward compatibility bumps the minor (and resets the patch) 64 | * Bug fixes and misc changes bumps the patch 65 | 66 | For more information on SemVer, please visit . 67 | 68 | ## License 69 | 70 | This library is released under the [MIT license](LICENSE). 71 | 72 | ## Contributing 73 | 74 | This is an open source project. If you'd like to contribute, 75 | please read the [Contributing Guidelines][3]. If you're submitting 76 | a pull request, please follow the guidelines in the [Submitting a Patch][4] section. 77 | 78 | [1]: https://github.com/rollerworks/PasswordStrengthBundle 79 | [2]: https://getcomposer.org/doc/00-intro.md 80 | [3]: https://github.com/rollerworks/contributing 81 | [4]: https://contributing.readthedocs.org/en/latest/code/patches.html 82 | -------------------------------------------------------------------------------- /src/Resources/translations/validators.ja.xlf: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | Your password must be at least {{length}} characters long. 7 | パスワードは最低でも {{length}} 文字必要です。 8 | 9 | 10 | Your password must include at least one letter. 11 | パスワードは最低でも1文字必要です。 12 | 13 | 14 | Your password must include both upper and lower case letters. 15 | パスワードには大文字と小文字を含む必要があります。 16 | 17 | 18 | Your password must include at least one number. 19 | パスワードには最低でも数字がひとつ必要です。 20 | 21 | 22 | Your password must contain at least one special character. 23 | パスワードは最低でも一つの特殊記号が必要です。 24 | 25 | 26 | password_too_weak 27 | パスワードは最低でも強度"{{ min_strength }}"レベル以上が必要です。現在のレベルは"{{ current_strength }}"なので、こちらをお試しください。 {{ strength_tips }} 28 | 29 | 30 | 31 | 32 | rollerworks_password.strength_level.very_weak 33 | とても弱い 34 | 35 | 36 | rollerworks_password.strength_level.weak 37 | 38 | 39 | 40 | rollerworks_password.strength_level.medium 41 | 42 | 43 | 44 | rollerworks_password.strength_level.strong 45 | 46 | 47 | 48 | rollerworks_password.strength_level.very_strong 49 | とても強い 50 | 51 | 52 | 53 | 54 | rollerworks_password.tip.letters 55 | (大文字/小文字)を追加してください 56 | 57 | 58 | rollerworks_password.tip.numbers 59 | 数字を追加してください。 60 | 61 | 62 | rollerworks_password.tip.lowercase_letters 63 | 小文字を追加してください 64 | 65 | 66 | rollerworks_password.tip.uppercase_letters 67 | 大文字を追加してください 68 | 69 | 70 | rollerworks_password.tip.special_chars 71 | 特殊記号を追加してください 72 | 73 | 74 | rollerworks_password.tip.length 75 | 文字数が足りてません。追加してください 76 | 77 | 78 | 79 | 80 | -------------------------------------------------------------------------------- /src/Resources/translations/validators.cs.xlf: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | Your password must be at least {{length}} characters long. 7 | Heslo musí mít alespoň {{length}} znaků. 8 | 9 | 10 | Your password must include at least one letter. 11 | Heslo musí obsahovat písmeno. 12 | 13 | 14 | Your password must include both upper and lower case letters. 15 | Heslo musí obsahovat velká i malá písmena. 16 | 17 | 18 | Your password must include at least one number. 19 | Heslo musí obsahovat číslici. 20 | 21 | 22 | Your password must contain at least one special character. 23 | Heslo musí obsahovat speciální znak. 24 | 25 | 26 | password_too_weak 27 | Úroveň hesla musí být alespoň "{{ min_strength }}", současná úroveň je "{{ current_strength }}", zkuste {{ strength_tips }}. 28 | 29 | 30 | 31 | 32 | rollerworks_password.strength_level.very_weak 33 | velmi slabé 34 | 35 | 36 | rollerworks_password.strength_level.weak 37 | slabé 38 | 39 | 40 | rollerworks_password.strength_level.medium 41 | střední 42 | 43 | 44 | rollerworks_password.strength_level.strong 45 | silné 46 | 47 | 48 | rollerworks_password.strength_level.very_strong 49 | velmi silné 50 | 51 | 52 | 53 | 54 | rollerworks_password.tip.letters 55 | přidat malá/velká písmena 56 | 57 | 58 | rollerworks_password.tip.numbers 59 | přidat číslici 60 | 61 | 62 | rollerworks_password.tip.lowercase_letters 63 | přidat malé písmeno 64 | 65 | 66 | rollerworks_password.tip.uppercase_letters 67 | přidat velké písmeno 68 | 69 | 70 | rollerworks_password.tip.special_chars 71 | přidat speciální znak 72 | 73 | 74 | rollerworks_password.tip.length 75 | delší heslo 76 | 77 | 78 | 79 | 80 | -------------------------------------------------------------------------------- /src/Resources/translations/validators.sk.xlf: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | Your password must be at least {{length}} characters long. 7 | Heslo musí obsahovať aspoň {{length}} znakov. 8 | 9 | 10 | Your password must include at least one letter. 11 | Heslo musí obsahovať písmeno. 12 | 13 | 14 | Your password must include both upper and lower case letters. 15 | Heslo musí obsahovať veľké aj malé písmená. 16 | 17 | 18 | Your password must include at least one number. 19 | Heslo musí obsahovať číslicu. 20 | 21 | 22 | Your password must contain at least one special character. 23 | Heslo musí obsahovať špeciálny znak. 24 | 25 | 26 | password_too_weak 27 | Úroveň hesla musí být aspoň "{{ min_strength }}", súčasná úroveň je "{{ current_strength }}", skúste {{ strength_tips }}. 28 | 29 | 30 | 31 | 32 | rollerworks_password.strength_level.very_weak 33 | veľmi slabé 34 | 35 | 36 | rollerworks_password.strength_level.weak 37 | slabé 38 | 39 | 40 | rollerworks_password.strength_level.medium 41 | priemerné 42 | 43 | 44 | rollerworks_password.strength_level.strong 45 | silné 46 | 47 | 48 | rollerworks_password.strength_level.very_strong 49 | veľmi silné 50 | 51 | 52 | 53 | 54 | rollerworks_password.tip.letters 55 | pridať malé/veľké písmená 56 | 57 | 58 | rollerworks_password.tip.numbers 59 | pridať číslicu 60 | 61 | 62 | rollerworks_password.tip.lowercase_letters 63 | pridať malé písmeno 64 | 65 | 66 | rollerworks_password.tip.uppercase_letters 67 | pridať veľké písmeno 68 | 69 | 70 | rollerworks_password.tip.special_chars 71 | pridať špeciálny znak 72 | 73 | 74 | rollerworks_password.tip.length 75 | dlhšie heslo 76 | 77 | 78 | 79 | 80 | -------------------------------------------------------------------------------- /src/Resources/translations/validators.th.xlf: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | Your password must be at least {{length}} characters long. 7 | รหัสผ่านต้องมีความยาวอย่างน้อย {{length}} ตัวอักษร 8 | 9 | 10 | Your password must include at least one letter. 11 | รหัสผ่านต้องมีตัวอักษรอย่างน้อยหนึ่งตัว 12 | 13 | 14 | Your password must include both upper and lower case letters. 15 | รหัสผ่านต้องประกอบด้วยอักษรตัวเล็กและตัวใหญ่ 16 | 17 | 18 | Your password must include at least one number. 19 | รหัสผ่านต้องประกอบด้วยตัวเลขอย่างน้อยหนึ่งตัว 20 | 21 | 22 | Your password must contain at least one special character. 23 | รหัสผ่านต้องประกอบด้วยอักขระพิเศษอย่างน้อยหนึ่งตัว 24 | 25 | 26 | password_too_weak 27 | ความปลอดภัยของรหัสผ่านต้องอยู่ในระดับ "{{ min_strength }}" เป็นอย่างน้อย, ระดับปัจจุบันคือ "{{ current_strength }}", คำแนะนำ {{ strength_tips }}. 28 | 29 | 30 | 31 | 32 | rollerworks_password.strength_level.very_weak 33 | คาดเดาง่ายมาก 34 | 35 | 36 | rollerworks_password.strength_level.weak 37 | คาดเดาง่าย 38 | 39 | 40 | rollerworks_password.strength_level.medium 41 | พอใช้ 42 | 43 | 44 | rollerworks_password.strength_level.strong 45 | เดายาก 46 | 47 | 48 | rollerworks_password.strength_level.very_strong 49 | ดีมาก 50 | 51 | 52 | 53 | 54 | rollerworks_password.tip.letters 55 | เพิ่ม (อักษรตัวใหญ่/ตัวเล็ก) 56 | 57 | 58 | rollerworks_password.tip.numbers 59 | เพิ่ม ตัวเลข 60 | 61 | 62 | rollerworks_password.tip.lowercase_letters 63 | เพิ่ม อักษรตัวเล็ก 64 | 65 | 66 | rollerworks_password.tip.uppercase_letters 67 | เพิ่ม อักษรตัวใหญ่ 68 | 69 | 70 | rollerworks_password.tip.special_chars 71 | เพิ่ม อักขระพิเศษ 72 | 73 | 74 | rollerworks_password.tip.length 75 | เพิ่มความยาวอีก 76 | 77 | 78 | 79 | 80 | -------------------------------------------------------------------------------- /src/Resources/translations/validators.pl.xlf: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | Your password must be at least {{length}} characters long. 7 | Hasło musi składać się z przynajmniej {{length}} znaków. 8 | 9 | 10 | Your password must include at least one letter. 11 | Hasło musi zawierać przynajmniej jedną literę. 12 | 13 | 14 | Your password must include both upper and lower case letters. 15 | Hasło musi zawierać duże i małe litery. 16 | 17 | 18 | Your password must include at least one number. 19 | Hasło musi zawierać przynajmniej jedną cyfrę. 20 | 21 | 22 | Your password must contain at least one special character. 23 | Hasło musi zawierać przynajmniej jeden znak specjalny. 24 | 25 | 26 | password_too_weak 27 | Hasło musi być przynajmniej "{{ min_strength }}". Obecny poziom siły hasła to "{{ current_strength }}", spróbuj: {{ strength_tips }}. 28 | 29 | 30 | 31 | 32 | rollerworks_password.strength_level.very_weak 33 | Bardzo słabe 34 | 35 | 36 | rollerworks_password.strength_level.weak 37 | Słabe 38 | 39 | 40 | rollerworks_password.strength_level.medium 41 | Średnie 42 | 43 | 44 | rollerworks_password.strength_level.strong 45 | Silne 46 | 47 | 48 | rollerworks_password.strength_level.very_strong 49 | Bardzo silne 50 | 51 | 52 | 53 | 54 | rollerworks_password.tip.letters 55 | dodać (małe/duże) litery 56 | 57 | 58 | rollerworks_password.tip.numbers 59 | dodać cyfry 60 | 61 | 62 | rollerworks_password.tip.lowercase_letters 63 | dodać małe litery 64 | 65 | 66 | rollerworks_password.tip.uppercase_letters 67 | dodać duże litery 68 | 69 | 70 | rollerworks_password.tip.special_chars 71 | dodać znaki specjalne 72 | 73 | 74 | rollerworks_password.tip.length 75 | dodać więcej znaków 76 | 77 | 78 | 79 | 80 | -------------------------------------------------------------------------------- /src/Resources/translations/validators.bg.xlf: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | Your password must be at least {{length}} characters long. 7 | Паролата трябва да е с дължина най-малко {{length}} знака. 8 | 9 | 10 | Your password must include at least one letter. 11 | Паролата трябва да съдържа поне една буква. 12 | 13 | 14 | Your password must include both upper and lower case letters. 15 | Паролата трябва да съдържа главни и малки букви. 16 | 17 | 18 | Your password must include at least one number. 19 | Паролата трябва да съдържа поне едно число. 20 | 21 | 22 | Your password must contain at least one special character. 23 | Паролата трябва да съдържа поне един специален знак. 24 | 25 | 26 | password_too_weak 27 | Паролата трябва да е поне на ниво "{{ min_strength }}", текущото ниво е "{{ current_strength }}", опитайте това: {{ strength_tips }}. 28 | 29 | 30 | 31 | 32 | rollerworks_password.strength_level.very_weak 33 | Много слабо 34 | 35 | 36 | rollerworks_password.strength_level.weak 37 | Слабо 38 | 39 | 40 | rollerworks_password.strength_level.medium 41 | Средно 42 | 43 | 44 | rollerworks_password.strength_level.strong 45 | Силно 46 | 47 | 48 | rollerworks_password.strength_level.very_strong 49 | Много силно 50 | 51 | 52 | 53 | 54 | rollerworks_password.tip.letters 55 | добавете букви (главни/малки) 56 | 57 | 58 | rollerworks_password.tip.numbers 59 | добавете цифри 60 | 61 | 62 | rollerworks_password.tip.lowercase_letters 63 | добавете малки букви 64 | 65 | 66 | rollerworks_password.tip.uppercase_letters 67 | добавете главни букви 68 | 69 | 70 | rollerworks_password.tip.special_chars 71 | добавете специални знаци 72 | 73 | 74 | rollerworks_password.tip.length 75 | добавете още знаци 76 | 77 | 78 | 79 | 80 | -------------------------------------------------------------------------------- /src/Resources/translations/validators.en.xlf: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | Your password must be at least {{length}} characters long. 7 | Password must be at least {{length}} characters long. 8 | 9 | 10 | Your password must include at least one letter. 11 | Password must include at least one letter. 12 | 13 | 14 | Your password must include both upper and lower case letters. 15 | Password must include both upper and lower case letters. 16 | 17 | 18 | Your password must include at least one number. 19 | Password must include at least one number. 20 | 21 | 22 | Your password must contain at least one special character. 23 | Password must contain at least one special character. 24 | 25 | 26 | password_too_weak 27 | Password needs to be at least at strength level "{{ min_strength }}", current level is "{{ current_strength }}", try the following: {{ strength_tips }}. 28 | 29 | 30 | 31 | 32 | rollerworks_password.strength_level.very_weak 33 | Very Weak 34 | 35 | 36 | rollerworks_password.strength_level.weak 37 | Weak 38 | 39 | 40 | rollerworks_password.strength_level.medium 41 | Medium 42 | 43 | 44 | rollerworks_password.strength_level.strong 45 | Strong 46 | 47 | 48 | rollerworks_password.strength_level.very_strong 49 | Very strong 50 | 51 | 52 | 53 | 54 | rollerworks_password.tip.letters 55 | add (upper/lowercase) letters 56 | 57 | 58 | rollerworks_password.tip.numbers 59 | add numbers 60 | 61 | 62 | rollerworks_password.tip.lowercase_letters 63 | add lowercase letters 64 | 65 | 66 | rollerworks_password.tip.uppercase_letters 67 | add uppercase letters 68 | 69 | 70 | rollerworks_password.tip.special_chars 71 | add special characters 72 | 73 | 74 | rollerworks_password.tip.length 75 | add more characters 76 | 77 | 78 | 79 | 80 | -------------------------------------------------------------------------------- /src/Resources/translations/validators.es.xlf: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | Your password must be at least {{length}} characters long. 7 | La contraseña debe tener por lo menos {{length}} caracteres. 8 | 9 | 10 | Your password must include at least one letter. 11 | La contraseña debe tener por lo menos una letra. 12 | 13 | 14 | Your password must include both upper and lower case letters. 15 | La contraseña debe tener mayúsculas y minúsculas. 16 | 17 | 18 | Your password must include at least one number. 19 | La contraseña debe tener por lo menos una cifra. 20 | 21 | 22 | Your password must contain at least one special character. 23 | La contraseña debe tener por lo menos un carácter especial. 24 | 25 | 26 | password_too_weak 27 | La contraseña debe tener una potencia de "{{ min_strength }}" por lo menos. La potencia actual es "{{ current_strength }}". Inténtelo aquí. {{ strength_tips }}. 28 | 29 | 30 | 31 | 32 | rollerworks_password.strength_level.very_weak 33 | Muy baja 34 | 35 | 36 | rollerworks_password.strength_level.weak 37 | Baja 38 | 39 | 40 | rollerworks_password.strength_level.medium 41 | Mediana 42 | 43 | 44 | rollerworks_password.strength_level.strong 45 | Potente 46 | 47 | 48 | rollerworks_password.strength_level.very_strong 49 | Muy potente 50 | 51 | 52 | 53 | 54 | rollerworks_password.tip.letters 55 | añadir letras (mayúsculas/minúsculas) 56 | 57 | 58 | rollerworks_password.tip.numbers 59 | añadir cifras 60 | 61 | 62 | rollerworks_password.tip.lowercase_letters 63 | añadir minúsculas 64 | 65 | 66 | rollerworks_password.tip.uppercase_letters 67 | añadir mayúsculas 68 | 69 | 70 | rollerworks_password.tip.special_chars 71 | añadir caracteres especiales 72 | 73 | 74 | rollerworks_password.tip.length 75 | añadir más caracteres 76 | 77 | 78 | 79 | 80 | -------------------------------------------------------------------------------- /src/Resources/translations/validators.pt_BR.xlf: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | Your password must be at least {{length}} characters long. 7 | A senha deve ter pelo menos {{length}} caracteres de comprimento. 8 | 9 | 10 | Your password must include at least one letter. 11 | A senha deve conter pelo menos uma letra. 12 | 13 | 14 | Your password must include both upper and lower case letters. 15 | A senha deve conter letras maiúsculas e minúsculas. 16 | 17 | 18 | Your password must include at least one number. 19 | A senha deve conter pelo menos um número. 20 | 21 | 22 | Your password must contain at least one special character. 23 | A senha deve conter pelo menos um caractere especial. 24 | 25 | 26 | password_too_weak 27 | A senha deve ter pelo menos o nível de intensidade "{{ min_strength }}" e o nível atual é "{{ current_strength }}". Tente o seguinte: {{ strength_tips }}. 28 | 29 | 30 | 31 | 32 | rollerworks_password.strength_level.very_weak 33 | Muito fraco 34 | 35 | 36 | rollerworks_password.strength_level.weak 37 | Fraco 38 | 39 | 40 | rollerworks_password.strength_level.medium 41 | Médio 42 | 43 | 44 | rollerworks_password.strength_level.strong 45 | Forte 46 | 47 | 48 | rollerworks_password.strength_level.very_strong 49 | Muito forte 50 | 51 | 52 | 53 | 54 | rollerworks_password.tip.letters 55 | adicionar letras (maiúsculas/minúsculas) 56 | 57 | 58 | rollerworks_password.tip.numbers 59 | adicionar números 60 | 61 | 62 | rollerworks_password.tip.lowercase_letters 63 | adicionar letras minúsculas 64 | 65 | 66 | rollerworks_password.tip.uppercase_letters 67 | adicionar letras maiúsculas 68 | 69 | 70 | rollerworks_password.tip.special_chars 71 | adicionar caracteres especiais 72 | 73 | 74 | rollerworks_password.tip.length 75 | adicionar mais caracteres 76 | 77 | 78 | 79 | 80 | -------------------------------------------------------------------------------- /src/Resources/translations/validators.it.xlf: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | Your password must be at least {{length}} characters long. 7 | La password deve contenere almeno {{length}} caratteri. 8 | 9 | 10 | Your password must include at least one letter. 11 | La password deve contenere almeno una lettera. 12 | 13 | 14 | Your password must include both upper and lower case letters. 15 | La password deve contenere almeno delle maiuscole e delle minuscole. 16 | 17 | 18 | Your password must include at least one number. 19 | La password deve contenere almeno una cifra. 20 | 21 | 22 | Your password must contain at least one special character. 23 | La password deve contenere almeno un carattere speciale. 24 | 25 | 26 | password_too_weak 27 | La password deve avere una forza di almeno {{ min_strength }}"; la forza attuale è "{{ current_strength }}"; provare quanto segue: {{ strength_tips }}. 28 | 29 | 30 | 31 | 32 | rollerworks_password.strength_level.very_weak 33 | Molto debole 34 | 35 | 36 | rollerworks_password.strength_level.weak 37 | Debole 38 | 39 | 40 | rollerworks_password.strength_level.medium 41 | Media 42 | 43 | 44 | rollerworks_password.strength_level.strong 45 | Forte 46 | 47 | 48 | rollerworks_password.strength_level.very_strong 49 | Molto forte 50 | 51 | 52 | 53 | 54 | rollerworks_password.tip.letters 55 | aggiungi delle lettere (maiuscole/minuscole) 56 | 57 | 58 | rollerworks_password.tip.numbers 59 | aggiungi delle cifre 60 | 61 | 62 | rollerworks_password.tip.lowercase_letters 63 | aggiungi delle minuscole 64 | 65 | 66 | rollerworks_password.tip.uppercase_letters 67 | aggiungi delle maiuscole 68 | 69 | 70 | rollerworks_password.tip.special_chars 71 | aggiungi dei caratteri speciali 72 | 73 | 74 | rollerworks_password.tip.length 75 | aggiungi più caratteri 76 | 77 | 78 | 79 | 80 | -------------------------------------------------------------------------------- /src/Resources/translations/validators.fr.xlf: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | Your password must be at least {{length}} characters long. 7 | Le mot de passe doit faire au moins {{length}} caractères. 8 | 9 | 10 | Your password must include at least one letter. 11 | Le mot de passe doit contenir au moins une lettre. 12 | 13 | 14 | Your password must include both upper and lower case letters. 15 | Le mot de passe doit contenir des majuscules et des minuscules. 16 | 17 | 18 | Your password must include at least one number. 19 | Le mot de passe doit contenir au moins un chiffre. 20 | 21 | 22 | Your password must contain at least one special character. 23 | Le mot de passe doit contenir au moins un caractère spécial. 24 | 25 | 26 | password_too_weak 27 | Le mot de passe doit avoir une force d'au moins "{{ min_strength }}", la force actuelle est "{{ current_strength }}", essayez ceci : {{ strength_tips }}. 28 | 29 | 30 | 31 | 32 | rollerworks_password.strength_level.very_weak 33 | Très faible 34 | 35 | 36 | rollerworks_password.strength_level.weak 37 | Faible 38 | 39 | 40 | rollerworks_password.strength_level.medium 41 | Moyenne 42 | 43 | 44 | rollerworks_password.strength_level.strong 45 | Forte 46 | 47 | 48 | rollerworks_password.strength_level.very_strong 49 | Très forte 50 | 51 | 52 | 53 | 54 | rollerworks_password.tip.letters 55 | ajouter des lettres (majuscules/minuscules) 56 | 57 | 58 | rollerworks_password.tip.numbers 59 | ajouter des chiffres 60 | 61 | 62 | rollerworks_password.tip.lowercase_letters 63 | ajouter des minuscules 64 | 65 | 66 | rollerworks_password.tip.uppercase_letters 67 | ajouter des majuscules 68 | 69 | 70 | rollerworks_password.tip.special_chars 71 | ajouter des caractères spéciaux 72 | 73 | 74 | rollerworks_password.tip.length 75 | ajouter plus de caractères 76 | 77 | 78 | 79 | 80 | -------------------------------------------------------------------------------- /src/Resources/translations/validators.nl.xlf: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | Your password must be at least {{length}} characters long. 7 | Wachtwoord moet minstens {{length}} tekens lang zijn. 8 | 9 | 10 | Your password must include at least one letter. 11 | Wachtwoord moet ten minste één letter bevatten. 12 | 13 | 14 | Your password must include both upper and lower case letters. 15 | Wachtwoord moet ten minste één hoofdletter en kleine letter bevatten. 16 | 17 | 18 | Your password must include at least one number. 19 | Wachtwoord moet ten minste één nummer bevatten. 20 | 21 | 22 | Your password must contain at least one special character. 23 | Wachtwoord moet ten minste één speciaal teken of leesteken bevatten. 24 | 25 | 26 | password_too_weak 27 | Wachtwoord moet ten minste aan veiligheidsniveau "{{ min_strength }}" voldoen, maar het huidige niveau is "{{ current_strength }}". Probeer het volgende: {{ strength_tips }}. 28 | 29 | 30 | 31 | 32 | rollerworks_password.strength_level.very_weak 33 | Erg zwak 34 | 35 | 36 | rollerworks_password.strength_level.weak 37 | Zwak 38 | 39 | 40 | rollerworks_password.strength_level.medium 41 | Gemiddeld 42 | 43 | 44 | rollerworks_password.strength_level.strong 45 | Sterk 46 | 47 | 48 | rollerworks_password.strength_level.very_strong 49 | Zeer sterk 50 | 51 | 52 | 53 | 54 | rollerworks_password.tip.letters 55 | voeg (hoofd/kleine) letters toe 56 | 57 | 58 | rollerworks_password.tip.numbers 59 | voeg cijfers toe 60 | 61 | 62 | rollerworks_password.tip.lowercase_letters 63 | voeg kleine letters toe 64 | 65 | 66 | rollerworks_password.tip.uppercase_letters 67 | voeg hoofdletters toe 68 | 69 | 70 | rollerworks_password.tip.special_chars 71 | voeg speciale tekens of leestekens toe 72 | 73 | 74 | rollerworks_password.tip.length 75 | gebruik meer tekens 76 | 77 | 78 | 79 | 80 | -------------------------------------------------------------------------------- /src/Resources/translations/validators.de.xlf: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | Your password must be at least {{length}} characters long. 7 | Das Passwort muss aus mindestens {{length}} Zeichen bestehen. 8 | 9 | 10 | Your password must include at least one letter. 11 | Das Passwort muss mindestens einen Buchstaben enthalten. 12 | 13 | 14 | Your password must include both upper and lower case letters. 15 | Das Passwort muss Groß- und Kleinbuchstaben enthalten. 16 | 17 | 18 | Your password must include at least one number. 19 | Das Passwort muss mindestens eine Ziffer enthalten. 20 | 21 | 22 | Your password must contain at least one special character. 23 | Das Passwort muss mindestens ein Sonderzeichen enthalten. 24 | 25 | 26 | password_too_weak 27 | Die Passwortstärke muss mindestens "{{ min_strength }}" sein, die aktuelle Stärke ist "{{ current_strength }}". Versuchen Sie Folgendes: {{ strength_tips }}. 28 | 29 | 30 | 31 | 32 | rollerworks_password.strength_level.very_weak 33 | Sehr schwach 34 | 35 | 36 | rollerworks_password.strength_level.weak 37 | Schwach 38 | 39 | 40 | rollerworks_password.strength_level.medium 41 | Mittel 42 | 43 | 44 | rollerworks_password.strength_level.strong 45 | Stark 46 | 47 | 48 | rollerworks_password.strength_level.very_strong 49 | Sehr stark 50 | 51 | 52 | 53 | 54 | rollerworks_password.tip.letters 55 | Buchstaben hinzufügen (Großbuchstaben/Kleinbuchstaben) 56 | 57 | 58 | rollerworks_password.tip.numbers 59 | Ziffern hinzufügen 60 | 61 | 62 | rollerworks_password.tip.lowercase_letters 63 | Kleinbuchstaben hinzufügen 64 | 65 | 66 | rollerworks_password.tip.uppercase_letters 67 | Großbuchstaben hinzufügen 68 | 69 | 70 | rollerworks_password.tip.special_chars 71 | Sonderzeichen hinzufügen 72 | 73 | 74 | rollerworks_password.tip.length 75 | Weitere Zeichen hinzufügen 76 | 77 | 78 | 79 | 80 | -------------------------------------------------------------------------------- /src/Resources/translations/validators.ru.xlf: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | Your password must be at least {{length}} characters long. 7 | Длина пароля должна быть не менее {{length}} символов. 8 | 9 | 10 | Your password must include at least one letter. 11 | Пароль должен содержать, по крайней мере, одну букву. 12 | 13 | 14 | Your password must include both upper and lower case letters. 15 | Пароль должен содержать как прописные, так и строчные буквы. 16 | 17 | 18 | Your password must include at least one number. 19 | Пароль должен содержать, по крайней мере, одну цифру. 20 | 21 | 22 | Your password must contain at least one special character. 23 | Пароль должен содержать, по крайней мере, один специальный символ. 24 | 25 | 26 | password_too_weak 27 | Пароль должен быть как минимум "{{ min_strength }}" уровня сложности, текущий уровень сложности "{{ current_strength }}", обратите внимание на эти советы: {{ strength_tips }}. 28 | 29 | 30 | 31 | 32 | rollerworks_password.strength_level.very_weak 33 | Очень слабый 34 | 35 | 36 | rollerworks_password.strength_level.weak 37 | Слабый 38 | 39 | 40 | rollerworks_password.strength_level.medium 41 | Средний 42 | 43 | 44 | rollerworks_password.strength_level.strong 45 | Сильный 46 | 47 | 48 | rollerworks_password.strength_level.very_strong 49 | Очень сильный 50 | 51 | 52 | 53 | 54 | rollerworks_password.tip.letters 55 | добавить буквы (прописные / строчные) 56 | 57 | 58 | rollerworks_password.tip.numbers 59 | добавить цифры 60 | 61 | 62 | rollerworks_password.tip.lowercase_letters 63 | добавить строчные буквы 64 | 65 | 66 | rollerworks_password.tip.uppercase_letters 67 | добавить заглавные буквы 68 | 69 | 70 | rollerworks_password.tip.special_chars 71 | добавить специальные символы 72 | 73 | 74 | rollerworks_password.tip.length 75 | добавить больше символов 76 | 77 | 78 | 79 | 80 | -------------------------------------------------------------------------------- /src/Validator/Constraints/PasswordStrengthValidator.php: -------------------------------------------------------------------------------- 1 | 9 | * 10 | * This source file is subject to the MIT license that is bundled 11 | * with this source code in the file LICENSE. 12 | */ 13 | 14 | namespace Rollerworks\Component\PasswordStrength\Validator\Constraints; 15 | 16 | use Symfony\Component\Translation\Loader\XliffFileLoader; 17 | use Symfony\Component\Translation\Translator; 18 | use Symfony\Component\Validator\Constraint; 19 | use Symfony\Component\Validator\ConstraintValidator; 20 | use Symfony\Component\Validator\Exception\UnexpectedTypeException; 21 | use Symfony\Contracts\Translation\TranslatorInterface; 22 | 23 | /** 24 | * Password strength Validation. 25 | * 26 | * Validates if the password strength is equal or higher 27 | * to the required minimum and the password length is equal 28 | * or longer than the minimum length. 29 | * 30 | * The strength is computed from various measures including 31 | * length and usage of characters. 32 | * 33 | * The strengths are marked up as follow. 34 | * 1: Very Weak 35 | * 2: Weak 36 | * 3: Medium 37 | * 4: Strong 38 | * 5: Very Strong 39 | */ 40 | class PasswordStrengthValidator extends ConstraintValidator 41 | { 42 | private TranslatorInterface $translator; 43 | 44 | /** 45 | * @var array 46 | */ 47 | private static array $levelToLabel = [ 48 | 1 => 'very_weak', 49 | 2 => 'weak', 50 | 3 => 'medium', 51 | 4 => 'strong', 52 | 5 => 'very_strong', 53 | ]; 54 | 55 | public function __construct(?TranslatorInterface $translator = null) 56 | { 57 | // If translator is missing create a new translator. 58 | // With the 'en' locale and 'validators' domain. 59 | if ($translator === null) { 60 | $translator = new Translator('en'); 61 | $translator->addLoader('xlf', new XliffFileLoader()); 62 | $translator->addResource('xlf', \dirname(__DIR__, 2) . '/Resources/translations/validators.en.xlf', 'en', 'validators'); 63 | } 64 | 65 | $this->translator = $translator; 66 | } 67 | 68 | public function validate(mixed $value, Constraint $constraint): void 69 | { 70 | if ($value === null || $value === '') { 71 | return; 72 | } 73 | 74 | if (! $constraint instanceof PasswordStrength) { 75 | throw new UnexpectedTypeException($constraint, PasswordStrength::class); 76 | } 77 | 78 | if (! \is_scalar($value) && ! (\is_object($value) && method_exists($value, '__toString'))) { 79 | throw new UnexpectedTypeException($value, 'string'); 80 | } 81 | 82 | $value = (string) $value; 83 | $passLength = mb_strlen($value); 84 | 85 | if ($passLength < $constraint->minLength) { 86 | $this->context->buildViolation($constraint->tooShortMessage) 87 | ->setParameters(['{{length}}' => $constraint->minLength]) 88 | ->addViolation() 89 | ; 90 | 91 | return; 92 | } 93 | 94 | $tips = []; 95 | 96 | if ($constraint->unicodeEquality) { 97 | $passwordStrength = $this->calculateStrengthUnicode($value, $tips); 98 | } else { 99 | $passwordStrength = $this->calculateStrength($value, $tips); 100 | } 101 | 102 | if ($passLength > 12) { 103 | ++$passwordStrength; 104 | } else { 105 | $tips[] = 'length'; 106 | } 107 | 108 | // There is no decrease of strength on weak combinations. 109 | // Detecting this is tricky and requires a deep understanding of the syntax. 110 | 111 | if ($passwordStrength < $constraint->minStrength) { 112 | $parameters = [ 113 | '{{ length }}' => $constraint->minLength, 114 | '{{ min_strength }}' => $this->translator->trans(/* @Ignore */ 'rollerworks_password.strength_level.' . self::$levelToLabel[$constraint->minStrength], [], 'validators'), 115 | '{{ current_strength }}' => $this->translator->trans(/* @Ignore */ 'rollerworks_password.strength_level.' . self::$levelToLabel[$passwordStrength], [], 'validators'), 116 | '{{ strength_tips }}' => implode(', ', array_map([$this, 'translateTips'], $tips)), 117 | ]; 118 | 119 | $this->context->buildViolation($constraint->message) 120 | ->setParameters($parameters) 121 | ->addViolation() 122 | ; 123 | } 124 | } 125 | 126 | private function translateTips(string $tip): string 127 | { 128 | return $this->translator->trans(/* @Ignore */ 'rollerworks_password.tip.' . $tip, [], 'validators'); 129 | } 130 | 131 | /** 132 | * @param array $tips 133 | */ 134 | private function calculateStrength(string $password, array &$tips): int 135 | { 136 | $passwordStrength = 0; 137 | 138 | if (preg_match('/[a-zA-Z]/', $password)) { 139 | ++$passwordStrength; 140 | 141 | if (! preg_match('/[a-z]/', $password)) { 142 | $tips[] = 'lowercase_letters'; 143 | } elseif (preg_match('/[A-Z]/', $password)) { 144 | ++$passwordStrength; 145 | } else { 146 | $tips[] = 'uppercase_letters'; 147 | } 148 | } else { 149 | $tips[] = 'letters'; 150 | } 151 | 152 | if (preg_match('/\d+/', $password)) { 153 | ++$passwordStrength; 154 | } else { 155 | $tips[] = 'numbers'; 156 | } 157 | 158 | if (preg_match('/[^a-zA-Z0-9]/', $password)) { 159 | ++$passwordStrength; 160 | } else { 161 | $tips[] = 'special_chars'; 162 | } 163 | 164 | return $passwordStrength; 165 | } 166 | 167 | /** 168 | * @param array $tips 169 | */ 170 | private function calculateStrengthUnicode(string $password, array &$tips): int 171 | { 172 | $passwordStrength = 0; 173 | 174 | if (preg_match('/\p{L}/u', $password)) { 175 | ++$passwordStrength; 176 | 177 | if (! preg_match('/\p{Ll}/u', $password)) { 178 | $tips[] = 'lowercase_letters'; 179 | } elseif (preg_match('/\p{Lu}/u', $password)) { 180 | ++$passwordStrength; 181 | } else { 182 | $tips[] = 'uppercase_letters'; 183 | } 184 | } else { 185 | $tips[] = 'letters'; 186 | } 187 | 188 | if (preg_match('/\p{N}/u', $password)) { 189 | ++$passwordStrength; 190 | } else { 191 | $tips[] = 'numbers'; 192 | } 193 | 194 | if (preg_match('/[^\p{L}\p{N}]/u', $password)) { 195 | ++$passwordStrength; 196 | } else { 197 | $tips[] = 'special_chars'; 198 | } 199 | 200 | return $passwordStrength; 201 | } 202 | } 203 | --------------------------------------------------------------------------------