views:

156

answers:

3

I have this controller set up for a login:

<?php
class Login extends Controller {

    function __construct() {
        parent::Controller();
        $this->form_validation->set_error_delimiters('', '');
        $this->output->enable_profiler(TRUE);
    }

    function index(){

        redirect('/login/terminal');

    }

    function terminal() {
    // terminal login

        $this->form_validation->set_rules(array('username','password'), 'Username', 'callback_terminal_login_check[$username,$password]');
        if ($this->form_validation->run() == FALSE) {
            $this->load->view('login_header');
            $this->load->view('login_terminal');
            $data['version'] = $this->master->GetVersion();
            $this->load->view('login_footer', $data);
        } else {
            redirect('/terminal');
        }

    }

    function terminal_login_check($username,$password) {
    // callback function to perform terminal login  

        if ($this->authentication->DoTerminalAuthentication($username,$password)) {
            echo $username;
            return TRUE;
        } else {
            $this->form_validation->set_message('terminal_login_check', 'Invalid');
            return FALSE;
        }


    }

}

What I am looking at is the line that does the form validation callback >> $this->form_validation->set_rules(array('username','password'), 'Username', 'callback_terminal_login_check[$username,$password]');

I know this is not right. Basically what I want to do is check the username and password against the Authentication->DoTerminalAuthentication model to process the user's login. I want to pass the $username and $password form fields. Here is my form view if it helps:

<div id="title">Terminal Login</div>
<?php 
    if (validation_errors()) {
        echo '<div id="error">' . validation_errors() . '</div>';
    }
?>

<?=form_open('login/terminal');?>
<?=form_label('Username', 'username')?><br />
<?=form_input(array('id'=>'username','name'=>'username','value'=>set_value('username')))?><br />
<?=form_label('Password', 'password')?><br />
<?=form_password(array('id'=>'password','name'=>'password'))?><br />
<?=form_submit(array('name'=>'passwordsubmit','value'=>'Login >>'))?><br />
<?=form_close();?>
+2  A: 

As I understand it, form validation works on a field by field basis. To achieve what you want, I would attach the callback to one of the fields (probably the password field would be best) and then access the other form field data using the global POST array. This way you don't need to pass anything to the callback function as parameters.

musoNic80
+1  A: 

Use this in your controller to set your validation rules.

$this->form_validation->set_rules('username', 'Username', 'required');
$this->form_validation->set_rules('password', 'Password', 'callback_terminal_login_check');

And a callback something like this. I'd use a model if you are comparing your post data to a database.

function terminal_login_check() 
{
  $username = $this->input->post('username');
  $password = $this->input->post('password');

  // LOAD MODEL HERE

  if ($this->authentication->DoTerminalAuthentication($username, $password)) 
  {
    echo $username;
    return TRUE;
  } 
  else 
  {
    $this->form_validation->set_message('terminal_login_check', 'Invalid');
    return FALSE;
  }
}
Nick Pyett
A: 

I prefer to use form validation for simple input validation like checking for empty fields, invalid email addresses, too short passwords etc. I tend not to use form validation for more complex logic like authentication. I'd put the authentication check in the action method rather than in a validation callback function. It would get past your particular problem by side-stepping it.

function terminal() 
{
    $this->form_validation->set_rules('username', 'Username', 'required');
    $this->form_validation->set_rules('password', 'password', 'required');   

    if ($this->form_validation->run()) 
    {
        $username = $this->input->post('username');
        $password = $this->input->post('password');

        if ($this->authentication->DoTerminalAuthentication($username, $password))
        {
            // Handle successful login
        }
        else
        {
            // Authentication failed. Alert the view.
            $this->load->view('terminal', array('login_failed' => true));
        }
    } 
    else 
    {
        $this->load->view('terminal', array('login_failed' => false));
    }
}

And then in the view you can place this below your login form

<?php if ($login_failed) : ?>
    <span id="login-failed-message">Login failed</span>
<?php endif; ?>
Stephen Curran