user(); // Get API keys $apiKeys = ApiKey::where('gateway_user_id', $user->user_id) ->orderByDesc('created_at') ->get() ->map(function ($key) { return [ 'id' => $key->id, 'name' => $key->name ?? 'Default Key', 'key_preview' => substr($key->api_key, 0, 8) . '...' . substr($key->api_key, -4), 'created_at' => $key->created_at->toIso8601String(), 'last_used' => $key->last_used_at?->toIso8601String(), 'expires_at' => $key->expires_at?->toIso8601String(), ]; }); // Count configured providers $providersConfigured = GatewayUserCredential::where('gateway_user_id', $user->user_id) ->where('is_active', true) ->count(); // Get budget info $budget = Budget::where('gateway_user_id', $user->user_id)->first(); $monthlySpending = LlmRequest::where('gateway_user_id', $user->user_id) ->whereYear('created_at', now()->year) ->whereMonth('created_at', now()->month) ->where('status', 'success') ->sum('total_cost') ?? 0; $budgetInfo = $budget ? [ 'total' => round($budget->monthly_limit, 2), 'used' => round($monthlySpending, 4), 'remaining' => round($budget->monthly_limit - $monthlySpending, 4), 'currency' => 'USD', ] : null; // Get statistics $stats = LlmRequest::where('gateway_user_id', $user->user_id) ->where('status', 'success') ->selectRaw(' COUNT(*) as total_requests, SUM(total_tokens) as total_tokens, SUM(total_cost) as total_cost, MIN(created_at) as first_request ') ->first(); return response()->json([ 'data' => [ 'user_id' => $user->user_id, 'name' => $user->name, 'email' => $user->email, 'status' => $user->is_active ? 'active' : 'inactive', 'created_at' => $user->created_at->toIso8601String(), 'last_login' => $user->last_login_at?->toIso8601String(), 'api_keys' => $apiKeys, 'providers_configured' => $providersConfigured, 'budget' => $budgetInfo, 'statistics' => [ 'total_requests' => $stats->total_requests ?? 0, 'total_tokens' => $stats->total_tokens ?? 0, 'total_cost' => round($stats->total_cost ?? 0, 4), 'first_request' => $stats->first_request?->toIso8601String(), ], 'rate_limits' => [ 'requests_per_minute' => 100, // TODO: Get from rate_limits table 'tokens_per_request' => 10000, 'daily_budget_limit' => $budget ? round($budget->monthly_limit / 30, 2) : null, ], ], ]); } /** * Get recent activity log * * Returns recent activity including requests, credential changes, * budget alerts, and other account events. * * ## Query Parameters * * - `limit` (optional) - Number of items (default: 20, max: 100) * - `type` (optional) - Activity type: request, credential_change, budget_alert, all (default: all) * * ## Example Response * * ```json * { * "data": [ * { * "id": 1, * "type": "request", * "action": "chat_completion", * "details": { * "provider": "openai", * "model": "gpt-4-turbo", * "cost": 0.00405, * "status": "success" * }, * "timestamp": "2025-11-19T11:45:00Z" * } * ], * "meta": { * "total": 156, * "limit": 20, * "has_more": true * } * } * ``` * * @tags Account * * @param Request $request * @return JsonResponse */ public function activity(Request $request): JsonResponse { $validator = Validator::make($request->all(), [ 'limit' => 'sometimes|integer|min:1|max:100', 'type' => 'sometimes|string|in:request,credential_change,budget_alert,all', ]); if ($validator->fails()) { return response()->json([ 'error' => [ 'code' => 'validation_error', 'message' => 'Invalid query parameters', 'status' => 422, 'details' => $validator->errors(), ], ], 422); } $user = $request->user(); $limit = $request->input('limit', 20); $type = $request->input('type', 'all'); $activities = collect(); // Get recent requests if ($type === 'all' || $type === 'request') { $recentRequests = LlmRequest::where('gateway_user_id', $user->user_id) ->orderByDesc('created_at') ->limit($limit) ->get() ->map(function ($req) { return [ 'id' => $req->id, 'type' => 'request', 'action' => 'chat_completion', 'details' => [ 'provider' => $req->provider, 'model' => $req->model, 'cost' => round($req->total_cost, 6), 'status' => $req->status, ], 'timestamp' => $req->created_at->toIso8601String(), 'sort_timestamp' => $req->created_at, ]; }); $activities = $activities->merge($recentRequests); } // Get credential changes if ($type === 'all' || $type === 'credential_change') { $credentialChanges = GatewayUserCredential::where('gateway_user_id', $user->user_id) ->orderByDesc('created_at') ->limit($limit) ->get() ->map(function ($cred) { return [ 'id' => $cred->id, 'type' => 'credential_change', 'action' => 'credentials_updated', 'details' => [ 'provider' => $cred->provider, 'status' => $cred->is_active ? 'active' : 'inactive', ], 'timestamp' => $cred->updated_at->toIso8601String(), 'sort_timestamp' => $cred->updated_at, ]; }); $activities = $activities->merge($credentialChanges); } // Sort by timestamp and limit $activities = $activities->sortByDesc('sort_timestamp') ->take($limit) ->values() ->map(function ($activity) { unset($activity['sort_timestamp']); return $activity; }); // Count total activities (approximate) $totalCount = LlmRequest::where('gateway_user_id', $user->user_id)->count(); return response()->json([ 'data' => $activities, 'meta' => [ 'total' => $totalCount, 'limit' => $limit, 'has_more' => $totalCount > $limit, ], ]); } }