* Copyright (C) 2014 Teddy Andreotti <125155@supinfo.com> * Copyright (C) 2017 Regis Houssin * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program. If not, see . * or see http://www.gnu.org/ */ /** * \file htdocs/core/modules/security/generate/modGeneratePassPerso.class.php * \ingroup core * \brief File to manage no password generation. */ require_once DOL_DOCUMENT_ROOT .'/core/modules/security/generate/modules_genpassword.php'; /** * \class modGeneratePassPerso * \brief Class to generate a password according to personal rules */ class modGeneratePassPerso extends ModeleGenPassword { var $id; var $length; var $length2; // didn't overright display var $NbMaj; var $NbNum; var $NbSpe; var $NbRepeat; var $WithoutAmbi; var $db; var $conf; var $lang; var $user; var $Maj; var $Min; var $Nb; var $Spe; var $Ambi; var $All; /** * Constructor * * @param DoliDB $db Database handler * @param Conf $conf Handler de conf * @param Translate $langs Handler de langue * @param User $user Handler du user connecte */ function __construct($db, $conf, $langs, $user) { $this->id = "Perso"; $this->length = $langs->trans("SetupPerso"); $this->db=$db; $this->conf=$conf; $this->langs=$langs; $this->user=$user; if(empty($conf->global->USER_PASSWORD_PATTERN)){ // default value (8carac, 1maj, 1digit, 1spe, 3 repeat, no ambi at auto generation. dolibarr_set_const($db, "USER_PASSWORD_PATTERN", '8;1;1;1;3;1','chaine',0,'',$conf->entity); } $this->Maj = "ABCDEFGHIJKLMNOPQRSTUVWXYZ"; $this->Min = strtolower($this->Maj); $this->Nb = "0123456789"; $this->Spe = "!@#$%&*()_-+={}[]\\|:;'/"; $this->Ambi = array("1","I","l","|","O","0"); $tabConf = explode(";",$conf->global->USER_PASSWORD_PATTERN); $this->length2 = $tabConf[0]; $this->NbMaj = $tabConf[1]; $this->NbNum = $tabConf[2]; $this->NbSpe = $tabConf[3]; $this->NbRepeat = $tabConf[4]; $this->WithoutAmbi = $tabConf[5]; if ($this->WithoutAmbi) { $this->Maj = str_replace($this->Ambi,"",$this->Maj); $this->Min = str_replace($this->Ambi,"",$this->Min); $this->Nb = str_replace($this->Ambi,"",$this->Nb); $this->Spe = str_replace($this->Ambi,"",$this->Spe); } $pattern = $this->Min . (! empty($this->NbMaj)?$this->Maj:'') . (! empty($this->NbNum)?$this->Nb:'') . (! empty($this->NbSpe)?$this->Spe:''); $this->All = str_shuffle($pattern); //$this->All = str_shuffle($this->Maj. $this->Min. $this->Nb. $this->Spe); //$this->All = $this->Maj. $this->Min. $this->Nb. $this->Spe; //$this->All = $this->Spe; } /** * Return description of module * * @return string Description of text */ function getDescription() { global $langs; return $langs->trans("PasswordGenerationPerso"); } /** * Return an example of password generated by this module * * @return string Example of password */ function getExample() { return $this->getNewGeneratedPassword(); } /** * Build new password * * @return string Return a new generated password */ function getNewGeneratedPassword() { $pass = ""; for($i=0; $i<$this->NbMaj; $i++){ // Y $pass .= $this->Maj[mt_rand(0,strlen($this->Maj) - 1)]; } for($i=0; $i<$this->NbNum; $i++){ // X $pass .= $this->Nb[mt_rand(0,strlen($this->Nb) - 1)]; } for($i=0; $i<$this->NbSpe; $i++){ // @ $pass .= $this->Spe[mt_rand(0,strlen($this->Spe) - 1)]; } for($i=strlen($pass);$i<$this->length2; $i++){ // y $pass .= $this->All[mt_rand(0,strlen($this->All) -1)]; } $pass = str_shuffle($pass); if ($this->validatePassword($pass)) { return $pass; } return $this->getNewGeneratedPassword(); } /** * Validate a password * * @param string $password Password to check * @return int 0 if KO, >0 if OK */ function validatePassword($password) { $password_a = str_split($password); $maj = str_split($this->Maj); $num = str_split($this->Nb); $spe = str_split($this->Spe); if(count(array_intersect($password_a, $maj)) < $this->NbMaj){ return 0; } if(count(array_intersect($password_a, $num)) < $this->NbNum){ return 0; } if(count(array_intersect($password_a, $spe)) < $this->NbSpe){ return 0; } if(!$this->consecutiveInterationSameCharacter($password)){ return 0; } return 1; } /** * consecutive iterations of the same character * * @param string $password Password to check * @return int 0 if KO, >0 if OK */ function consecutiveInterationSameCharacter($password){ $last = ""; $count = 0; $char = str_split($password); foreach($char as $c){ if($c != $last){ $last = $c; $count = 0; }else{ $count++; } if($count >= $this->NbRepeat) { return 0; } } return 1; } }