After digging quite a bit in the AuthComponent source, I think I've
found the problem. There are still some things I don't understand, so
please feel free to correct me where I might be wrong. For example,
identify() gets called twice in a login, but I can't figure where does
the second call come from and why the passed data is different in each
call: first the POST data, then username/password fields as part of a
User array. This second call is the one logging the user even if no
username/password information was given on the login form, see code
bellow. On a side note for my previous code, it is not necessary to
call $this->Auth->login() passing it $this->data. It will use $_POST
data if nothing is specified.

The identify() function of AuthComponent (auth.php 5437 2007-07-10
16:25:23Z gwoo) will use an empty array as a condition for a model-
>find() call if any of the login fields are empty, thus finding the
first result in the database: in my case, user with id=1: the
administrator. The problematic code commented:

/* Initialize the array we are going to use as a find condition as
empty */
$find = array();
/* If *both* username and password are provided as a user object */
if (isset($user[$this->fields['username']]) && !empty($user[$this-
>fields['username']])  && !empty($user[$this->fields['password']])) {

        if (trim($user[$this->fields['username']]) == '=' || trim($user[$this-
>fields['password']]) == '=') {
                return false;
        }
                /* Set find conditions */
        $find = array(
                $this->fields['username'] => $user[$this->fields['username']],
                $this->fields['password'] => $user[$this->fields['password']]
        );
/* Else, if username is provided in POST */
} elseif (isset($user[$this->userModel . '.' . $this-
>fields['username']]) && !empty($user[$this->userModel . '.' . $this-
>fields['username']])) {
                /* If both are empty (why '='?) this should return a
login failure, but the misterious (for me!) second call will ruin the
login failure */
        if (trim($user[$this->userModel . '.' . $this->fields['username']])
== '=' || trim($user[$this->userModel . '.' . $this-
>fields['password']]) == '=') {
                return false;
        }
                /* Set find conditions */
        $find = array(
                $this->fields['username'] => $user[$this->userModel . '.' . 
$this-
>fields['username']],
                $this->fields['password'] => $user[$this->userModel . '.' . 
$this-
>fields['password']]
        );
}
/* At this point, if we were working with the user array and *any* but
not both of the fields were empty, find = array( ) */
$model =& $this->getModel();
/*
    $model->find(am(array(), $this->userScope), null, null, -1) will
seek:
    If $this->userScope == array() the first user record,
unconditionally.
    Else, the first user record that matches filtering conditions, but
ommiting the identifying information: username/password
*/
$data = $model->find(am($find, $this->userScope), null, null, -1);

/*
    If there are any users on the DB, $data won't be empty, thus login
is authorized
    and user is acknowledged to be the first matching the prior
conditions. In my case, user with id=1: administrator.
*/
if (empty($data) || empty($data[$this->userModel])) {
        return null;
}

Now the questions are:

    Q1. What is this second call to identify and where does it come
from?
    Q2. Is this a bug and should be reported to trac or am I doing
something deadly wrong?

On 27 jul, 12:10, Gorka <[EMAIL PROTECTED]> wrote:
> I thought AuthComponent handled user login and logout on its own,
> validating username/password pairs and thus I saw no reason to use a
> validLogin function on the model as you did.
>
> But: AuthComponent won't log me in with an invalid password for a
> given username, but what is freaking me out is that it logs me in with
> any username/password combination (even both blanks) that are not in
> the database... incidentally, it logs me in with a user id of '1',
> which means I turn into admin without even specifying a name or
> password.
>
> So, I'm damn sure I'm missing some very crucial information on how
> AuthComponent is supposed to be used. Could anyone tell what am I
> doing wrong?
>
> My users controller:
>
> <?php
>
>     class UsuariosController extends AppController {
>
>         var $name = 'Usuarios';
>
>         function login() {
>
>             $user_id = $this->Auth->user('id');
>             if (!empty($user_id) && $this->Session->valid()) {
>                 $this->Session->setFlash(__('Already logged in',
> true), 'message', array('class' => 'error'));
>                 $this->redirect('/');
>                 exit();
>             }
>
>             if (!empty($this->data)) {
>                 if (!$this->Auth->login($this->data)) {
>                     $this->Session->setFlash(__('Login failed', true),
> 'message', array('class' => 'error'));
>                 } else {
>                      $this->flashRedirect(__('Welcome', true), '/');
>                 }
>             }
>         }
>
>         function logout() {
>             $this->Auth->logout();
>             $this->flashRedirect(__('Logged out', true), '/');
>         }
>
>     }
>
> And App Controller:
>
> <?php
>
> class AppController extends Controller {
>
>     var $components = array('Session', 'Acl', 'Auth');
>     var $helpers = array('html', 'javascript', 'form', 'head');
>
>     function beforeFilter() {
>         if (isset($this->Auth)) {
>             $this->Auth->fields = array('username' => 'email',
> 'password' => 'password');
>             $this->Auth->userModel = 'Usuario';
>             $this->Auth->loginAction = array('controller'=>'usuarios',
> 'action'=>'login');
>             $this->Auth->loginRedirect =
> array('controller'=>'usuarios', 'action'=>'index');
>         }
>         parent::beforeFilter();
>     }
>
>     function flashRedirect($message, $url = array(), $class = 'info')
> {
>         $this->Session->setFlash($message, 'message', array('class' =>
> $class));
>         $this->redirect($url);
>         exit();
>     }
>
> }
>
> The user login view:
>
> <?=$form->create('Usuario', array('action'=>'login'))?>
>     <?=$form->input('Usuario.email')?>
>     <?=$form->input('Usuario.password', array('type'=>'password',
> 'value'=>''))?>
>     <?=$form->submit('Entrar')?>
> <?=$form->end()?>
>
> On 21 jun, 10:24, danfreak <[EMAIL PROTECTED]> wrote:
>
>
>
> > Dunno why but I can't post in the original thread.
>
> > original thread=> " new auth component in cake 1.2   
> > "http://groups.google.com/group/cake-php/browse_frm/thread/f2d0143c2e5...
>
> > My 2 cents about the new Auth component (Cake 1.2.0.5146alpha)
>
> > It stores encrypted passwords in the DB when you add/edit a new user.
>
> > Let's start with the users controller:
>
> > -------------------------------------------------------------------------------------------------------
> > users_controller.php
> > -------------------------------------------------------------------------------------------------------
> > <?php
> > class UsersController extends AppController {
>
> >         var $name = 'Users';
> >         var $helpers = array('Html', 'Form', 'Session');
> >         var $components = array('Auth', 'Session');
>
> >         function beforeFilter()
> >     {
> >         //actions we allow without authentication, you can also put
> > them in the app_controller.php
> >        $this->Auth->allow('index', 'register', 'login', 'logout');
> >     }
>
> >     function login()
> >     {
> >         //user already logged in?
> >         //checking if session has been written
> >         $user_id = $this->Auth->user('id');
> >         if (!empty($user_id) && $this->Session->valid())
> >         {
> >             $this->Session->setFlash('You are already logged in');
> >             $this->redirect(array('action'=>''), null, true);
> >         }
> >         else
> >         {
> >             if(!empty($this->data))
> >             {
> >                 //calling login validation validLogin() in model
> >                 if($this->User->validLogin($this->data))
> >                 {
> >                     if($this->Auth->login($this->User->user))
> >                     {
> >                         $this->Session->setFlash('You have
> > successfully logged in');
> >                         $this->redirect(array('action'=>''), null,
> > true);
> >                     }
> >                     else
> >                     {
> >                         $this->set('password', null);
> >                         $this->set('auth_msg', 'Please try again');
> >                     }
>
> >                 }
> >             }
> >             else
> >             {
> >                 $this->set('auth_msg', 'Please enter your username and
> > password');
> >             }
> >         }
>
> >     }
>
> >     function logout()
> >     {
> >         $this->Session->destroy('user');
> >         $this->Session->setFlash('You\'ve successfully logged out.');
> >         $this->redirect(array('action'=>'login'), null, true);
> >     }
>
> > -------------------------------------------------------------------------------------------------------
> > MODEL-> user.php
> > the model has just a particular function (see below) that you must add
> > -------------------------------------------------------------------------------------------------------
> > function validLogin($data)
> >     {
>
> >         $user = $this->find(array('username' => $data['User']
> > ['username'], 'password' => ($data['User']['password'])), array('id',
> > 'username', 'password'));
> >         if(!empty($user)){
> >             $this->user = $user['User'];
> >             return TRUE;
> >         }
> >         else {
> >             return FALSE;
> >         }
>
> >     }
>
> > -------------------------------------------------------------------------------------------------------
> > DB table users
> > -------------------------------------------------------------------------------------------------------
> > CREATE TABLE `users` (
> >   `id` int(10) NOT NULL auto_increment,
> >   `username` varchar(250) NOT NULL default '',
> >   `password` varchar(50) NOT NULL,
> >   `name` varchar(255) default NULL,
> >   `email` varchar(250) NOT NULL default '',
> >   `created` datetime NOT NULL default '0000-00-00 00:00:00',
> >   `modified` datetime NOT NULL default '0000-00-00 00:00:00',
> >   PRIMARY KEY  (`id`)
> > ) ENGINE=InnoDB DEFAULT CHARSET=latin1 AUTO_INCREMENT=1 ;
>
> > -------------------------------------------------------------------------------------------------------
> > VIEW->login.ctp
> > -------------------------------------------------------------------------------------------------------
> > <h1>Log In:</h1>
> > <?= isset($auth_msg) ? $auth_msg: ''?>
> > <?php e($form->create('User', array('action'=>'login')));?>
> >                 <?php echo $form->input('username');?>
> >                 <?php echo $form->input('password',
> > array('value'=>''));?>
>
> > <div class="submit"><input type="submit" value="Login" /></div>
> > <?php echo $form->end();?>
>
> > -------------------------------------------------------------------------------------------------------
>
> > Enjoy and let me know if you have better ways for authentication.
>
> > Dan- Ocultar texto de la cita -
>
> - Mostrar texto de la cita -


--~--~---------~--~----~------------~-------~--~----~
You received this message because you are subscribed to the Google Groups "Cake 
PHP" group.
To post to this group, send email to [email protected]
To unsubscribe from this group, send email to [EMAIL PROTECTED]
For more options, visit this group at 
http://groups.google.com/group/cake-php?hl=en
-~----------~----~----~----~------~----~------~--~---

Reply via email to