I am using Laravel Passport (auth:api), all works well however I've came with the idea to log record user requests on a specific route.
When an GET request is made to /movie/65 I would like to store in movie_view the following data: user_id, movie_id (if the user is logged in)
However in my controller I am unable to call $request->user() without setting auth:api middleware.
What is the best practice you recommend to achieve this?
Default Auth Type should be set to 'api' in config/auth.php
Source: https://laracasts.com/discuss/channels/general-discussion/optional-authentication-for-api?page=0 (it was very hard to find)
Best way to do this is:
if (\Auth::guard('api')->check()) {
$user = \Auth::guard('api')->user();
}
you have to setup the guard to 'api', the default one is 'web'.
You can create a custom middleware as suggested here -- https://laracasts.com/discuss/channels/laravel/how-to-handle-route-with-optional-authentication. Then apply api guard to it. Let say you assign that custom middleware as auth.optional in Kernel.php, then you can use that middleware as auth.optional:api (with that api guard). Then you can access user thru $request->user() in your case above.
Related
I was able to check Auth::check() via controller before redirecting to my other route that needed to passthrough a middleware to check if the Auth::check() == true, however, when i'm trying to check the value of Auth::check() via my Middleware it returned a FALSE / NULL value. Any Idea guys ??
Did the following already:
Set session via ENV file to database
Tried using multiple Guard as i needed this feature. though for the sake of making it working first, i disabled the Guard setup.
When Laravel is running through your middlewares, the authentication code still hasn't ran and hence why you get null as if there was no user logged in.
Enclose the routes in your web.php which utilize Authenticate middleware with the auth middleware.
That's when your Auth facade will work the same way it'd work in your controller.
I am new in laravel and I have one problem with middleware. On official laravel site, I found code for creating controller.
When I creating controller it is recommended to add middleware in constructor or this is only if I need some additional functionalities?
Also, if I include auth middleware, did I get some benefits by default, like security checks or similar or I must to rewrite middleware code first?
class UserController extends Controller {
/**
* Instantiate a new controller instance.
*
* #return void
*/
public function __construct() {
**//this part includes some protection or similar by default ?**
$this->middleware('auth');
}
}
Middleware is used when you want to filter the HTTP requests entering your application.
For example, including the built-in auth middleware will restrict non-authenticated users from accessing a page and redirect them to the login screen.
You can include middleware into your controller and routes.
In the controller you do it like so:
public function __construct()
{
$this->middleware('auth');
}
For a route you do this:
Route::get('/page', 'MyController#myMethod')->middleware('auth');
Do I need to include this part of code when I creating controller or not ?
As I said in my comment, it really depends on the desired functionality whether you use it or not.
An example
Your homepage should probably be accessible for anyone who visits you website, while your dashboard should only be displayed to authenticated users.
That's where you would include the auth middleware.
Question #1
Do you need to use $this->middleware('auth'); in your controller?
Answer: Only if you want to protect all of the methods of that controller from non-authenticated users and only allow signed in users to access controller actions.
Question #2
Do you get benefits for using the auth middleware?
Answer: Yes you do, only authenticated users can access the controller or routes protected by auth.
** Question #3**
Do you need to write your own middleware?
Answer: Only if you need to override a middleware or need extra functionality that is not already provided (php artisan make:auth), but if you are rolling your own login functionality then you will likely need/want to create your own middleware.
Resources:
Look in App\Http\Kernel.php and you will see that the $routeMiddleware array matches the auth middleware to the \Illuminate\Auth\Middleware\Authenticate::class which actually verifies that the current user is logged in and allows them to pass, if they are not logged in then it will redirect them to the '/login' route.
You will see that Laravel uses quite a bit of middleware by default, such as starting the session, encrypting cookies and protecting against CSRF forgery.
There are several ways to implement middleware, which I'm sure you saw in the docs.
Some Helpful Video Tutorials:
I suggest you watch each of the free series usually titled Laravel from Scratch on Laracasts.com. I would also suggest watching all of from Laravel 5.7 back to 5.1 or 5.0 as Jeffrey Way may use different techniques in similar situations and it will provide you with a great tips and helpful information as to how things work along with some Laravel best practices along the way. I've subscribed to him for years and work in Laravel everyday and I still learn some new things from watching his videos, a subscription is easily worth 10-20 what he charges.
I am attempting to create a 2FA Middleware with CakePHP 3. I have created the middleware basics just fine, however, I do not know how to get the user id of the current user in the middleware, typically I get the id like so...
$this->Auth->user('id');
Is there anyway to load the AuthComponent in the Middleware?
If not, how can I go about getting the current user id?
I think You can use request session handler to grab current user id
$this->request->session()->read( 'Auth.User.id' )
Use the official authentication plugin which replaces the AuthComponents authentication part: https://github.com/cakephp/authentication This will oficially replace the component approach in the next release.
It features also a middleware, just make sure it's in the pipe before yours and you can use $request->getParam('identity').
I am a bit confused, I have a web application having a login, Register, Logout. Some dashboard views etc(CRUD), I want to make an api for this application too.
Like an api which third party will use, Can update records, Can delete records etc.
Actually there should be some way which can be use by mobile app for CRUD.
I know we have that routes/api.php, But i am pretty confused that when to use it. Please explain the scenario, I am blank.
Update:
Scenario
Application having views, authentication system etc, How an android app will be able to perform CRUD operations on the same application ?
1.web routing uses session state, CSRF protection. does it mean api routing not using session state, CSRF protection?
All it possible but not required. You still can using sessions etc, but this is a REST principles violation.
2.laravel 5.3 uses seperate web and api routing, is there any advantages ?
It's just for your convenience. In Laravel 5.2 you need specify middleware for routes like ['web'] or ['api'] but it doesn't required anymore. In 5.3 routes stored in separated files and specify routes middleware not required.
If you are specifying routes in api.php, you will need to use the auth:api middleware. For example:
Route::group(['middleware' => ['auth:api']], function () {
Route::get('/test', function (Request $request) {
return response()->json(['name' => 'test']);
});
});
Notes about Token auth and Laravel 5.3:
If you've setup laravel's default auth system, you will also need to add a column for api_token to the user table. If you are using DB seeders, you might want to add something like:
$table->char('api_token', 60)->nullable();
to your users table seeder. Alternatively just add the column manually and fill that column with a random 60-char key.
When making the request, you can add the api_token as a URL/Querystring parameter like so:
domain.com/api/test?api_token=[your 60 char key].
You can also send the key as a header (if using Postman or similar), i.e: Header: Authorization, Value: Bearer [your 60 char key].
I order to get a useful error if the token is incorrect, also send the following header with all requests:
Header: Accept, Value: application/json. This allows the expectsJson() check in the unauthenticated() function inside App/Exceptions/Handler.php to work correctly.
in my user table I have a active_id column to track this user account is still active or not.
Is it possible when a logged in user visit our website, check if it's not a active user then logout the logged in user.
Or when the logged in inactive user perform a post request , log out the user immediately .
Is it possible ?
You can accomplish this very easily with Middleware
Do the console command php artisan make:middleware CheckUserIsActive
Go to the generated file at app/Http/Middlewares/CheckUserIsActive
In the handle method
public function handle($request, Closure $next)
{
if (! $user = auth()->user()->is_active) {
auth()->user()->logout();
}
return $next($request);
}
Edit the app/Http/Kernel.php file: find web key on middlewareGroups property and append your new middleware \App\Http\Middlewares\CheckUserIsActive::class,
With this approach the check will be fired off on each request on your app, assuming that in your routes.php file you have web group middleware applied to all your routes, which is the case if you installed laravel and didn't change it.
Take a closer look at middlewares in the Documentation
Also note, that this will work only when there is an authenticated user. If there isn't then auth()->user() will return null and you'll get and error like 'Trying to call method logout() on null'. To avoid this error you need to make sure that there is an authenticated user and only then check if he's active. To do so Laravel provides built in auth middleware. Just append it to the middlewaresGroups's web key before your own middleware.
But again this is to work if it's fit your projects needs. If you do require user to be authenticated to go to any of the pages of your app then do this approach. if not - you need to limit some requests to be filtered by middlewares. Again, you may find this on docs or ask here if needed, I'll provide samples