Laravel 8 Jetstream custom api - php

I'm attempting to create a login endpoint so that I can use it without a blade.php file. While working with Unreal engine I cant use a actual web page so wanting to create a Login endpoint that will send back custom json. The below is what I have set up. When i use postman or Python requests I get a page response of Not Found or page expired. How can I get this to return the test or failed?
api.php
Route::post('/unreal-login', 'App\Http\Controllers\UnrealLoginController#authenticate');
UnrealLoginController.php
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
class UnrealLoginController extends Controller{
public function authenticate(Request $request){
// Retrive Input
$credentials = $request->only('email', 'password');
if (Auth::attempt($credentials)) {
// if success login
return "test";
//return redirect()->intended('/details');
}
// if failed login
return "failed";
}
}

Related

Laravel Http request to route sends forever

I want to have a link in an email that send to the user, the link is the url of the site and has an api token for the user to authenticate with.
however I am trying to send an api request to get the user details so I can authenticate the user and redirect them to the relavent page, however doing this I end up with a request the spins endlessly.
what could be the issue and if there are any other solutions please let me know.
the link/request looks like this
http://localhost:8005/api/token?_token=<API TOKEN>
The controller that handles the request
<?php
namespace App\Http\Controllers;
use Auth;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\URL;
use Illuminate\Support\Facades\Http;
class PassportController extends Controller
{
function getToken(Request $request)
{
// return $request->_token;
return $user = Http::withToken($request->_token)->get('http://localhost:8005/api/user');
Auth::login($user);
return redirect('/dashboard');
}
}
Also when I send the request it gets stuck and I have to restart my php artisan serve again to make more requests, and every time i do so, It opens up on a new port, 8001,8002,8003 etc
You can make a call back to the app itself like this:
$tokenRequest = Request::create('/api/user', 'GET', ['name' => 'value']);
$tokenResult = app()->handle($tokenRequest);
Update the variables to match your implementations.

Laravel 8: How do i verify the users email address after registration without having to require login information?

I set up a Laravel 8 installation with Jetstream and implemented a custom user registration, where an event is fired after a successful creation of the database record event(new Registered($user));.
The initial registration process should not require a password yet, because only a selected set of users should be able to login to a dashboard in the future.
After the registration the user gets an email with a verification link, however he still needs to login in order to get verified.
I tried to remove the auth middleware in routes/web.php, however i get an error message after attempting to verify a users email address.
Route::get('/email/verify/{id}/{hash}', function (EmailVerificationRequest $request) {
$request->fulfill();
return view('home');
})->middleware(['auth','signed'])->name('verification.verify');
Is it possible to verify a users email address without login information?
It is possible.
You can modify files directly in Jetstream packages however I will present method adding new files and keeping original packages untouched.
Add new Controller App\Http\Controllers\VerifyEmailController.php
<?php
namespace App\Http\Controllers;
use Illuminate\Auth\Events\Verified;
use Illuminate\Http\RedirectResponse;
use Illuminate\Http\Request;
use Illuminate\Routing\Controller;
use App\Models\User;
class VerifyEmailController extends Controller
{
public function __invoke(Request $request): RedirectResponse
{
$user = User::find($request->route('id')); //takes user ID from verification link. Even if somebody would hijack the URL, signature will be fail the request
if ($user->hasVerifiedEmail()) {
return redirect()->intended(config('fortify.home') . '?verified=1');
}
if ($user->markEmailAsVerified()) {
event(new Verified($user));
}
$message = __('Your email has been verified.');
return redirect('login')->with('status', $message); //if user is already logged in it will redirect to the dashboard page
}
}
In web.php add a new route without auth middleware:
use App\Http\Controllers\VerifyEmailController;
...
Route::get('/email/verify/{id}/{hash}', [VerifyEmailController::class, '__invoke'])
->middleware(['signed', 'throttle:6,1'])
->name('verification.verify');
At the end clear routes cache:
php artisan route:cache
Open config/fortify.php file and uncomment the Features::emailVerification(), line.
'features' => [
Features::registration(),
Features::resetPasswords(),
// Features::emailVerification(),
Features::updateProfileInformation(),
Features::updatePasswords(),
Features::twoFactorAuthentication([
'confirmPassword' => true,
]),
],
Next go to the User modal and implement the MustVerifyEmail interface.
class User extends Authenticatable implements MustVerifyEmail{
use Notifiable;
}
Note: you should have knowledge about Mail in Laravel

Laravel API Not Found

I'm trying to test my api and for this matter I don't need authentication for my api all I want to do is to share my published posts with api but I get 404 page.
Code
controller
<?php
namespace App\Http\Controllers\API;
use Illuminate\Http\Request;
use App\Http\Controllers\Controller;
use App\Post;
class PostController extends Controller
{
public function index(){
return Post::orderby('id', 'desc')->where('status', '=', '1')->get();
}
public function single($slug){
return Post::where('slug', $slug)->where('status', '=', '1')->firstOrFail();
}
}
api.php (routes folder)
Route::get('posts', 'API\PostController#index');
Route::get('posts/{slug}', 'API\PostController#single');
I tried to access my api posts with url like: http://newapp.test/api/posts and it returns 404 error.
Any idea?
Update
api.php
<?php
use Illuminate\Http\Request;
// Route::middleware('auth:api')->get('/user', function (Request $request) {
// return $request->user();
// });
Route::get('posts', 'API\PostController#index');
Route::get('posts/{slug}', 'API\PostController#single');
Leave all things as it is and RUN Command
php artisan route:clear
Run command php artisan route:list. It will show you list of available routes in your application. In this way, you could first verify the existing routes and the ones you are trying to access.
My API mistake was: redirecting back
if($validator->fails()){ return redirect()->back()->withInput()->with('error',$validator->errors()->first());}
corrected by: returning a JSON
if($validator->fails()){ return $this->responseWithError($validator->errors()->first()); }
responseWithError is a helper method that returns JSON in a certain structure

Auth::check() returning false in Laravel 5.4

I am using laravel 5.4 as backend for my application and for front-end I am using angular. I am using laravel auth for authentication.
Issue is Auth::attempt() is working fine and if immediately I print the Auth::user() then it prints the data but it returns false if I try to fetch it in next method. But this functionality is working fine in hosted server.
Tested,
Changing session from file to database.
Changes in kernel.php (Content of $middleware).
Did php artisan make:auth one more time.
Did changes in user table column.
Adding private $primarykey = 'id' to model.
Adding 'web' middleware to all routes.
This is my Controller
namespace App\Http\Controllers\Auth;
use App\Http\Controllers\Controller;
use Illuminate\Foundation\Auth\AuthenticatesUsers;
use Illuminate\Support\Facades\Validator;
use Illuminate\Support\Facades\Input;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
use App\User;
public function login()
{
if (Auth::attempt(['email' => $email, 'password' => $password ]))
{
$response = array('response' =>'Succssfully Login!' , 'success' => true);
return $response;
}
}
This is where i am using Auth::check() in the same controller
public function check()
{
if(Auth::check())
$response = array('response' =>'Authenticated' , 'success'=>true);
else
$response = array('response' =>'UnAuthenticated' , 'success'=>false);
return $response;
}
I am confused because same code is working fine in hosted server but not working on localhost. Do I need to do any http related changes in laravel for this?
In case your Angular application is outside laravel, and loading without using blade template to load your Angular app's entry point i.e. Angular's index.html then what happens is Laravel is not able to set session for the app, hence when you request for the next time your laravel is not able to recognise the session so it gives false when you call Auth::check().
To achieve authentication on external (i.e Angular app on your case) you should use either Laravel Passport's password client or JWT based authentication using https://github.com/tymondesigns/jwt-auth <- this package. (Instructions on the package's readme file)
For angular and web based app I would prefer to go with JWT.

Log in a user based on value Laravel

I am verifying user's account via email and I want to redirect the user directly to home page after account is verified.
The issue I am having is that I am not sure how to actually log in the user using login function.
class VerificationController extends Controller {
public function verify($token){
User::where('email_token',$token)->firstOrFail()->verified();
// auth()->login($user); works if $user exists
return redirect('/home');
}
}
Can I log in the user based on the email_token? I tried but it doesn't seem to work as expected.
You are on the right way. You just need to get the User instance and pass it to the login Method of the Auth class. I've made an example controller for you to show how this could be done.
class VerificationController extends Controller
{
public function verify($token)
{
// Fetch the user by the email token from the database.
// #firstOrFail returns the first matching user or aborts
// the request with a 404 error.
$user = User::where('email_token', $token)->firstOrFail();
// Activate your user or whatever this method does.
$user->verified();
// Logs the Client who did this web request into the
// User account fetched above in.
Auth::login($user);
// Redirect to wherever you want.
return redirect('/home');
}
}
Read more about authenticating users in the official documentation:
https://laravel.com/docs/authentication#other-authentication-methods
First, you have to configure login model in providers section in config/auth.php
Some changes have to made in login model also
<?php
namespace App;
use Illuminate\Database\Eloquent\Model;
use Illuminate\Auth\Authenticatable;
class ModelName extends Model implements \Illuminate\Contracts\Auth\Authenticatable
{
use Authenticatable;
}
and in your controller
if (!Auth::attempt(['username' => $username, 'password' => $password])) {
return redirect()->back()->with(['error' => 'Could Not Log You In!']);
} else {
return redirect()->route('routeName');
}
or did you ask to manually authenticate the user from a controller, here is the solution also
Auth::login($user);
where $user is the login model record of corresponding user

Categories