import type { HttpContext } from '@adonisjs/core/http' import { registerValidator, loginValidator } from '#validators/auth' import User from '#models/user' import logger from '@adonisjs/core/services/logger' export default class AuthController { /** * Registers a user using the provided email, password, and full name. * * @bodyParam *email* - string | The email of the user. * @bodyParam *password* - string | The password of the user. * @bodyParam *fullName* - string | The full name of the user. * @returns The user access token. */ async register({ request }: HttpContext) { try { const data = await request.validateUsing(registerValidator) const user = await User.create(data) logger.info('User registered: %s, %s, %s', user.fullName, user.email, request.ip()) return User.accessTokens.create(user) } catch (error) { logger.error('Registration failed: %s', error) throw error } } /** * Log in a user using the provided email and password. * * @bodyParam *email* - string | The email of the user. * @bodyParam *password* - string | The password of the user. * @returns The access token of the user. */ async login({ request }: HttpContext) { try { const { email, password } = await request.validateUsing(loginValidator) const user = await User.verifyCredentials(email, password) logger.info('User logged in: %s', email) return User.accessTokens.create(user) } catch (error) { logger.error('Login failed: %s', error) throw error } } /** * Deletes the user's access token and logs them out. If the user is not * authenticated, returns an unauthorized message. */ async logout({ auth }: HttpContext) { const user = auth.user! logger.info('User logout: %s', auth.getUserOrFail().email) try { await User.accessTokens.delete(user, user.currentAccessToken.identifier) return { message: 'User logged out' } } catch (error) { logger.error('Logout failed: %s', error) throw error } } /** * Retrieves the authenticated user's information if authenticated, * otherwise deletes the access token and returns an unauthorized message. * * @param auth - The HTTP context's auth object. * @returns An object containing the user data if authenticated, * otherwise an unauthorized message. */ async me({ auth }: HttpContext) { if (await auth.check()) { return { user: auth.user } } else { await User.accessTokens.delete(auth.user!, auth.user!.currentAccessToken.identifier) return { message: 'Unauthorized' } } } }