Laravel attempt() doesn't work, getAuthIdentifier use wrong column - php

I want to use column email and password for login.
Password is hashed during registration and saved to the database ('driver' => 'database').
Email column is not primary key, but just unique.
AuthController.php:
// Get all the inputs
$userdata = array(
'email' => Input::get('username'),
'password' => Input::get('password')
);
// Declare the rules for the form validation.
$rules = array(
'email' => 'Required',
'password' => 'Required'
);
// Validate the inputs.
$validator = Validator::make($userdata, $rules);
// Check if the form validates with success.
if ($validator->passes())
{
// Try to log the user in.
if (Auth::attempt($userdata, true))
{
// Redirect to homepage
return Redirect::to('')->with('success', 'You have logged in successfully');
}
else
{
// Redirect to the login page.
return Redirect::to('login')->withErrors(array('password' => 'password invalid'))->withInput(Input::except('password'));
}
}
Anyway, I just got error:
ErrorException
Undefined index: id
It also shows me this:
public function getAuthIdentifier()
{
return $this->attributes['id'];
}
What I am doing wrong? Thanks
EDIT
User model:
<?php
use Illuminate\Auth\UserInterface;
use Illuminate\Auth\Reminders\RemindableInterface;
class User extends Eloquent implements UserInterface, RemindableInterface {
/**
* The database table used by the model.
*
* #var string
*/
protected $table = 'users';
/**
* The attributes excluded from the model's JSON form.
*
* #var array
*/
protected $hidden = array('password');
/**
* Get the unique identifier for the user.
*
* #return mixed
*/
public function getAuthIdentifier()
{
return $this->getKey();
}
/**
* Get the password for the user.
*
* #return string
*/
public function getAuthPassword()
{
return $this->password;
}
/**
* Get the e-mail address where password reminders are sent.
*
* #return string
*/
public function getReminderEmail()
{
return $this->email;
}
}

getAuthIdentifier is an interface method. GenericUser class is implementating that method and requires user id.
So check do you really have id attribute on your model.

In case this helps someone in the future here is how I resolved this. As #WereWolf suggested you do want to set
protected $primaryKey = 'id';
in your model, but your driver should also be 'eloquent' in your auth.php config.
'driver' => 'eloquent',
This will tell laravel to use your Eloquent model as the user object instead of the generic user object from the database table.

You most probably didn't assign your primary key in the user table, the ID should be primary key and also you may add following in your User model to specify your custom primary key:
protected $primaryKey = 'id';
Make sure that, the primary key in the user table matched with this ($primaryKey), means that, must be same.

Related

Why does my Login only work in these specific circumstances?

I am using laravel/ui with Laravel 7.15.0 and PHP7.3 to build a login for my website, but I have issues logging in my user.
I have the checkmark option for the remember_token on my login page.
What is happening on my login page
First case: 'remember_token' column exists in my users table
When I click on the login button, it will shortly authenticate the user. If I dump 'Auth::check()' in the method 'authenticated' in my LoginController (made by laravel/ui), it will return true. But then the user won't be logged in anymore, once it redirects me to my home page.
When 'remember me' is ticked, it will write a value to the column in my users table .
Second case: 'remember_token' column does not exist in my users table AND the 'remember me' box is ticked
Now this is the weird part. When I don't have that column, on login, it will throw an error
SQLSTATE[42S22]: Column not found: 1054 Unknown column 'remember_token' in 'field list'
BUT then when I navigate to any page and run Auth::check() there, it returns true, so the user has been logged in.
If the box has not been ticked it has the same result as the first case.
What I have tried
So far I have tried to look into how the remember_token thing works in the laravel/ui code. Using the token should not even be necessary though if I am not mistaken.
Some infos
I have not changed my Authentication guard
I have changed my user.php and LoginController.php since my users
table has a different name and column names.
I have wrapped my routes in the 'web' middleware, since apparently
that might be necessary to persist the session.
I can provide more info about my code if necessary. Any help would be appreciated!
This is my User.php file:
class User extends Authenticatable
{
use Notifiable;
/**
* If timestamps should be used in the database.
*
* #var array
*/
public $timestamps = false;
/**
* The table where the users are stored.
*
* #var array
*/
protected $table = 'backend_user';
/**
* The primary key of the table.
*
* #var array
*/
protected $primaryKey = 'bck_userid';
/**
* The attributes that are mass assignable.
*
* #var array
*/
protected $fillable = [
'bck_userid', 'bck_fullname', 'bck_password', 'bck_email'
];
/**
* The attributes that should be hidden for arrays.
*
* #var array
*/
protected $hidden = [
'bck_password',
];
/**
* The attributes that should be cast to native types.
*
* #var array
*/
// protected $casts = [
// 'email_verified_at' => 'datetime',
// ];
public function getAuthIdentifierName()
{
return 'bck_email';
}
public function getAuthIdentifier()
{
return $this->bck_email;
}
public function getAuthPassword()
{
return $this->bck_password;
}
}
And this is the definition of my "users table". Its name is 'backend_user':

Laravel authentication fails

I,ve just started with Laravel but i still have an problem with my authentication. I need to build my system on an existing database structure. The user table password uses md5 and i like to convert that to the Laravel Hash. But after converting the md5 password to hash the login fails with this new hash. I cannot find the solution for this problem.
Table
id (int11)
gebruikersnaam (varchar 255)
wachtwoord (varchar 255)
updated_at (timestamp)
created_at (timestamp)
remember_token (timestamp)
User model
use Illuminate\Auth\UserTrait;
use Illuminate\Auth\UserInterface;
use Illuminate\Auth\Reminders\RemindableTrait;
use Illuminate\Auth\Reminders\RemindableInterface;
class User extends Eloquent implements UserInterface, RemindableInterface {
use UserTrait, RemindableTrait;
/**
* The database table used by the model.
*
* #var string
*/
protected $table = 'gebruikers';
/**
* The attributes excluded from the model's JSON form.
*
* #var array
*/
protected $hidden = array('wachtwoord');
}
Login controller
class LoginController extends BaseController {
function starten(){
$rules = array(
'gebruikersnaam' => 'required', // make sure the email is an actual email
'wachtwoord' => 'required' // password can only be alphanumeric and has to be greater than 3 characters
);
$validator = Validator::make(Input::all(), $rules);
if ($validator->fails()) {
return Redirect::to('/')
->withErrors($validator)
->withInput(Input::except('password'));
} else {
$user = User::where('gebruikersnaam','=',Input::get('gebruikersnaam'))
->first();
if(isset($user)) {
if($user->wachtwoord == md5(Input::get('wachtwoord'))) {
$user->wachtwoord = Hash::make(Input::get('wachtwoord'));
$user->save();
}
}
$userdata = array(
'gebruikersnaam' => Input::get('gebruikersnaam'),
'wachtwoord' => Input::get('wachtwoord')
);
if (Auth::attempt($userdata)) {
return Redirect::to('users/dashboard')
->with('message', 'You are now logged in!');
} else {
return Redirect::to('/')
->with('message', 'Deze combinatie van gebruikersnaam en wachtwoord lijkt helaas niet te kloppen')
->withInput();
}
}
}
}
Auth
return array(
'driver' => 'eloquent',
'model' => 'User',
'table' => 'gebruikers',
'reminder' => array(
'email' => 'emails.auth.reminder',
'table' => 'password_reminders',
'expire' => 60,
),
'username' => 'gebruikersnaam',
'password' => 'wachtwoord',
);
Note: Input::get('wachtwoord') and Input::get('gebruikersnaam') are filled correctly by post in the controller. The md5 is correcly changed to the Laravel hash in my db so i cannot find the problem what i dealing with.
Note2: "gebruikersnaam" is dutch for username and "wachtwoord" is dutch for password
Note 3: i use Laravel 4
** EDIT **
Output $user
["attributes":protected]=> array(16) { ["id"]=> int(8681) ["gebruikersnaam"]=> string(22) "---" ["wachtwoord"]=> string(60) "$2y$10$i3bemDK9NzNf/E0jmliv/eBPrqhq/3s3WGPTX3h6WNCMlXcS5W51i" ["email"]=> string(22) "---" ["voornaam"]=> string(5) "Jelle" ["tussenvoegsel"]=> NULL ["achternaam"]=> string(4) "Pals" ["school_id"]=> int(110) ["telefoonnummer"]=> string(10) "0655684308" ["geslacht"]=> string(3) "man" ["geboortedatum"]=> string(19) "1990-03-22 09:00:00" ["groep_id"]=> int(8811) ["status"]=> string(1) "1" ["updated_at"]=> string(19) "2014-06-25 14:53:43" ["created_at"]=> string(19) "0000-00-00 00:00:00" ["remember_token"]=> string(0) "" }
**Found strange 000000 in updated_at **
I think the issue is that you're using the default Eloquent user settings (UserTrait) which assume that your password field is 'password' (see here), but you're using 'wachtwoord'. As such, logins fail due to the lack of a value in the password column (due to the lack of the column entirely) to test passwords on.
In case you're thinking "but I clearly specify the password column in my auth config!" that's unfortunately a bit of a red herring - that part of the config is for if you use the standard DB auth, whereas you are using Eloquent auth (notice how, in your config, you have driver set to eloquent?), so you need to specify these fields in your model as per the interface.
Luckily, a class's own implementation overrides that of a trait, so you can theoretically keep the trait on your model, and just override the getAuthPassword method.
That said, that trait (and the remindable one) does very much assume you're using English names everywhere, so it may be worth you removing the two traits entirely (UserTrait and RemindableTrait) and writing your own versions of the interface methods, as you'll likely see the same thing happen if/when you use "remember me" or "forgotten password".
Edit: initial suggestion:
use Illuminate\Auth\UserTrait;
use Illuminate\Auth\UserInterface;
use Illuminate\Auth\Reminders\RemindableTrait;
use Illuminate\Auth\Reminders\RemindableInterface;
class User extends Eloquent implements UserInterface, RemindableInterface
{
use UserTrait, RemindableTrait;
/**
* The database table used by the model.
*
* #var string
*/
protected $table = 'gebruikers';
/**
* The attributes excluded from the model's JSON form.
*
* #var array
*/
protected $hidden = array('wachtwoord');
/**
* Override UserTrait#getAuthPassword
*/
public function getAuthPassword()
{
return $this->wachtwoord;
}
}
But, as I say, if you continue to use Dutch column names, you'll end up being better off dropping the traits entirely and implementing the methods yourself:
use Illuminate\Auth\UserInterface;
use Illuminate\Auth\Reminders\RemindableInterface;
class User extends Eloquent implements UserInterface, RemindableInterface
{
/**
* The database table used by the model.
*
* #var string
*/
protected $table = 'gebruikers';
/**
* The attributes excluded from the model's JSON form.
*
* #var array
*/
protected $hidden = array('wachtwoord');
/**
* Get the unique identifier for the user.
*
* #return mixed
*/
public function getAuthIdentifier()
{
return $this->getKey();
}
/**
* Get the password for the user.
*
* #return string
*/
public function getAuthPassword()
{
return $this->wachtwoord;
}
/**
* Get the token value for the "remember me" session.
*
* #return string
*/
public function getRememberToken()
{
return $this->aandenken_onthouden; // okay I made this up based on Google translate and some guesswork, use your own version!
}
/**
* Set the token value for the "remember me" session.
*
* #param string $value
* #return void
*/
public function setRememberToken($value)
{
$this->aandenken_onthouden = $value;
}
/**
* Get the column name for the "remember me" token.
*
* #return string
*/
public function getRememberTokenName()
{
return 'aandenken_onthouden';
}
/**
* Get the e-mail address where password reminders are sent.
*
* #return string
*/
public function getReminderEmail()
{
return $this->email;
}
}

Unable to Verify user in laravel

I'm new to laravel, so i started by creating a messaging application. User should be able to send message to each other. So i created migrations, seeds,models and also defined relationships in models. Everything was working fine. I was able to seed perfectly.
So i created a login page, applied validations. But now i'm unable to login.
Here is the route :
Route::group(array('prefix'=>'social'), function(){
Route::get('/', array('as' => 'loginformshow', 'uses' => 'LoginformController#showLogin'));
Route::post('loginform', array('as'=>'loginformdo', 'uses'=>'LoginformController#doLogin'));
Route::get('loggedin', array('as'=>'loggedin', 'uses'=>'LoginformController#loggedin'));
});
Here's the respective method in controller
public function doLogin(){
$rules = array('email'=> 'required|email', 'password'=>'required');
$validator = Validator::make(Input::all(), $rules);
if($validator->fails()){
return Redirect::to('social')->withErrors($validator)->withInput(Input::except('password'));
}else {
$userdata = array('email' => Input::get('email'), 'password' => Input::get('password'));
if(Auth::attempt($userdata)) {
return Redirect::route('loggedin');
}else echo "Invalid User";
}
}
Auth::attempt is returning false every time and so the output is Invalid User.
i used print_r to check the data received in $userdata and it's showing correct credentials.
Here's the User model:
<?php
use Illuminate\Auth\UserInterface;
use Illuminate\Auth\Reminders\RemindableInterface;
class User extends Eloquent implements UserInterface, RemindableInterface {
/**
* The database table used by the model.
*
* #var string
*/
protected $table = 'users';
/**
* The attributes excluded from the model's JSON form.
*
* #var array
*/
protected $hidden = array('password');
/**
* Get the unique identifier for the user.
*
* #return mixed
*/
public function getAuthIdentifier()
{
return $this->getKey();
}
/**
* Get the password for the user.
*
* #return string
*/
public function getAuthPassword()
{
return $this->password;
}
/**
* Get the e-mail address where password reminders are sent.
*
* #return string
*/
public function getReminderEmail()
{
return $this->email;
}
public function conversationsReply(){
return $this->hasMany('ConversationReply', 'user_id', 'id');
}
}

Login authentication fails in laravel 4

In Laravel4,I have written the following code in routes but it always redirect me to login page.
I have googled and found it on stack overflow too and tried all solutions but not succeeded.I am sure it would be a silly mistake but kindly track it out.Thank You
Routes:
Route::post('login', function ()
{
$user = array(
'username' => Input::get('username'),
'password' => Hash::make(Input::get('password'))
);
/* Store entered username and password in an array named as 'user' */
print_r($user);
if (Auth::attempt($user))
{
return Redirect::route('home')->with('flash_notice', 'You are successfully logged in.');
/* Authentication Success!!..Redirect user to home page */
}
else
{
return Redirect::route('login')
->with('flash_error', 'Your username/password combination was incorrect.')->withInput();
/* Authentication failure!! lets go back to the login page */
}
});
User Model:
<?php
use Illuminate\Auth\UserInterface;
use Illuminate\Auth\Reminders\RemindableInterface;
class User extends Eloquent implements UserInterface, RemindableInterface
{
/**
* The database table used by the model.
*
* #var string
*/
protected $table = 'users';
// public $timestamps = false;
/**
* The primary key of the table.
*
* #var string
*/
protected $primaryKey = 'id';
/**
* The attributes excluded from the model's JSON form.
*
* #var array
*/
protected $hidden = array('password');
/**
* Get the password for the user.
*
* #return string
*/
public function getAuthPassword()
{
return $this->password;
}
/**
* Get the e-mail address where password reminders are sent.
*
* #return string
*/
public function getReminderEmail()
{
return $this->email;
}
/**
* Get the unique identifier for the user.
*
* #return mixed
*/
public function getAuthIdentifier()
{
return $this->getKey();
}
/**
* Get the password for the user.
*
* #return string
*/
}
User Seeder:
<?php
class UserSeeder extends Seeder {
public function run()
{
DB::table('users')->delete();
return array('table'=>'users',
array(
'username' => 'admin',
'password' => 'admin'
),
);
}
}
When you ask the Auth class to attempt a login, you pass in the username and pass as it is. But if you look into the method, it will first hash the password to make it secure and then match it with database entry. When you are storing it, from your present implementation, its not hashed.
As suggested above, you should make this change in your seeder:
array(
'username' => 'admin',
'password' => Hash::make('password')
),
Although I am not very sure if the way you are using seeder is correct by syntax, but if it works, just hash the password there.
You should hash your password.
array(
'username' => 'admin',
'password' => Hash::make('password')
),
You can find more information in the docs.

Why cannot authenticate a user using Auth::atempt in Laravel?

This is routes file and $users shows the values but login fails
Route::post('login', function () {
$user = array(
'username' => Input::get('username'),
'password' => Input::get('password')
);
if(Auth::attempt($user))
{
return Redirect::to('profile')
->with('flash_notice', 'You are successfully logged in.');
}
else
{
// authentication failure! lets go back to the login page
return Redirect::route('login')
->with('flash_error', 'Your username/password combination was incorrect.')
->withInput();
}
});
Modal:
<?php
use Illuminate\Auth\UserInterface;
use Illuminate\Auth\Reminders\RemindableInterface;
class User extends Eloquent implements UserInterface, RemindableInterface {
/**
* The database table used by the model.
*
* #var string
*/
protected $table = 'users';
/**
* The attributes excluded from the model's JSON form.
*
* #var array
*/
protected $hidden = array('password');
/**
* Get the unique identifier for the user.
*
* #return mixed
*/
public function getAuthIdentifier()
{
return $this->getKey();
}
/**
* Get the password for the user.
*
* #return string
*/
public function getAuthPassword()
{
return $this->password;
}
/**
* Get the e-mail address where password reminders are sent.
*
* #return string
*/
public function getReminderEmail()
{
return $this->email;
}
}
When using the authentication mechanism provided by Laravel you should pass the following check list:
The database column where you store the password should be a string with a length of 60 characters.
The password should be stored encrypted, no plain. Since we are talking about BCrypt it has to be a value similar to: $2a$10$KssILxWNR6k62B7yiX0GAe2Q7wwHlrzhF3LqtVvpyvHZf0MwvNfVu.
You have to configure the security mechanism by editing the file located app/config/auth.php.
After that, you will eventually have your problem solved.

Categories