CoolFace
Apppublic

kenken999/php

sourceHugging Faceupdated 2y agoView on Hugging Face
0likes
changepwdpage.php490 linesDownload Raw Back to classes
1<?php2class ChangePasswordPage extends RunnerPage3{4	protected $pwdStrong = false;5 6	public $token = "";7 8	public $action;9 10	protected $passwordField;11	protected $usernameField;12 13	protected $auditObj = null;14 15	protected $changePwdFields;16 17	protected $changedSuccess = false;18 19	/**20	 *21	 */22	function __construct(&$params = "")23	{24		parent::__construct($params);25 26		if( !$this->action && !$this->checkToken() )27		{28			Security::saveRedirectURL();29			HeaderRedirect("login");30			return;31		}32 33		$this->passwordField = Security::passwordField();34		$this->usernameField = Security::usernameField();35 36		$this->auditObj = GetAuditObject();37 38		if( $this->token )39		{40			$this->changePwdFields = array("newpass", "confirm");41			// to send it back with a form (user may delete session before submit)42			$this->setProxyValue("token", $this->token);43		}44		else45			$this->changePwdFields = array("oldpass", "newpass", "confirm");46 47		// fill global password settings48		$this->pwdStrong = GetGlobalData("pwdStrong", false);49 50		if( $this->pwdStrong )51		{52			$this->settingsMap["globalSettings"]["pwdStrong"] = true;53			$this->settingsMap["globalSettings"]["pwdLen"] = GetGlobalData("pwdLen", 0);54			$this->settingsMap["globalSettings"]["pwdUnique"] = GetGlobalData("pwdUnique", 0);55			$this->settingsMap["globalSettings"]["pwdDigits"] = GetGlobalData("pwdDigits", 0);56			$this->settingsMap["globalSettings"]["pwdUpperLower"] = GetGlobalData("pwdUpperLower", false);57		}58 59		$this->headerForms = array( "top" );60		$this->footerForms = array( "footer" );61		$this->bodyForms = array( "above-grid", "grid" );62	}63 64	/**65	 * Set the connection property66	 */67	protected function setTableConnection()68	{69		global $cman;70		$this->connection = $cman->getForLogin();71	}72 73	/**74	 *75	 */76	protected function assignCipherer()77	{78		$this->cipherer = RunnerCipherer::getForLogin();79	}80 81	/**82	 *83	 */84	protected function setReferer()85	{86		$referer = @$_SERVER["HTTP_REFERER"] ? @$_SERVER["HTTP_REFERER"] : "";87 88		// ignore referer if from another site or if came from the same "change password" page89		$home = strtoupper( projectUrl() );90		$changePwdPage = strtoupper( projectUrl() . GetTableLink("changepwd") );91		if( substr( strtoupper( $referer ), 0 , strlen( $home ) ) != $home ||92			substr( strtoupper( $referer ), 0 , strlen( $changePwdPage ) ) == $changePwdPage ) {93		94			$referer = "";95		}96 97		if( $referer ) {98			$_SESSION["changepwd_referer"] = $referer;99		}100		if( !$_SESSION["changepwd_referer"] ) {101			$_SESSION["changepwd_referer"] = projectUrl();102		}103 104	}105 106	/**107	 * @return DsCondition108	 */109	protected function getTokenCondition() {110		return DataCondition::FieldEquals( "reset_token", $this->token );111	}112 113	/**114	 * @return DsCondition115	 */116	protected function getUsernameCondition() {117		if( $this->token ) {118			return $this->getTokenCondition();119		}120 121		$caseInsensitive = Security::caseInsensitiveUsername() ? dsCASE_INSENSITIVE : dsCASE_STRICT;122		return DataCondition::FieldEquals( $this->usernameField, Security::getUserName(), 0, $caseInsensitive );123	}124 125	/**126	 * @param String newpass127	 * @return 128	 */129	protected function getUpdateCommand( $newpass ) {130		$dc = new DsCommand();131 132		if( GetGlobalData( "bEncryptPasswords" ) ) {133			if( !$this->cipherer->isFieldEncrypted( $this->passwordField ) )134				$newpass = Security::hashPassword( $newpass );135		}136 137		$values = array();138		$values[ $this->passwordField ] = $newpass;139		if( $this->token ) {140			$values[ "reset_token" ] = "";141			$values[ "reset_date" ] = NULL;142			if( GetGlobalData( "userRequireActivation" ) ) {143				$values[  GetGlobalData( "userActivationField" ) ] = "1";144			}145		}146 147		$dc->values = $values;148		$dc->filter = $this->getUsernameCondition();149		return $dc;150	}151 152 153	/**154	 * @return Array155	 */156	protected function getControlValues()157	{158		$filename_values = array();159		$blobfields = array();160		$values = array();161		foreach( $this->changePwdFields as $fName )162		{163			$fControl = $this->getControl( $fName, $this->id );164			$fControl->readWebValue( $values, $blobfields, NULL, NULL, $filename_values );165		}166 167		return $values;168	}169 170 171	/**172	 * @return Boolean173	 */174	protected function changePassword() {175		//	CSRF protection176		if( !isPostRequest() )177			return;178 179		global $globalEvents;180 181		$values = $this->getControlValues();182 183		$dc = new DsCommand();184		$dc->filter = $this->getUsernameCondition();185		$qResult = $this->dataSource->getList( $dc );186 187		$data = $qResult->fetchAssoc();188		$row = $this->cipherer->DecryptFetchedArray( $data );189 190		$dbOldPass = "";191		if( !$row ) {192			$this->message = "Invalid password";193			return false;194		}195 196		$dbOldPass = $row[ $this->passwordField ];197		$username = $row[ $this->usernameField ];198 199		if( !$this->token && $this->pSet->hasOldPassField() ) {200			if( !Security::verifyPassword( $values["oldpass"], $dbOldPass ) ) {201				$this->message = "Invalid password";202				return false;203			}204		}205 206		$oldPass = $dbOldPass;207 208		$newPass = $values["newpass"];209		if( $this->pwdStrong && !checkpassword( $newPass ) ) {210			$this->message = $this->getPwdStrongFailedMessage();211			$this->jsSettings["tableSettings"][ $this->tName ]["msg_passwordError"] = $this->message;212			return false;213		}214 215		$retval = true;216		if( $globalEvents->exists("BeforeChangePassword") )217			$retval = $globalEvents->BeforeChangePassword( $oldPass, $newPass, $this );218 219		$values["newpass"] = $newPass;220		if( $retval ) {221			$dc = $this->getUpdateCommand( $values["newpass"] );222			$this->dataSource->updateSingle( $dc, false );223 224			if( $this->auditObj )225				$this->auditObj->LogChPassword( $username );226 227			if( $globalEvents->exists("AfterChangePassword") )228				$globalEvents->AfterChangePassword( $oldPass, $values["newpass"], $this );229		}230 231		return $retval;232	}233 234	/**235	 * @return String236	 */237	protected function getPwdStrongFailedMessage()238	{239		$msg = "";240		$pwdLen = GetGlobalData("pwdLen", 0);241		if($pwdLen)242		{243			$fmt = "Password must be at least %% characters length.";244			$fmt = str_replace("%%", "".$pwdLen, $fmt);245			$msg.= "<br>".$fmt;246		}247		$pwdUnique = GetGlobalData("pwdUnique", 0);248		if($pwdUnique)249		{250			$fmt = "Password must contain %% unique characters.";251			$fmt = str_replace("%%", "".$pwdUnique, $fmt);252			$msg.= "<br>".$fmt;253		}254		$pwdDigits = GetGlobalData("pwdDigits", 0);255		if($pwdDigits)256		{257			$fmt = "Password must contain %% digits or symbols.";258			$fmt = str_replace("%%", "".$pwdDigits, $fmt);259			$msg.= "<br>".$fmt;260		}261		if(GetGlobalData("pwdUpperLower", false))262		{263			$fmt = "Password must contain letters in upper and lower case.";264			$msg.= "<br>".$fmt;265		}266 267		if($msg)268			$msg = substr($msg, 4);269 270		return $msg;271	}272 273	/**274	 *275	 */276	public function process()277	{278		global $globalEvents;279 280		$this->setReferer();281 282		//	Before Process event283		if( $globalEvents->exists("BeforeProcessChangePwd") )284			$globalEvents->BeforeProcessChangePwd( $this );285 286		if( $this->action == "Change" ) {287			$this->changedSuccess = $this->changePassword();288		289			if( !$this->changedSuccess && $this->mode == CHANGEPASS_POPUP ) {290				$returnJSON = array();291				$returnJSON['success'] = false;292					293				if( strlen( $this->message ) )294					$returnJSON['message'] = $this->message;295				296				if( !$this->isCaptchaOk )297					$returnJSON['wrongCaptchaFieldName'] = $this->getCaptchaFieldName();298					299				echo printJSON( $returnJSON );300				exit();301			}302		}303 304		if( !$this->changedSuccess ) {305			$this->prepareEditControls();306		} else {307			$this->pageName = $this->pSet->getDefaultPage( $this->successPageType() );308			$this->pSet = new ProjectSettings( $this->tName, $this->successPageType(), $this->pageName, $this->pageTable );309 310			$this->pageData["buttons"] = array_merge( $this->pageData["buttons"], $this->pSet->buttons() );311			foreach( $this->pSet->buttons() as $b ) {312				$this->AddJSFile( "include/button_".$b.".js" );313			}314		}315 316		$this->addCommonJs();317		$this->fillSetCntrlMaps();318		$this->addButtonHandlers();319		$this->doCommonAssignments();320 321		$this->showPage();322	}323 324	/**325	 * @param Boolean logged326	 */327	protected function reportChangeStatus( $changed )328	{329		$returnJSON = array();330 331		$returnJSON["message"] = $this->message;332		$returnJSON["success"] = true;333 334		echo printJSON( $returnJSON );335		exit();336	}	337	338	/**339	 *340	 */341	protected function prepareEditControls()342	{343		foreach($this->changePwdFields as $fName)344		{345			$parameters = array();346			$parameters["id"] = $this->id;347			$parameters["mode"] = "add";348			$parameters["field"] = $fName;349			$parameters["format"] = "Password";350			$parameters["pageObj"] = $this;351			$parameters["suggest"] = true;352			$parameters["validate"] = array('basicValidate' => array('IsRequired'));353 354			$parameters["extraParams"] = array();355			$parameters["extraParams"]["getConrirmFieldCtrl"] = true;356 357			$controls = array('controls' => array());358			$controls["controls"]['id'] = $this->id;359			$controls["controls"]['mode'] = "add";360			$controls["controls"]['ctrlInd'] = 0;361			$controls["controls"]['fieldName'] = $fName;362			$controls["controls"]['suggest'] = $parameters["suggest"];363 364			$this->xt->assign_function( $fName."_editcontrol", "xt_buildeditcontrol", $parameters );365			$this->xt->assign($fName."_label", true);366 367			$this->xt->assign("labelfor_" . goodFieldName($fName), "value_".$fName."_".$this->id);368 369			if( $this->is508 )370				$this->xt->assign_section($fName."_label", "<label for=\"value_".$fName."_".$this->id."\">", "</label>");371 372			$this->xt->assign($fName."_block", true);373 374			$this->fillControlsMap($controls);375		}376	}377 378	/**379	 *380	 */381	protected function assignBody()382	{383		$this->body["begin"] .= GetBaseScriptsForPage(false);384		$this->body["end"] = XTempl::create_method_assignment( "assignBodyEnd", $this );385 386		$this->xt->assignbyref("body", $this->body);387	}388 389	/**390	 *391	 */392	protected function doCommonAssignments()393	{394		$this->xt->assign("submit_attrs", "id=\"saveButton".$this->id."\"");395		396		if( $this->mode == CHANGEPASS_POPUP ) {397			$this->hideItemType("changepwd_back");398			if( $this->changedSuccess )399				$this->xt->assign("backlink_attrs", "id=\"backButton".$this->id."\"");400		} else {401			$this->xt->assign("backlink_attrs", "href=\"". runner_htmlspecialchars( $_SESSION["changepwd_referer"] )."\"");402		}403			404		$this->xt->assign("message_block", true);405		if( $this->message ) {406			$this->xt->assign("message_class", "alert-danger" );407			$this->xt->assign("message", $this->message);408		} else {409			$this->hideElement("message");410		}411 412		$this->assignBody();413	}414 415	/**416	 *417	 */418	protected function showPage() {419		global $globalEvents;420 421		if( $this->changedSuccess )422			$this->switchToSuccessPage();423 424		$templatefile = $this->templatefile;425		426		if( $globalEvents->exists("BeforeShowChangePwd") )427			$globalEvents->BeforeShowChangePwd( $this->xt, $templatefile, $this );428 429		if( $this->mode == CHANGEPASS_POPUP )430		{431			$this->xt->assign("footer", false);432			$this->xt->assign("header", false);433			$this->xt->assign("body", $this->body);434 435			$this->displayAJAX( $templatefile, $this->id + 1 );436			exit();437		}		438		439		$this->display( $templatefile );440	}441 442	/**443	 * @return String444	 */445	public static function readActionFromRequest()446	{447		if( @$_POST["btnSubmit"] )448			return @$_POST["btnSubmit"];449 450		return "";451	}452 453	/**454	 * @return Boolean455	 */456	protected function checkToken()457	{458		if( !$this->token )459			return true;460 461		$dc = new DsCommand();462		$dc->filter = $this->getTokenCondition();463		$qResult = $this->dataSource->getList( $dc );464		465		$data = $this->cipherer->DecryptFetchedArray( $qResult->fetchAssoc() );466		if( $data )467			return secondsPassedFrom( $data["reset_date"] ) < 86400;468 469		return false;470	}471	472	/**473	 * @return Number474	 */475	public static function readModeFromRequest()476	{477		if( postvalue("mode") == "popup" )478			return CHANGEPASS_POPUP;479 480		return CHANGEPASS_SIMPLE;481	}482 483	function element2Item( $name ) {484		if( $name == "message" ) {485			return array( "changepwd_message" );486		}487		return parent::element2Item( $name );488	}	489}490?>