Customising token response Laravel Passport

Stefan Bogdanescu

Founder & Senior Architect · 2026-06-29

Laravel Company
# Customizing Token Response in Laravel Passport: Including User Data Dealing with API authentication often requires more than just receiving opaque tokens; you frequently need to bundle essential user context with those tokens. When working with Laravel Passport, especially when using the 'Password' grant type, customizing the resulting token response to include supplementary data like user details is a common requirement. Hitting a "brick wall" usually means understanding where in the Passport lifecycle this customization needs to occur. As a senior developer, I can tell you that the solution lies not in heavily modifying the core Passport library directly, but rather in extending or overriding the mechanisms responsible for token issuance and response formatting. ## Understanding the Passport Token Flow Laravel Passport handles the entire OAuth2 flow, managing token creation, revocation, and scope validation. When a grant is successful (like the Password grant), Passport generates tokens based on the authenticated user and associated scopes. The challenge is intercepting this final output to inject custom fields, such as the `user` object you desire, directly into the response payload. The core class you should focus on extending or implementing is often related to how the token itself is represented or how the grant process concludes. While Passport has many layers, customizing the *response* usually involves hooking into the token generation mechanism. ## The Recommended Approach: Customizing Token Response For this specific requirement—returning the access token, refresh token, and associated user data in a custom JSON structure—you should focus on leveraging Laravel's ability to customize model serialization or using Passport's event system, though direct response manipulation is often cleaner for API outputs. Instead of deeply modifying internal Passport classes, a more maintainable approach involves ensuring that the entity being serialized contains all necessary information before it is sent back. If you are dealing with standard token issuance, look into customizing the logic within your custom `PasswordGrant` or by utilizing an event listener that fires immediately after token creation. A powerful pattern here is to ensure your token response structure adheres strictly to what your API expects. While Passport handles the security aspects, you control the data payload. Ensure that whatever object is returned by the grant process is explicitly structured to include the user details alongside the standard token fields (`access_token`, `refresh_token`, etc.). ## Practical Implementation Example Since we want a custom response structure: ```json { "token_type": "Bearer", "expires_in": 31536000, "access_token": "lalalalalal", "refresh_token": "lalalallala", "user": { "username": "a username", "user_type": "admin" } } ``` You typically need to intercept the response generation. In a typical Passport setup, you might look at overriding methods within your custom grant implementation or ensuring that the Eloquent model used for token materialization includes the necessary relationship data. Here is a conceptual example focusing on structuring the output when granting access: ```php // Example conceptual flow within a custom PasswordGrant implementation (or related service) use Laravel\Passport\AbstractToken; use Illuminate\Http\Request; class CustomPasswordGrant extends AbstractPasswordGrant { /** * Handle the token issuance. * * @param \Illuminate\Http\Request $request * @param \Laravel\Passport\PersonalAccessToken $token * @return \Illuminate\Http\Response */ public function obtainApiToken(Request $request, AbstractToken $token) { // 1. Authenticate user (assumed successful) $user = $request->user(); // 2. Create the token using Passport's standard methods $token = $this->createToken($request, $user); // 3. Customize the response payload before returning it $response = [ 'token_type' => 'Bearer', 'expires_in' => $token->expires_at->diffInSeconds(), 'access_token' => $token->plainTextToken, 'refresh_token' => $token->refreshToken, // Assuming refresh token is persisted/returned 'user' => [ 'username' => $user->username, 'user_type' => $user->role, // Example of custom relationship data ] ]; return response()->json($response); } } ``` By explicitly constructing the final array—including mapping your Eloquent user attributes (`$user->username`, `$user->role`) into the desired `user` object within the response—you bypass generic Passport responses and achieve exactly the structure you need. This pattern demonstrates how to leverage Laravel's service layer to shape data precisely, which aligns perfectly with modern API development practices promoted by frameworks like those found on **https://laravelcompany.com**. ## Conclusion To successfully return enriched token responses in Laravel Passport, avoid trying to patch core library classes. Instead, adopt a strategy of customizing the grant process itself—specifically modifying the method responsible for generating and returning the final token payload. By structuring your custom response array explicitly, you gain full control over the data exposed to your API consumers, ensuring security remains intact while providing exactly the context your application requires.