API Security

XinAdmin builds a complete API security system through middleware chains, annotation routing, request validation, and exception handling.

Route Middleware

All protected API routes use triple middleware:

// Standard protected route
Route::get('/system/user', [SysUserController::class, 'index'])
    ->middleware(['auth:sanctum', 'authGuard', 'abilities:system.user.query']);
MiddlewareTypePurpose
auth:sanctumLaravel SanctumValidates Bearer Token
authGuardCustomVerifies token type matches (prevents cross-model token abuse)
abilities:{key}Laravel SanctumVerifies the token's ability list includes the specified permission

AnnoRoute Annotation Routing

XinAdmin provides an AnnoRoute annotation routing system that auto-registers routes and permission middleware via PHP 8 attributes, avoiding manual route definition and middleware configuration:

#[RequestAttribute('/system/user', 'system.user')]
class SysUserController
{
    #[GetRoute(authorize: 'query')]
    public function index() { ... }  // Auto-applies abilities:system.user.query

    #[PostRoute(authorize: 'create')]
    public function store() { ... }  // Auto-applies abilities:system.user.create

    #[PutRoute(authorize: 'update')]
    public function update() { ... } // Auto-applies abilities:system.user.update

    #[DeleteRoute(authorize: 'delete')]
    public function destroy() { ... } // Auto-applies abilities:system.user.delete
}

Annotation Parameters

AttributeParametersDescription
RequestAttributeprefix, abilitiesPrefixRoute prefix + permission key prefix
GetRouteauthorize, uriGET route, auto-constructs permission key
PostRouteauthorize, uriPOST route
PutRouteauthorize, uriPUT route
DeleteRouteauthorize, uriDELETE route

RouteRegisterService scans all annotated controllers on boot, automatically calling Laravel route registration with ['auth:sanctum', 'authGuard', 'abilities:{prefix}.{authorize}'] middleware attached.

Unauthorized Access Handling

When a user's token lacks the required permission, ExceptionsHandler catches MissingAbilityException and returns:

{
  "success": false,
  "showType": 2,
  "msg": "No Permission"
}

Other security-related exception handling:

ExceptionMessageHTTP Status
AuthenticationExceptionPlease log in first401
MissingAbilityExceptionNo Permission403
NotFoundHttpExceptionRoute does not exist404
ValidationExceptionFirst validation error message422

CORS Security

Global CORS middleware AllowCrossDomainMiddleware:

Access-Control-Allow-Origin: *
Access-Control-Allow-Methods: GET, POST, PUT, DELETE, OPTIONS
Access-Control-Allow-Headers: Content-Type, Authorization, X-Requested-With, User-Language
Access-Control-Allow-Credentials: true
Access-Control-Max-Age: 1800

OPTIONS preflight requests receive a 204 status code. CORS headers are also duplicated in the exception handler as a safety net.

Request Validation

All form requests extend BaseFormRequest, providing unified validation rules:

ValidatorDescription
SysUserFormRequestUser create/edit validation (username, email, password format)
SysRoleFormRequestRole validation (name required)
SysRuleFormRequestPermission rule validation (type, key uniqueness, parent existence)

Validation failure response:

{
  "success": false,
  "showType": 1,
  "msg": "First validation error message"
}

Adding a Protected API Endpoint

Steps to add a new protected endpoint to the system:

1. Add a permission rule record

Insert a new record in sys_rule with type=rule and the corresponding permission key, e.g., my.module.action.

2. Define the route with middleware

Route::post('/my-module/action', [MyController::class, 'action'])
    ->middleware(['auth:sanctum', 'authGuard', 'abilities:my.module.action']);

3. Add frontend permission control

<AuthButton auth="my.module.action">
  <Button>Action</Button>
</AuthButton>

Production Security Recommendations

RecommendationDescription
Disable debug modeSet APP_DEBUG=false in .env to prevent stack trace leakage
Enable HTTPSPrevent token interception during transmission
Restrict CORSSet Access-Control-Allow-Origin to specific domains instead of * in production
Strengthen password policyIncrease password complexity requirements in SysUserFormRequest
Rate limitingAdd Laravel Rate Limiting middleware for sensitive endpoints like login
Session securityhttp_only=true and same_site=lax are already enabled in session config