Yii-user and Facebook Login--code debug

Hi everyone,

I am using Yii-user and Facebook login part from the (yii-user-management)

Now i have finished writing the code, however, each time I click Facebook login button. After I logged in to Facebook,

I still need to login with my site.(and nothing happens to my database) That means, I guess…something went wrong with my user identity …

Here are my codes…any hints?

LoginController:


<?php


class LoginController extends Controller

{

	public $defaultAction = 'login';


public function actionFacebook() {


		Yii::app()->user->logout();

		Yii::import('application.modules.user.vendors.facebook.*');

$facebook = new Facebook(Yii::app()->params['facebookApi'], Yii::app()->params['facebookSecretCode']);

        $fb_uid = $facebook->getUser();

        if($fb_uid){

            $user = User::model()->findByAttributes(array('facebook_id' => $fb_uid));

            

            if($user === NULL){

                

                // Save new facebook user to database

                $user = new User;

                $user->facebook_id = $fb_uid;

                $user->status = User::STATUS_ACTIVE;

                $user->createtime = time();

                $user->lastvisit = time();

                $user->superuser = 0;


                if($user->save(false)){

                    $profile = new Profile;

                    $profile->user_id=$user->id;

                    $profile->save(false);

                }

                

            }


            $identity=new UserIdentity($fb_uid, $user->id);

            $identity->authenticate(true);


            switch($identity->errorCode)

            {

                case UserIdentity::ERROR_NONE:

                    $duration= 3600*24*30; // 30 days

                    Yii::app()->user->login($identity,$duration);

                    $this->redirect(Yii::app()->controller->module->returnUrl);

                    

                    break;

                case UserIdentity::ERROR_STATUS_NOTACTIV:

                    $user->addError("status",UserModule::t("You account is not activated."));

                    break;

                case UserIdentity::ERROR_STATUS_BAN:

                    $user->addError("status",UserModule::t("You account is blocked."));

                    break;

                case UserIdentity::ERROR_PASSWORD_INVALID:

                    $user->addError("password",UserModule::t("Password is incorrect."));

                    break;

            }


            $this->render('facebook', array('user' => $user));


        } 

        else

        {

            $this->redirect(Yii::app()->controller->module->returnLogoutUrl);

        }


        


        

    }

	/**

	 * Displays the login page

	 */


public function actionLogin()

{

        if (Yii::app()->user->isGuest) {

                $model=new UserLogin;


                // if called without specific returnUrl, set it to the previous page

                if (!isset($_POST['UserLogin']) && Yii::app()->user->returnUrl === Yii::app()->request->scriptUrl)

                {

                        if (isset($_SERVER['HTTP_REFERER']))

                        {

                                Yii::app()->user->setReturnUrl($_SERVER['HTTP_REFERER']);

                        }

                }


                // collect user input data

                if(isset($_POST['UserLogin']))

                {

                        $model->attributes=$_POST['UserLogin'];

                        // validate user input and redirect to previous page if valid

                        if($model->validate()) {

                                $this->lastViset();

                                $returnUrl = Yii::app()->user->returnUrl;

                                /*

                                if (strpos($returnUrl,'/index.php')!==false)

                                        $returnUrl = Yii::app()->controller->module->returnUrl;

                                */

                                Yii::app()->user->setReturnUrl('');

                                $this->redirect($returnUrl);

                        }

                }

                // display the login form

                $this->render('/user/login',array('model'=>$model));

        } else

                $this->redirect(Yii::app()->controller->module->returnUrl);

}

	

	private function lastViset() {

		$lastVisit = User::model()->notsafe()->findByPk(Yii::app()->user->id);

		$lastVisit->lastvisit = time();

		$lastVisit->save();

	}


}

UserIdentity:


class UserIdentity extends CUserIdentity

{


	private $_id;

        public  $facebook_id;

    

        const ERROR_EMAIL_INVALID=3;

        const ERROR_STATUS_NOTACTIV=4;

        const ERROR_STATUS_BAN=5;

        /**

         * Authenticates a user.

         * The example implementation makes sure if the username and password

         * are both 'demo'.

         * In practical applications, this should be changed to authenticate

         * against some persistent user identity storage (e.g. database).

         * @return boolean whether authentication succeeds.

         */

        public function authenticate($facebook = false)

        {

        // Validate facebook user

        if($facebook){

           Yii::import('application.modules.user.vendors.facebook.*');

		require_once('Facebook.php');

            $facebook = new Facebook(Yii::app()->params['facebookApi'], Yii::app()->params['facebookSecretCode']);

            $fb_uid = $facebook->getUser();

            $user=User::model()->findByAttributes(array('facebook_id'=> $fb_uid));


            if($user===null){

                $this->errorCode=self::ERROR_USERNAME_INVALID;

            }

            else if($user->status==0&&Yii::app()->controller->module->loginNotActiv==false)

                $this->errorCode=self::ERROR_STATUS_NOTACTIV;

            else if($user->status==-1)

                $this->errorCode=self::ERROR_STATUS_BAN;

            else {

                $this->_id= $user->id;

                $this->username = 'facebook';

                $this->facebook_id = $fb_uid;

                $this->errorCode=self::ERROR_NONE;

            }

        }

        else

        {

            if (strpos($this->username,"@")) {

			$user=User::model()->notsafe()->findByAttributes(array('email'=>$this->username));

		} else {

			$user=User::model()->notsafe()->findByAttributes(array('username'=>$this->username));

		}


            if($user===null)

                if (strpos($this->username,"@")) {

                    $this->errorCode=self::ERROR_EMAIL_INVALID;

                } else {

                    $this->errorCode=self::ERROR_USERNAME_INVALID;

                }

            else if(Yii::app()->getModule('user')->encrypting($this->password)!==$user->password)

			$this->errorCode=self::ERROR_PASSWORD_INVALID;

		else if($user->status==0&&Yii::app()->getModule('user')->loginNotActiv==false)

			$this->errorCode=self::ERROR_STATUS_NOTACTIV;

		else if($user->status==-1)

			$this->errorCode=self::ERROR_STATUS_BAN;

		else {

			$this->_id=$user->id;

			$this->username=$user->username;

			$this->errorCode=self::ERROR_NONE;

		}

		return !$this->errorCode;

        }

}

    

    /**

    * @return integer the ID of the user record

    */

        public function getId()

        {

                return $this->_id;

        }

}



Login form:-----only Facebook login part


<?php if (!Yii::app()->user->isGuest): ?>

<a href="<?php echo $this->createUrl('/user/auth/logout'); ?>" class="exit"><div></div>

   <span>Logout</span>

</a>

<?php else: ?>

<fb:login-button perms="email,user_birthday,read_stream,publish_stream">

<span>Login to Facebook</span>

</fb:login-button>

<?php endif; ?>



Main config:


'params'=>array(

		// this is used in contact page

		'adminEmail'=>'no-reply@xxxxxxxxx.com',

                  'facebookApi' => 'xxxxxxxx',

                  'facebookSecretCode' => 'xxxxxxxxxxx',

	),

Main layout: head and part codes:


<?php


Yii::import('application.modules.user.vendors.facebook.*');

$facebook = new Facebook(Yii::app()->params['facebookApi'], Yii::app()->params['facebookSecretCode']);

    $fb_session = $facebook->getSession();

?>

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">

<html xmlns="http://www.w3.org/1999/xhtml" xmlns:fb="http://www.facebook.com/2008/fbml">

<head>

....

...

</head>


<body>

<script>

window.fbAsyncInit = function() {

    FB.init({

        appId   : '<?php echo xxxxxxxxxxxx; ?>',

    });


    // whenever the user logs in, we refresh the page

    FB.Event.subscribe('auth.login', function() {

        window.location.reload();

    });

};


(function() {

    var e = document.createElement('script');

    e.src = document.location.protocol + '//connect.facebook.net/en_us/all.js';

    e.async = true;

    document.getElementById('fb-root').appendChild(e);

}());

</script>

...

...

</body>



This gives me auth type error…

Any ideas???

this is the attachment

Facebook.php

Ive been trying with this for a couple of days, I dont fully understand yii authentication methods etc but hey, I learned more now:

I do like this:




$userid = Yii::app()->facebook->getUser();

		if ( !$userid == "") //if the user is logged in vya facebook

			{

				$user = User::model()->find('facebook='.$userid); 

				if( $user ==="" ) //if there is not an user account associated with the fb id we create new one

					{

						$user = new User;

						$user->facebook = $userid;	

						$password = rand(1,9);

						$user->password = $password;

						// Save to get an id

						//Set id as username temporarely

						if ( $user->save() )

							{ $user->username = $user->id;}

						//save again

						if ( $user->save ){

						$dir = User::USER_DIR . $user->id; //specifies a path for the users unique file dir

						mkdir($dir,0777,true);  // creates the dir

						$this->autoLogin($user);//logs in the user


						}

					}

				else{ //there is already a user account with the fb id, so log him in.

				$this->autoLogin($user); 

				}

			}





public function autoLogin($user)

	{

	$identity=new UserIdentity($user->username, "");

	$identity->facebook();

	

	if ( $identity->errorCode == UserIdentity::ERROR_NONE )

		{

			$duration= 3600*24*30; // 30 days

			Yii::app()->user->login($identity,$duration);

			$this->redirect("/profile/u/".$user->username);

		}

		else

		{

		 //echo $identity->errorCode;

		}

	

	}



Notice I user $identity->facebook() because I have to authenticate the user not knowing the password,

its a modified version of $identity->authenticate()

here it is:




	public function facebook()

	{

		$user=User::model()->find("username = '" . $this->username . "'");

		if ( $user === null ) 

			$this->errorCode = self::ERROR_USERNAME_INVALID;

		else

		{

			$this->_id = $user->id;

			$this->username = $user->username;

			$this->errorCode = self::ERROR_NONE;

		}

		return $this->errorCode == self::ERROR_NONE;

	}



Thanks for your help…

but I’m sorry i don’t really understand it…

Would you please be more specific?

Have you solved the Facebook login ?

Hi, I’m also trying to integrate Yii-User with Facebook Login. Has anybody successfully integrate both using this method? Thanks for your help.