浏览代码

Debug v18

Laurent Destailleur 2 年之前
父节点
当前提交
49faae3a0b

+ 1 - 1
htdocs/bookmarks/bookmarks.lib.php

@@ -204,7 +204,7 @@ function printDropdownBookmarksList()
 		';
 
 		$html .= '
-				<!-- Menu Body -->
+				<!-- Menu Body bookmarks -->
 				<div class="bookmark-body dropdown-body">'.$bookmarkList.'
 				<span id="top-bookmark-search-nothing-found" class="'.($bookmarkNb ? 'hidden-search-result ' : '').'opacitymedium">'.dol_escape_htmltag($langs->trans("NoBookmarkFound")).'</span>
 				</div>

+ 22 - 22
htdocs/core/login/functions_googleoauth.php

@@ -47,7 +47,7 @@ function check_user_password_googleoauth($usertotest, $passwordtotest, $entityto
 
 	// Get identity from user and redirect browser to Google OAuth Server
 	if (GETPOST('actionlogin') == 'login') {
-		if (!GETPOST('aftergoogleoauthreturn')) {
+		if (GETPOST('beforeoauthloginredirect')) {
 			// We post the form on the login page by clicking on the link to login using Google.
 			dol_syslog("We post the form on the login page by clicking on the link to login using Google");
 
@@ -70,27 +70,27 @@ function check_user_password_googleoauth($usertotest, $passwordtotest, $entityto
 			);
 
 			// Make the redirect to the google_authcallback.php page to start the redirect to Google OAUTH.
-			/*
-				global $dolibarr_main_url_root;
-
-				// Define $urlwithroot
-				$urlwithouturlroot = preg_replace('/'.preg_quote(DOL_URL_ROOT, '/').'$/i', '', trim($dolibarr_main_url_root));
-				$urlwithroot = $urlwithouturlroot.DOL_URL_ROOT; // This is to use external domain name found into config file
-				//$urlwithroot=DOL_MAIN_URL_ROOT;					// This is to use same domain name than current
-
-				//$shortscope = 'userinfo_email,userinfo_profile';
-				$shortscope = 'openid,email,profile';	// For openid connect
-
-				$oauthstateanticsrf = bin2hex(random_bytes(128/8));
-				$_SESSION['oauthstateanticsrf'] = $shortscope.'-'.$oauthstateanticsrf;
-				// TODO Can add param hd and login_hit
-				$urltorenew = $urlwithroot.'/core/modules/oauth/google_oauthcallback.php?shortscope='.$shortscope.'&state=forlogin-'.$shortscope.'-'.$oauthstateanticsrf;
-
-				// we go on oauth provider authorization page
-				header('Location: '.$url);
-				exit();
-			*/
-		} else {
+
+			// Define $urlwithroot
+			//global $dolibarr_main_url_root;
+			//$urlwithouturlroot = preg_replace('/'.preg_quote(DOL_URL_ROOT, '/').'$/i', '', trim($dolibarr_main_url_root));
+			//$urlwithroot = $urlwithouturlroot.DOL_URL_ROOT; // This is to use external domain name found into config file
+			$urlwithroot=DOL_MAIN_URL_ROOT;					// This is to use same domain name than current
+
+			//$shortscope = 'userinfo_email,userinfo_profile';
+			$shortscope = 'openid,email,profile';	// For openid connect
+
+			$oauthstateanticsrf = bin2hex(random_bytes(128/8));
+			$_SESSION['oauthstateanticsrf'] = $shortscope.'-'.$oauthstateanticsrf;
+
+			$url = $urlwithroot.'/core/modules/oauth/google_oauthcallback.php?shortscope='.urlencode($shortscope).'&state='.urlencode('forlogin-'.$shortscope.'-'.$oauthstateanticsrf).'&username='.urlencode($usertotest);
+
+			// we go on oauth provider authorization page
+			header('Location: '.$url);
+			exit();
+		}
+
+		if (GETPOST('afteroauthloginreturn')) {
 			// We reach this code after a call of a redirect to the targeted page from the callback url page of Google OAUTH2
 			dol_syslog("We reach the code after a call of a redirect to the targeted page from the callback url page of Google OAUTH2");
 

+ 74 - 47
htdocs/core/modules/oauth/google_oauthcallback.php

@@ -45,11 +45,12 @@ use OAuth\Common\Consumer\Credentials;
 use OAuth\OAuth2\Service\Google;
 
 // Define $urlwithroot
+global $dolibarr_main_url_root;
 $urlwithouturlroot = preg_replace('/'.preg_quote(DOL_URL_ROOT, '/').'$/i', '', trim($dolibarr_main_url_root));
 $urlwithroot = $urlwithouturlroot.DOL_URL_ROOT; // This is to use external domain name found into config file
 //$urlwithroot=DOL_MAIN_URL_ROOT;					// This is to use same domain name than current
 
-
+$langs->load("oauth");
 
 $action = GETPOST('action', 'aZ09');
 $backtourl = GETPOST('backtourl', 'alpha');
@@ -124,8 +125,6 @@ $apiService = $serviceFactory->createService('Google', $credentials, $storage, $
 $apiService->setAccessType('offline');
 
 
-$langs->load("oauth");
-
 if (!getDolGlobalString($keyforparamid)) {
 	accessforbidden('Setup of service '.$keyforparamid.' is not complete. Customer ID is missing');
 }
@@ -138,7 +137,6 @@ if (!getDolGlobalString($keyforparamsecret)) {
  * Actions
  */
 
-
 if ($action == 'delete') {
 	$storage->clearToken('Google');
 
@@ -148,13 +146,67 @@ if ($action == 'delete') {
 	exit();
 }
 
-if (GETPOST('code')) {     // We are coming from oauth provider page.
+if (!GETPOST('code')) {
+	// If we enter this page without 'code' parameter, we arrive here. This is the case when we want to get the redirect
+	// to the OAuth provider login page.
+	$_SESSION["backtourlsavedbeforeoauthjump"] = $backtourl;
+	$_SESSION["oauthkeyforproviderbeforeoauthjump"] = $keyforprovider;
+	$_SESSION['oauthstateanticsrf'] = $state;
+
+	if ($forlogin) {
+		$apiService->setApprouvalPrompt('force');
+	}
+
+	// This may create record into oauth_state before the header redirect.
+	// Creation of record with state in this tables depend on the Provider used (see its constructor).
+	if ($state) {
+		$url = $apiService->getAuthorizationUri(array('state' => $state));
+	} else {
+		$url = $apiService->getAuthorizationUri(); // Parameter state will be randomly generated
+	}
+	// The redirect_uri is included into this $url
+
+	// Add more param
+	$url .= '&nonce='.bin2hex(random_bytes(64/8));
+
+	if ($forlogin) {
+		// TODO Add param hd. What is it for ?
+		//$url .= 'hd=xxx';
+
+		if (GETPOST('username')) {
+			$url .= '&login_hint='.urlencode(GETPOST('username'));
+		}
+
+		// Check that the redirect_uri that wil be used is same than url of current domain
+
+		// Define $urlwithroot
+		global $dolibarr_main_url_root;
+		$urlwithouturlroot = preg_replace('/'.preg_quote(DOL_URL_ROOT, '/').'$/i', '', trim($dolibarr_main_url_root));
+		$urlwithroot = $urlwithouturlroot.DOL_URL_ROOT; // This is to use external domain name found into config file
+		//$urlwithroot = DOL_MAIN_URL_ROOT;				// This is to use same domain name than current
+
+		include DOL_DOCUMENT_ROOT.'/core/lib/geturl.lib.php';
+		$currentrooturl = getRootURLFromURL(DOL_MAIN_URL_ROOT);
+		$externalrooturl = getRootURLFromURL($urlwithroot);
+
+		if ($currentrooturl != $externalrooturl) {
+			$langs->load("errors");
+			setEventMessages($langs->trans("ErrorTheUrlOfYourDolInstanceDoesNotMatchURLIntoOAuthSetup", $currentrooturl, $externalrooturl), null, 'errors');
+			$url = DOL_URL_ROOT;
+		}
+	}
+
+	// we go on oauth provider authorization page
+	header('Location: '.$url);
+	exit();
+} else {
+	// We are coming from the return of an OAuth2 provider page.
 	dol_syslog("We are coming from the oauth provider page keyforprovider=".$keyforprovider." code=".dol_trunc(GETPOST('code'), 5));
 
 	// We must validate that the $state is the same than the one into $_SESSION['oauthstateanticsrf'], return error if not.
 	if (isset($_SESSION['oauthstateanticsrf']) && $state != $_SESSION['oauthstateanticsrf']) {
 		//var_dump($_SESSION['oauthstateanticsrf']);exit;
-		print 'Value for state = '.dol_escape_htmltag($state).' differs from value in $_SESSION["oauthstateanticsrf"]. Code is refused.';
+		print 'Value for state='.dol_escape_htmltag($state).' differs from value in $_SESSION["oauthstateanticsrf"]. Code is refused.';
 		unset($_SESSION['oauthstateanticsrf']);
 	} else {
 		// This was a callback request from service, get the token
@@ -228,11 +280,14 @@ if (GETPOST('code')) {     // We are coming from oauth provider page.
 				if ($forlogin) {
 					dol_syslog("we received the login/email to log to, it is ".$useremail);
 
+					$tmparray = (empty($_SESSION['datafromloginform']) ? array() : $_SESSION['datafromloginform']);
+					$entitytosearchuser = (isset($tmparray['entity']) ? $tmparray['entity'] : -1);
+
 					// Delete the token
 					$storage->clearToken('Google');
 
 					$tmpuser = new User($db);
-					$res = $tmpuser->fetch(0, '', '', 0, -1, $useremail);
+					$res = $tmpuser->fetch(0, '', '', 0, $entitytosearchuser, $useremail);
 
 					if ($res > 0) {
 						$username = $tmpuser->login;
@@ -240,14 +295,18 @@ if (GETPOST('code')) {     // We are coming from oauth provider page.
 						$_SESSION['googleoauth_receivedlogin'] = dol_hash($conf->file->instance_unique_id.$username, '0');
 						dol_syslog('$_SESSION[\'googleoauth_receivedlogin\']='.$_SESSION['googleoauth_receivedlogin']);
 					} else {
-						$_SESSION["dol_loginmesg"] = "Failed to login using Google. User with this Email not found.";
+						$errormessage = "Failed to login using Google. User with the Email '".$useremail."' was not found";
+						if ($entitytosearchuser > 0) {
+							$errormessage .= ' ('.$langs->trans("Entity").' '.$entitytosearchuser.')';
+						}
+						$_SESSION["dol_loginmesg"] = $errormessage;
 						$errorincheck++;
 					}
 				}
 			} else {
 				// If call back to url for a OAUTH2 login
 				if ($forlogin) {
-					$_SESSION["dol_loginmesg"] = "Failed to login using Google. OAuth callback URL retreives a token with non valid data.";
+					$_SESSION["dol_loginmesg"] = "Failed to login using Google. OAuth callback URL retreives a token with non valid data";
 					$errorincheck++;
 				}
 			}
@@ -264,9 +323,13 @@ if (GETPOST('code')) {     // We are coming from oauth provider page.
 			if (empty($backtourl)) {
 				$backtourl = DOL_URL_ROOT;
 			}
+
 			// If call back to url for a OAUTH2 login
 			if ($forlogin) {
-				$backtourl .= '?actionlogin=login&aftergoogleoauthreturn=1&username='.urlencode($username).'&token='.newToken();
+				$backtourl .= '?actionlogin=login&afteroauthloginreturn=1&username='.urlencode($username).'&token='.newToken();
+				if (!empty($tmparray['entity'])) {
+					$backtourl .= '&entity='.$tmparray['entity'];
+				}
 			}
 
 			dol_syslog("Redirect now on backtourl=".$backtourl);
@@ -277,42 +340,6 @@ if (GETPOST('code')) {     // We are coming from oauth provider page.
 			print $e->getMessage();
 		}
 	}
-} else {
-	// If we enter this page without 'code' parameter, we arrive here. This is the case when we want to get the redirect
-	// to the OAuth provider login page.
-	$_SESSION["backtourlsavedbeforeoauthjump"] = $backtourl;
-	$_SESSION["oauthkeyforproviderbeforeoauthjump"] = $keyforprovider;
-	$_SESSION['oauthstateanticsrf'] = $state;
-
-	if ($forlogin) {
-		$apiService->setApprouvalPrompt('force');
-	}
-
-	// This may create record into oauth_state before the header redirect.
-	// Creation of record with state in this tables depend on the Provider used (see its constructor).
-	if ($state) {
-		$url = $apiService->getAuthorizationUri(array('state' => $state));
-	} else {
-		$url = $apiService->getAuthorizationUri(); // Parameter state will be randomly generated
-	}
-
-	// Add more param
-	$url .= '&nonce='.bin2hex(random_bytes(64/8));
-
-	if ($forlogin) {
-		// TODO Add param hd
-		//$url .= 'hd=xxx';
-		if (GETPOST('login_hint')) {
-			$url .= '&login_hint='.urlencode(GETPOST('login_hint'));
-		}
-	}
-
-
-	//var_dump($url);exit;
-
-	// we go on oauth provider authorization page
-	header('Location: '.$url);
-	exit();
 }
 
 
@@ -320,6 +347,6 @@ if (GETPOST('code')) {     // We are coming from oauth provider page.
  * View
  */
 
-// No view at all, just actions, so we never reach this line.
+// No view at all, just actions, so we reach this line only on error.
 
 $db->close();

+ 6 - 3
htdocs/core/tpl/login.tpl.php

@@ -351,7 +351,7 @@ if (isset($conf->file->main_authentication) && preg_match('/google/', $conf->fil
 	echo '<br>';
 	echo '<div class="center" style="margin-top: 4px; margin-bottom: 10px">';
 
-	global $dolibarr_main_url_root;
+	/*global $dolibarr_main_url_root;
 
 	// Define $urlwithroot
 	$urlwithouturlroot = preg_replace('/'.preg_quote(DOL_URL_ROOT, '/').'$/i', '', trim($dolibarr_main_url_root));
@@ -365,9 +365,12 @@ if (isset($conf->file->main_authentication) && preg_match('/google/', $conf->fil
 	$_SESSION['oauthstateanticsrf'] = $shortscope.'-'.$oauthstateanticsrf;
 	$urltorenew = $urlwithroot.'/core/modules/oauth/google_oauthcallback.php?shortscope='.$shortscope.'&state=forlogin-'.$shortscope.'-'.$oauthstateanticsrf;
 
-	$url = $urltorenew;
+	//$url = $urltorenew;
+	 */
 
-	print img_picto('', 'google', 'class="pictofixedwidth"').'<a class="alogin" href="'.$url.'">'.$langs->trans("LoginWith", "Google").'</a>';
+	echo '<input type="hidden" name="beforeoauthloginredirect" id="beforeoauthloginredirect" value="">';
+	print img_picto('', 'google', 'class="pictofixedwidth"');
+	print '<a class="alogin" href="#" onclick="jQuery(\'#beforeoauthloginredirect\').val(1); $(this).closest(\'form\').submit();">'.$langs->trans("LoginWith", "Google").'</a>';
 
 	echo '</div>';
 }

+ 1 - 0
htdocs/langs/en_US/errors.lang

@@ -313,6 +313,7 @@ ErrorCoherenceMenu=<b>%s</b> is required when <b>%s</b> is 'left'
 ErrorUploadFileDragDrop=There was an error while the file(s) upload
 ErrorUploadFileDragDropPermissionDenied=There was an error while the file(s) upload : Permission denied 
 ErrorFixThisHere=<a href="%s">Fix this here</a>
+ErrorTheUrlOfYourDolInstanceDoesNotMatchURLIntoOAuthSetup=Error: The URL of you current instance (%s) does not match the URL defined into your OAuth2 login setup (%s). Doing OAuth2 login in such a configuration is not allowed.
 
 # Warnings
 WarningParamUploadMaxFileSizeHigherThanPostMaxSize=Your PHP parameter upload_max_filesize (%s) is higher than PHP parameter post_max_size (%s). This is not a consistent setup.

+ 12 - 8
htdocs/main.inc.php

@@ -781,21 +781,24 @@ if (!defined('NOLOGIN')) {
 		$passwordtotest = GETPOST('password', 'none', $allowedmethodtopostusername);
 		$entitytotest = (GETPOST('entity', 'int') ? GETPOST('entity', 'int') : (!empty($conf->entity) ? $conf->entity : 1));
 
-		// Define if we received data to test the login.
+		// Define if we received the correct data to go into the test of the login with the checkLoginPassEntity().
 		$goontestloop = false;
-		if (isset($_SERVER["REMOTE_USER"]) && in_array('http', $authmode)) {
+		if (isset($_SERVER["REMOTE_USER"]) && in_array('http', $authmode)) {	// For http basic login test
 			$goontestloop = true;
 		}
-		if ($dolibarr_main_authentication == 'forceuser' && !empty($dolibarr_auto_user)) {
+		if ($dolibarr_main_authentication == 'forceuser' && !empty($dolibarr_auto_user)) {	// For automatic login with a forced user
 			$goontestloop = true;
 		}
-		if (GETPOST("username", "alpha", $allowedmethodtopostusername)) {
+		if (GETPOST("username", "alpha", $allowedmethodtopostusername)) {	// For posting the login form
 			$goontestloop = true;
 		}
-		if (!empty($_COOKIE['login_dolibarr'])) {	// TODO Remove this ?
+		if (GETPOST('openid_mode', 'alpha', 1)) {	// For openid_connect ?
 			$goontestloop = true;
 		}
-		if (GETPOST('openid_mode', 'alpha', 1) || GETPOST('googleoauth_mode', 'alpha', 1)) {
+		if (GETPOST('beforeoauthloginredirect', 'int') || GETPOST('afteroauthloginreturn')) {	// For oauth login
+			$goontestloop = true;
+		}
+		if (!empty($_COOKIE['login_dolibarr'])) {	// TODO For ? Remove this ?
 			$goontestloop = true;
 		}
 
@@ -2299,6 +2302,7 @@ function top_menu_user($hideloginname = 0, $urllogout = '')
 	$dropdownBody .= '<span id="topmenulogincompanyinfo-btn"><i class="fa fa-caret-right"></i> '.$langs->trans("ShowCompanyInfos").'</span>';
 	$dropdownBody .= '<div id="topmenulogincompanyinfo" >';
 
+	$dropdownBody .= '<br><b>'.$langs->trans("Company").'</b>: <span>'.dol_escape_htmltag($mysoc->name).'</span>';
 	if ($langs->transcountry("ProfId1", $mysoc->country_code) != '-') {
 		$dropdownBody .= '<br><b>'.$langs->transcountry("ProfId1", $mysoc->country_code).'</b>: <span>'.dol_print_profids(getDolGlobalString("MAIN_INFO_SIREN"), 1).'</span>';
 	}
@@ -2454,7 +2458,7 @@ function top_menu_user($hideloginname = 0, $urllogout = '')
 	                </p>
 	            </div>
 
-	            <!-- Menu Body -->
+	            <!-- Menu Body user-->
 	            <div class="user-body">'.$dropdownBody.'</div>
 
 	            <!-- Menu Footer-->
@@ -2920,7 +2924,7 @@ function top_menu_search()
     ';
 
 	$dropDownHtml .= '
-        <!-- Menu Body -->
+        <!-- Menu Body search -->
         <div class="dropdown-body search-dropdown-body">
         '.$buttonList.'
         </div>