api versioning page not found

Viewed 206

I'm trying to create my 1st API on Laravel 8, and want to create versioning that would look like this

https://domain/api/v1/users

My user controller looks like this

namespace App\Http\Controllers\Api\V1;
use App\Models\User;
class UserController
{
    public function getUser(int $idUser)
    {
        $user = User::find($idUser);
        
        return new \App\Http\Resources\V1\User($user);
    }
}

in my config/app.php i have this

'api_latest' => '1',

in my middleware (app\Http\Middleware\APIVersion.php)

namespace App\Http\Middleware;
use Closure;

class APIVersion
{
    public function handle($request, Closure $next, $guard)
    {
        config(['app.api.version' => $guard]);
        return $next($request);
    }
}

in my kernal (app/http/kernel.php)

protected $routeMiddleware = [
    // ...
    'api_version' => App\Http\Middleware\APIversion::class,
];

in my /app/Providers/RouteServiceProvider.php

    /** @var string $apiNamespace */
    protected $apiNamespace ='App\Http\Controllers\Api';

protected function mapApiRoutes()
{
    Route::group([
        'middleware' => ['api', 'api_version:v1'],
        'namespace'  => "{$this->apiNamespace}\V1",
        'prefix'     => 'api/v1',
    ], function ($router) {
        require base_path('routes/api_v1.php');
    });    
}

and in my routes/api_v1.php i have this

Route::middleware('api_version')->get('/user', function (Request $request) {
    return $request->user();
});

I'm getting a 404 error when i type this in the browser https://domain/api/v1/users and how do i return a json error instead of a html page for this route?

UPDATE

php artisan route:list gives me this

+--------+----------+------------------------+----------------------+------------------------------------------------------------------------+------------+
| Domain | Method   | URI                    | Name                 | Action
                         | Middleware |
+--------+----------+------------------------+----------------------+------------------------------------------------------------------------+------------+
|        | GET|HEAD | /                      |                      | Closure
   |

|        | GET|HEAD | home                   | home                 | App\Http\Controllers\HomeController@index     
                         | web        |
|        |          |                        |                      |

|        | GET|HEAD | login                  | login                | App\Http\Controllers\Auth\LoginController@showLoginForm                | web        |
|        |          |                        |                      |
                         | guest      |
|        | POST     | login                  |                      | App\Http\Controllers\Auth\LoginController@login                        | web        |
|        |          |                        |                      |
                         | guest      |
|        | POST     | logout                 | logout               | App\Http\Controllers\Auth\LoginController@logout                       | web        |
|        | GET|HEAD | password/confirm       | password.confirm     | App\Http\Controllers\Auth\ConfirmPasswordController@showConfirmForm    | web        |
|        |          |                        |                      |
                         | auth       |
|        | POST     | password/confirm       |                      | App\Http\Controllers\Auth\ConfirmPasswordController@confirm            | web        |
|        |          |                        |                      |
                         | auth       |
|        | POST     | password/email         | password.email       | App\Http\Controllers\Auth\ForgotPasswordController@sendResetLinkEmail  | web        |
|        | GET|HEAD | password/reset         | password.request     | App\Http\Controllers\Auth\ForgotPasswordController@showLinkRequestForm | web        |
|        | POST     | password/reset         | password.update      | App\Http\Controllers\Auth\ResetPasswordController@reset                | web        |
|        | GET|HEAD | password/reset/{token} | password.reset       | App\Http\Controllers\Auth\ResetPasswordController@showResetForm        | web        |
|        | GET|HEAD | register               | register             | App\Http\Controllers\Auth\RegisterController@showRegistrationForm      | web        |
|        |          |                        |                      |                                                                        | guest      |
|        | POST     | register               |                      | App\Http\Controllers\Auth\RegisterController@register                  | web        |
|        |          |                        |                      |                                                                        | guest      |
+--------+----------+------------------------+----------------------+------------------------------------------------------------------------+------------+
1 Answers

ok, do not uses middleware for changes url, only working with the routes, proof with this.

frist you must install passport or sanctum, in my case I have used passport. See the documentation continue with the installation

in app/Providers/RouteServiceProvider.php

/**
 * Define the "api" routes for the application.
 *
 * These routes are typically stateless.
 *
 * @return void
 */
protected function mapApiRoutes()
{
    Route::prefix('api/v1')
         ->middleware(['api'])
         ->namespace($this->namespace)
         ->group(base_path('routes/api/v1/api.php'));
}

In routes/api/v1/api.php

Route::prefix('/user')->group(function (){
  Route::post('/login', [LoginController::class,'login']);
});

In app/Http/Controller/Auth/LoginController

to see the client's IP is like this $request->ip();

public function login(Request $request)
{       
    $loginData = $request->validate([
        'email' => 'email|required',
        'password' => 'required'
    ]);

    if (!\auth()->attempt($loginData)) {
        return response()->json(['message'=>'Datos invalidos de usuarios','success'=>false], 404);
    }

    $accessToken = \auth()->user()->createToken('authToken')->accessToken;

    return response()->json( ['success'=>true,'message'=>'Acceso consedido',
        'user' => \auth()->user(),
        "token_type" => "Bearer",
        "access_token" => $accessToken,
    ],200);
}

In app/Http/Controller/UserController

<?php


namespace App\Http\Controllers\Api\V1;


use App\Http\Controllers\Controller;
use App\Models\User;

class UserController extends Controller
{
    public function getUser()
    {
        $users = User::get();

        return response()->json(['data'=> $users]);
    }
}

In routes/api/v1/api.php

if you look. I have used middleware so only authenticated users can see content.

<?php

use App\Http\Controllers\Api\V1\UserController;
use App\Http\Controllers\Auth\LoginController;

Route::prefix('/user')->group(function (){
    Route::post('/login', [LoginController::class,'login']);
    Route::get('/users',[UserController::class,'getUser'])->middleware('auth:api', 'client');
});

I hope this information helps you.

λ php artisan route:list
+--------+----------+-------------------+------+----------------------------------------------------+------------+
| Domain | Method   | URI               | Name | Action                                             | Middleware |
+--------+----------+-------------------+------+----------------------------------------------------+------------+
|        | GET|HEAD | /                 |      | Closure                                            | web        |
|        | POST     | api/v1/user/login |      | App\Http\Controllers\Auth\LoginController@login    | api        |
|        | GET|HEAD | api/v1/user/users |      | App\Http\Controllers\Api\V1\UserController@getUser | api        |
|        |          |                   |      |                                                    | auth:api   |
|        |          |                   |      |                                                    | client     |
+--------+----------+-------------------+------+----------------------------------------------------+------------+
Related