/**
     * Logs the user in eZPublish taking the data from the ESB
     * /!\ Does not check login / password. This check needs to be done before!!!!!
     *
     * @param string $uuid
     * @param ESBResult $esbResult
     * @param boolean $rememberMe
     * @param boolean $context
     * @return array destUrl or null if error
     */
    public static function esbLogin( $uuid, $esbResult, $rememberMe = false, $context = false )
    {
        $localizedLoginApplication = CacheApplicationTool::buildLocalizedApplicationByIdentifier( 'login' );

        $validationStatus = $esbResult->getValidationStatus();
        if ( $validationStatus == 'PV' && $localizedLoginApplication->getCustomParameter( 'RestrictPendingUsers' ) == 1 )
        {
            UserLog::instance()->esb_status('Pending')->store();
            
            $redirectURL = eZINI::instance( 'site.ini' )->variable( 'SiteSettings', 'PendingUserStaticPage' );
            if( SolrSafeOperatorHelper::featureIsActive( 'GoogleAnalytics' ) )
            {
                $redirectURL = $redirectURL . '#?vs=PV';
            }
            header( "Location: $redirectURL" );
            eZExecution::cleanExit();
        }
        else if ( $validationStatus == 'RP' && $localizedLoginApplication->getCustomParameter( 'RestrictRejectedUsers' ) == 1 )
        {
            UserLog::instance()->esb_status('Rejected')->store();
            
            $redirectURL = eZINI::instance( 'site.ini' )->variable( 'SiteSettings', 'RejectedUserStaticPage' );
            if( SolrSafeOperatorHelper::featureIsActive( 'GoogleAnalytics' ) )
            {
                $redirectURL = $redirectURL . '#?vs=RP';
            }
            header( "Location: $redirectURL" );
            eZExecution::cleanExit();
        }

        if( is_null($esbResult->countryOfRegistration))
            $esbResult->countryOfRegistration = eZINI::instance()->variable( 'RegionalSettings', 'CountryOfRegistration' );

        if( is_null($esbResult->userSpecialty) )
        {
            self::logError( $uuid, null, $esbResult->toTicket(), 'Missing main specialty' );
            return null;
        }

        if( is_null( $esbResult->customerType ) )
        {
            self::logError( $uuid, null, $esbResult->toTicket(), 'Missing Customer type' );
            return null;
        }

        // temporary fix to parse forced string prepended with A
        $userSpeciality = $esbResult->userSpecialty = preg_replace( '#^A#', '', $esbResult->userSpecialty );
        $customerType = $esbResult->customerType = preg_replace( '#^A#', '', $esbResult->customerType );

        if( !preg_match('#^216\.#', $userSpeciality) )
        {
            self::logError( $uuid, null, $esbResult->toTicket(), "Invalid User specialty: $userSpeciality" );
            return null;
        }
        if( !preg_match( '#^102\.#', $customerType ) )
        {
            self::logError( $uuid, null, $esbResult->toTicket(), "Invalid Customer type: $customerType" );
            return null;
        }

        $esbResult->userName = $uuid;
        $esbResult->rememberMe = $rememberMe;
        $decodedContext = urldecode(urldecode($context));

        // If we need to check the Terms of Use for the cluster, we need to skip my-newsletters app for legal reasons (1-click unsubscribe).
        $toUToCheck = (    eZINI::instance( 'merck.ini')->hasVariable( 'LoginSettings', 'ToUCheck')
            && eZINI::instance( 'merck.ini' )->variable( 'LoginSettings', 'ToUCheck') == 'enabled'
            && !strpos($decodedContext, 'my-newsletters')
        );

        if( $toUToCheck ){
            $toUValidated = ( $esbResult->termsOfUse );
            $toUValidated &= ( $esbResult->privacyPolicy );

            if( $esbResult->forceToUValidated )
                $toUValidated = true;

            $esbResult->toUValidated = (bool)$toUValidated;
        }

        // Check if we need to check the autologin status for the cluster
        if( SolrSafeOperatorHelper::featureIsActive('RestrictAutologgedInUsers') && SolrSafeOperatorHelper::feature('RestrictAutologgedInUsers', 'Restricted')
            && in_array( $esbResult->autologin, array( 1, "yes" ) ))
        {
            $esbResult->autologin = true;
        }
        else
        {
            $esbResult->autologin = false;
        }

        if ( self::loginUser( $esbResult->toTicket() ) )
        {
            $user = MMUsers::getCurrentUserObject();

            $destUrl = ContextTool::instance()->contextUrl( $context );

            if( $toUToCheck && !$user->toUValidated() )
            {
                if( preg_match('#^(?:https?://[^/]+)'.eZINI::instance()->variable('SiteSettings', 'ToUAgreementPage').'?#', $destUrl) )
                    $destUrl = '/';
                $destUrl = preg_replace('#^https?://([^?]+)//#', '\1', $destUrl);
                $destUrl = eZINI::instance()->variable('SiteSettings', 'ToUAgreementPage')
                    .'?context='.urlencode($destUrl);
            }

            // Store user action in mm_front_user_action table
            $mmFrontUserAction = MMFrontUserAction::fetchByUsername( $esbResult->userName );
            if ( $mmFrontUserAction instanceof MMFrontUserAction )
            {
                $mmFrontUserAction->LastVisitDate = date( 'Y-m-d H:i:s' );
                $mmFrontUserAction->Processed = MMFrontUserAction::PROCESSED;
                $mmFrontUserAction->store(array('processed', 'last_visit_date'));
            }
            else
            {
                $mmFrontUserAction = MMFrontUserAction::create( array(
                        'id' => null,
                        'username' => $esbResult->userName,
                        'country_registration' => $esbResult->countryOfRegistration,
                        'processed' => MMFrontUserAction::PROCESSED,
                        'last_visit_date' => date( 'Y-m-d H:i:s' ),
                ) );
                $mmFrontUserAction->store();
            }

            if ( $rememberMe )
            {
                $userKey = !is_null($esbResult->userId) ? $esbResult->userId : $uuid;
                $cookieExpiration = time() + eZINI::instance( 'merck.ini' )->variable( 'TIBCOCookieSettings', 'TIBCOCookieExpiration' );
               
                //fix to remove the old cookie for new sso cluster #39800
                $splitDepth = eZINI::instance('merck.ini')->variable( 'CookieSettings', 'CookieDomainSplitDepth' );
                $splitDepth= 0;
                if( $splitDepth == 0 ) {
                    $cookieDomain = preg_replace('#^(https?://)?([^.]+.){1}#', '', contextTool::instance()->domain() );
                    $cookieExpirationToDelete = time() - 2000;
                    setcookie( 'remember_me', '', self::encryptText(json_encode($userKey)), $cookieExpirationToDelete, '/', $cookieDomain );
                }//end fix
                setcookie( 'remember_me', self::encryptText(json_encode($userKey)), $cookieExpiration, '/', CookieTool::getCookieDomain() );
            }
            else
            {
                $cookieExpiration = 0;
            }

            // Set cookie
            $esbSessionId = $esbResult->sessionID;
            $countryCode = '';
            if ( !empty( $esbSessionId ) )
            {
                $cookieName   = eZINI::instance( 'merck.ini' )->variable( 'TIBCOCookieSettings', 'TIBCOCookieName' );
                $esbSessionId = str_replace( ' ', '+', '"'.urldecode($esbSessionId).'"' );
                setrawcookie( $cookieName, $esbSessionId, $cookieExpiration, '/', CookieTool::getCookieDomain() );
            }
            
            // set residenceCountry country code for google tag manager
            $countryOfResidence = $esbResult->othersParams['countryOfResidence'] ? $esbResult->othersParams['countryOfResidence'] : ($esbResult->othersParams['Country_of_residence'] ? $esbResult->othersParams['Country_of_residence'] : null );
            if($countryOfResidence)
            {
                if($countryOfResidence > 2)
                {
                    $countries = SolrSafeOperatorHelper::clusterIni('CountryCode','CountryCode','merck.ini');
                    $countryCode = $countries[$esbResult->othersParams['Country_of_residence']];
                }
            }
            else
            {
                $countryCode = $esbResult->countryOfRegistration;
            }
            
            $esbResult -> setResidenceCountry($countryCode);
              
            return array(
                'destUrl' => $destUrl,
                'params'  => $esbResult->toTicket(),
            );
        }

        return null;
    }
    public function relog()
    {
        $uuid       = isset( $this->_input['uuid'] ) ? $this->_input['uuid'] : null;
        //$h          = isset( $_COOKIE['h'] ) ? $_COOKIE['h'] : null;
        $h          = isset( $this->_input['h'] ) ? $this->_input['h'] : null;
        $context    = isset( $this->_input['context'] ) ? $this->_input['context'] : ContextTool::instance()->domain().'/';

        //delete session id cookie
        //unset($_COOKIE['h']);

        if ( is_null( $uuid ) || is_null( $h ) )
        {
            MMUserLogin::logError( $uuid, null, null, 'Empty uuid or hash given on Relog' );
            return $this->relogError();
        }

        if ( $h != sha1( eZINI::instance( 'merck.ini' )->variable( 'TicketLogin', 'DESKey' ) . $uuid ) )
        {
            MMUserLogin::logError( $uuid, null, null, 'Invalid hash given on Relog' );
            return $this->relogError();
        }

        UserLog::instance()->action( 'rememberme' )->uuid( $uuid )->step( 'received' )->store();

        $esbResult = new ESBResult();
        
        if ( !SolrSafeOperatorHelper::featureIsActive('UUMP') )
        {
            $datas = static::readCall( $uuid, $esbResult );
        }
        else
        {
            $readService = ESBFactory::getUserService();
            $parameters  = $readService->getFormParameters($uuid);
            $datas       = $readService->read( $parameters, $uuid );
        }

        $isPopulated = static::populateESBResult( $esbResult, $datas );
        $this->_esbResult = $esbResult;
        
        if ( !$isPopulated )
        {
            // error log caught on WS stack
            return $this->relogError();
        }
        
        $esbResult->login = ( $esbResult->userId === $uuid );
        

        if ( !$isPopulated )
        {
            // error log caught on WS stack
            return $this->relogError();
        }

        $loginResult = MMUserLogin::esbLogin( $uuid, $esbResult, true, $context );

        if ( $loginResult )
        {
            $this->_isLoginSuccessful = true;
            $this->_destUrl = $loginResult['destUrl'];

            UserLog::instance()
                ->uuid( $uuid )
                ->esb_status( 'Accepted' )
                ->store();

            $user = MMUsers::getCurrentUserObject();

            $sl = SystemLocale::fetchByClusterAndSystem( ClusterTool::clusterIdentifier(), 'esb_language' );
            $customerLanguage = !is_null( $sl ) ? $sl : eZINI::instance()->variable( 'RegionalSettings', 'ContentObjectLocale' );

            if( SolrSafeOperatorHelper::featureIsActive( 'AsynchronousAnalyticsLoginCall' ) && SolrSafeOperatorHelper::feature( 'AsynchronousAnalyticsLoginCall', 'GoogleAnalytics' ) )
            {
                $amq = new ActiveMQManager();
                $domains = eZINI::instance( 'merck.ini' )->variable( 'DomainMappingSettings', 'ClusterDomains' );
                $domain  = isset( $domains[ClusterTool::clusterIdentifier()] ) ? $domains[ClusterTool::clusterIdentifier()] : 'unidentified.univadis.com';
                $gasl = SystemLocale::fetchByClusterAndSystem( ClusterTool::clusterIdentifier(), 'ga_visitor_country' );
                $gaCountry = !is_null( $gasl ) ? $gasl : $user->attribute( 'country' );
                $gaParams = array(
                    'v'   => 1,
                    'tid' => 'UA-41415675-6',
                    'uid' => $uuid,
                    't'   => 'event',
                    'ec'  => 'esb',
                    'ea'  => 'login',
                    'ni'  => 1,
                    'cd1' => $uuid,
                    'cd2' => 'logged',
                    'cd7' => $gaCountry,
                    'dh'  => preg_replace( '#^.*?\.#', '', $domain ),
                );
                $gaParams = 'https://ssl.google-analytics.com/collect?' . http_build_query( $gaParams );
                $amq->sendMessageToQueue( 'portail.analytics.google', $gaParams );
            }

            // Stringify params
            $loginResult['params'][AppBarControl::COOKIE_UNORDERED_APPLIST_KEY] = $user->getApplicationList();
            $loginResult['params'][MMUsers::COOKIE_KEY] = $user->getMMSettings();
            $strParams = json_encode( $loginResult['params'] );

            // Encrypts params
            $encryptedParams = MMUserLogin::encryptText( $strParams );
            // Redirect to PHP-ESI
            $redirectURL = "/loginActions.php?context=" . urlencode( $loginResult['destUrl'] ) . "&params=" . urlencode( $encryptedParams );
            if ( !MMUsers::checkCookieLaw() && SolrSafeOperatorHelper::feature('CookieLaw', 'Mode') == MMUsers::COOKIE_LAW_ACTIVE_VERSION_KEY)
            {
                $cookieLawPage = SolrSafeOperatorHelper::feature( 'CookieLaw', 'CookieLawPage' );
                $redirectURL   = ( $cookieLawPage ? $cookieLawPage : '/page/cookie-law' );
            }

            // Branding reconsent check, done only if:
            // 1. feature ToUPPPopin enabled
            // 2. Always on WEB with this feature
            // 3. Only on mobile, whne setting showOnMobile is ON.
            if
            (
                SolrSafeOperatorHelper::featureIsActive( 'ToUPPPopin')
                &&
                (
                    !ContextTool::instance()->isMobile()
                    ||
                    ( ContextTool::instance()->isMobile() && SolrSafeOperatorHelper::feature('ToUPPPopin','showOnMobile') )
                )
            )
            {
                $displayReconsent = $this->checkTouPPPopin( $datas );
                // if we need to ask user for reconsent ($displayReconsent - taken fromESB response) we decide if we want page below if:
                // 1. On WEB and useDedicatedPage setting is ON
                // 2. On mobile and useDedicatedPageMobile setting is ON
                if (
                    $displayReconsent
                    &&
                    (
                        ( !ContextTool::instance()->isMobile() && SolrSafeOperatorHelper::feature( 'ToUPPPopin', 'useDedicatedPage' ) )
                        ||
                        ( ContextTool::instance()->isMobile() && SolrSafeOperatorHelper::feature( 'ToUPPPopin', 'useDedicatedPageMobile' ) )
                    )
                )
                {
                    CookieTool::destroyCookie( 'displayToUPPPopin' );
                    CookieTool::destroyCookie( 'displayToUPPPopin', '/', null );
                    CookieTool::setCookie( 'displayToUPPPage', 1, time() + ( 2 * 24 * 60 * 60 ) );
                    $touPpPageUrl = eZINI::instance( 'site.ini' )->variable( 'SiteSettings', 'ToUPPPageUrl' ) . "/#?tpc=" . urlencode( $loginResult['destUrl'] );
                    $redirectURL = "/loginActions.php?context=" . urlencode( $touPpPageUrl ) . "&params=" . urlencode( $encryptedParams );
                }
            }

            $this->response( $redirectURL );
        }
    }