You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

请求指导基于Laravel开发POST型PHP认证API(返回JSON)

如何用Laravel开发支持密码/SSO双认证的POST JSON API

没问题,我来一步步教你实现这个需求——用Laravel框架开发一个基于POST请求的API,支持邮箱+密码和SSO token两种验证方式,并且返回你指定格式的JSON响应。

1. 前期准备:模型与迁移

首先确保你已经创建了Laravel项目(如果没有,用composer create-project laravel/laravel auth-api快速生成)。我们需要调整用户表的字段,匹配你的需求:

创建用户表迁移(如果是新项目,修改默认的users迁移)

打开database/migrations/xxxx_xx_xx_xxxxxx_create_users_table.php,修改up()方法:

public function up()
{
    Schema::create('users', function (Blueprint $table) {
        $table->id();
        $table->string('email_address')->unique(); // 用email_address代替默认email
        $table->string('password')->nullable(); // SSO用户可能不需要密码,设为nullable
        $table->timestamp('last_login')->nullable();
        $table->timestamps();
    });
}

然后运行迁移:php artisan migrate

配置User模型

打开app/Models/User.php,更新$fillable和认证字段:

namespace App\Models;

use Illuminate\Foundation\Auth\User as Authenticatable;
use Illuminate\Notifications\Notifiable;

class User extends Authenticatable
{
    use Notifiable;

    // 允许批量赋值的字段
    protected $fillable = [
        'email_address',
        'password',
        'last_login',
    ];

    // 指定认证用的邮箱字段(默认是email,这里改成email_address)
    public function getAuthIdentifierName()
    {
        return 'email_address';
    }

    // 隐藏敏感字段(比如密码哈希)
    protected $hidden = [
        'password',
        'remember_token',
    ];
}

2. 配置API路由

打开routes/api.php,添加POST登录路由:

use App\Http\Controllers\AuthController;

Route::post('/auth/login', [AuthController::class, 'login'])->name('api.auth.login');

因为API接口不需要CSRF保护,所以需要在app/Http/Middleware/VerifyCsrfToken.php里排除这个路由:

protected $except = [
    '/api/auth/login',
];

3. 创建认证控制器AuthController

运行命令生成控制器:php artisan make:controller AuthController

然后打开app/Http/Controllers/AuthController.php,编写核心逻辑:

namespace App\Http\Controllers;

use App\Models\User;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
use Carbon\Carbon;

class AuthController extends Controller
{
    public function login(Request $request)
    {
        // 验证请求参数
        $request->validate([
            'email_address' => 'required|email',
            // 密码和token二选一
            'password' => 'required_without:token',
            'token' => 'required_without:password',
        ]);

        $timestamp = Carbon::now()->timestamp;
        $sessionExpires = $timestamp + 3600; // 会话1小时后过期,可按需调整

        // 情况1:密码认证
        if ($request->has('password')) {
            // 验证邮箱和密码
            if (Auth::attempt([
                'email_address' => $request->email_address,
                'password' => $request->password
            ])) {
                $user = Auth::user();
                // 更新最后登录时间
                $user->update(['last_login' => Carbon::now()]);

                return response()->json([
                    'data' => [
                        [
                            'id' => $user->id,
                            'email_address' => $user->email_address,
                            'authenticated' => true,
                            'type' => 'password',
                            'timestamp' => $timestamp,
                            'last_login' => $user->last_login->timestamp,
                            'session_expires' => $sessionExpires
                        ]
                    ]
                ], 200);
            }
        }

        // 情况2:SSO Token认证
        if ($request->has('token')) {
            // 这里需要根据你的SSO逻辑验证token,比如从缓存/数据库查询关联的用户
            // 示例:假设token存储在users表的sso_token字段(你可以根据实际调整)
            $user = User::where('sso_token', $request->token)->first();

            if ($user) {
                // 更新最后登录时间
                $user->update(['last_login' => Carbon::now()]);

                return response()->json([
                    'data' => [
                        [
                            'id' => $user->id,
                            'email_address' => $user->email_address,
                            'authenticated' => true,
                            'type' => 'sso',
                            'timestamp' => $timestamp,
                            'last_login' => $user->last_login->timestamp,
                            'session_expires' => $sessionExpires
                        ]
                    ]
                ], 200);
            }
        }

        // 认证失败返回401
        return response()->json([
            'error' => 'Invalid credentials or token'
        ], 401);
    }
}

4. 测试API

你可以用Postman、curl或者其他API工具测试:

密码认证请求

  • 请求方法:POST
  • URL:http://your-domain/api/auth/login
  • 请求体(JSON):
{
    "email_address": "test@gmail.com",
    "password": "your-password"
}

成功响应会和你给出的示例完全一致。

SSO认证请求

  • 请求方法:POST
  • URL:http://your-domain/api/auth/login
  • 请求体(JSON):
{
    "email_address": "test@gmail.com",
    "token": "your-sso-token"
}

成功响应格式和密码认证类似,仅type字段为sso。

注意事项

  • SSO Token验证逻辑:上面的示例只是基础实现,你需要根据实际的SSO系统调整(比如调用SSO服务的验证接口,或者从缓存中读取token关联的用户)。
  • 密码哈希:创建用户时记得用Hash::make($password)加密密码,不然Auth::attempt会验证失败。
  • 会话过期:session_expires的时间可以根据你的业务需求调整,比如设置为24小时(86400秒)。
  • 错误处理:可以根据不同的失败原因返回更具体的错误信息(比如"Password incorrect"或"Invalid SSO token")。

内容的提问来源于stack exchange,提问作者CodingFlow

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.26 09:18:36