I've tried to find information on this and can't find any. I have a Laravel 7 application and have used the Laravel AUTH scaffolding for login/registration/authentication.
I would like to allow a logged in user to add other users, I've done the simply but pushing the data in to the database (obviously no password is set) but now I would like to send an email to these users asking them to set a password and am unsure how to do this. I see Laravel has some events related to auth built in such as this called in the register function of RegistersUsers.php:
event(new Registered($user = $this->create($request->all())));
Can anyone confirm where I would need to create such an event and how I call it from the store function that adds the user to the database?
Any help much appreciated.
As suggested by #lagbox I simply did the following:
$user = \App\User::create([
'firstname' => $validatedData['firstname'],
'lastname' => $validatedData['lastname'],
'email' => $validatedData['email'],
'company_id' => $company_id,
'phone_number' => $validatedData['phone_number'],
'password' => Str::random(16),
]);
event(new Registered($user));
Related
I have a Laravel web application (website.nl) AND an Laravel API (api.website.nl).
When the user logs in with the login form on the website. A post request is done to the API. When the login request is successfull a token AND User object is send back in the form of a JSON string. The login method looks like this.
public function login(Request $request)
{
$email = $request->input('email');
$password = $request->input('password');
$response = $this->client->request('POST', self::$apiRootUrl . '/login', [
'headers' => [
'Accept' => 'application/json',
],
'form_params' => [
'email' => $email,
'password' => $password
],
]);
$result = json_decode($response->getBody()->getContents());
if (isset($result->success->token))
{
$user = User::create([
'id' => $result->success->user->id,
'name' => $result->success->user->name,
'email' => $result->success->user->email,
'password' => $password
]);
Auth::login($user);
$this->apiToken = $result->success->token;
return $this->sendLoginResponse($request);
}
return $this->sendFailedLoginResponse($request);
}
Where I want this login function to be as stupid as possible, meaning, let the API figure out if this is a valid login request. This method only passes the arguments.
The main website should not have a database. It only uses the API to login, get a token, and do requests with that token to gather data for the user to see on the main website's dashboard.
For this reason my question is this: How can I store the User object retrieved from the API in such a manner that it will be query-able like an Eloquent model. But without the need to store it in a database. Again, the main website shouldn't need a database. It only communicates with the API for it's data.
I hope this question makes sense, if not, please ask for more details.
I don't want to create a duplicate database with migrations on the main website. Because that's the job of the .api subdomain. Also, all the models are used within a session. Never being stored for a longer time, because that's also located in a store method on the .api subdomain.
This would require you to write your own grammar for Eloquent, an ActiveRecord implementation for the API you're using.
In theory it's possible, in practice it's a lot of work.
Take a look here for how Laravel implements the database types it currently supports.
https://laravel.com/api/5.8/Illuminate/Database/Schema/Grammars.html
I defined an option in my website named "define user". So I need to do some changes in the current laravel registration system. Actually I did what I need:
public function register(Request $request)
{
$this->validator($request->all())->validate();
event(new Registered($user = $this->create($request->all())));
if ( !isset($request->registered_by_id) ) { -- added
$this->guard()->login($user);
$status = ""; -- added
$msg = ""; -- added
} else { -- added
$status = "define-user-alert-success"; -- added
$msg = "the user registered successfully";
} -- added
return $this->registered($request, $user)
?: redirect($this->redirectPath())
->with($status, $msg); -- added
}
As you know, function above is located under /vendor/laravel/framework/src/illuminate/Foundation/Auth/RegisterUsers.php path. The problem is all the change I made will be ignored when I upload my website and execute composer install command.
Any idea how can I keep my changes in the vendor directory?
composer install will overwrite your changes as it just fetches the latest version from the public repo and installs that.
I would suggest one of the following;
Create your own fork of laravel and have composer load this over default laravel. I did this recently with a Symfony component fork, the idea is to change the repo branch name to your modified one and override the source with your own repo. Instruction from my fork are here.
Upload the file manually via after executing composer install (not recommended, only use a stop-gap).
Override/extend the original class, this answer lays out the process nicely.
As defined in this answer on Laracasts (which is very similar to your case), use event listeners to execute your code after user registration.
Hope this helps!
I would strongly recommend against making any changes to the core framework - aside from the issue you mentioned, it can also make upgrades extremely difficult.
Fortunately, Laravel makes user registrations easy. All you need to do is create a new controller (E.g. UserController) and then use a function like this to create a model for them ...
public function registerUser(Request $request){
$request->validate([
'username' => 'bail|required|unique:users,username|max:255',
'first_name' => 'required',
'last_name' => 'required',
'email' => 'required|email'
]);
$user = User::create([
'first_name' => $request->first_name,
'last_name' => $request->last_name,
'username' => $request->username,
'password' => Hash::make($request->password),
'email' => $request->email
]);
return redirect('/settings/people/'.$user->user_id);
}
The key here is to use the hash facade to encrypt the password before committing the model to the database. Otherwise, it's essentially like working with any other model.
Yea, don't edit the file in vendor.
This trait is used in the RegisterController which exists in your app, not the framework. You can simply override that method in your controller, done.
Perhaps your changes can go in registered which is called after registration so you don't have to override this functionality of register itself (since registered is a blank method waiting to be overridden)
I need to customise the logic for Laravel's authentication. I found a solution on SO, by overriding the credentials method in the LoginController like so:
return ['email' => $request->{$this->username()}, 'password' => $request->password, 'status_id' => $whatever];
But now I discovered an issue where a user can still reset their password and then they get signed in automatically. So how can I disable password resets for users who should not be allowed to sign in?
There is a method on the ResetsPasswords trait called resetPassword()
Override this in your Auth/ResetPasswordController and replace the line
$this->guard()->login($user);
with whatever functionality you want to achieve after the password reset.
If you want to prevent a disabled user from resetting their password, use a middleware to check if the account is disabled before continuing with the password reset.
You can create a new column to your user table isbanned that excepts only boolean value. And check further of this column value of a user that requests for reset password. If the value is TRUE, don't give the reset link, otherwise, give it.
Below you can see this example:
if (Auth::attempt(array('phone' => $request->input('phone'), 'password' => $request->input('password'), 'isactive' => '1', 'isbannes' => '0'), $remember)){
// your logic
}
Hope this helps you.
I'm currently developing a little web portal where users can register, but they should also be able to login as guests.
How I'm trying to do that is by this code:
public function registerGuest(){
$user = User::create([
'name' => "Gast",
'firstName' => "Gast",
'sex' => "gast",
'password' => bcrypt("pw"),
'role' => "buyer",
'templateURL' => "",
'confirmation_code' => ""
]);
$user->attachRole(2);
Auth::loginUsingID($user,true);
return redirect('/home');
}
found in my RegisterController.
So I'm basically registering a user (the same way they normally register) but with a simple password and no email address entered. Then I try to login this user using the ID. The user is created in the database but the login doesn't work.
Does anybody happen to know why this happens? And how can I fix this?
A more elaborate explanation to understand my idea:
Users can normally register, entering some of their personal data. But they should also be able to click on a button saying "proceed as guest", which points to the above function. Then they are logged in like the registered user and can afterwards also register, keeping the information they entered while being logged in as guest user and also they can then set a password? The purpose: They might want to first test it and then register afterwards.
Any ideas?
The function expects the user ID, not the object:
Auth::loginUsingID($user->id,true);
I am new to laravel I have integrated inbuilt authentication system and works perfect. Now I also want to consider status field of user table while authenticate. I search a lot but could not find proper way to integrate such functionality with inbuilt laravel's authentication system.
Considering user status when authenticating is simple. There are 2 ways to do that, depending whether you call Auth::attempt() manually or you use AuthenticatesUsers or RegistersAndAuthenticatesUsers trait in your controller.
If you are calling Auth::attempt() manually, you always pass an array of credentials to the method. Those credentials are used to fetch user from the database. Add status field to those credentials and only users with given status will be able to log in, e.g.:
Auth::attempt([
'username' => Request::input('username'),
'password' => Request::input('password'),
'status' => 'active'
]);
Above will allow only users with status=active to log in.
If you are using AuthenticatesUsers or RegistersAndAuthenticatesUsers trait in your controller, you need to override the getCredentials() method. This method should return the same array that you'd pass to Auth::attempt():
protected function getCredentials(Request $request) {
return [
'username' => Request::input('username'),
'password' => Request::input('password'),
'status' => 'active'
];
}