package com.estateunified.panel import io.ktor.http.HttpStatusCode import io.ktor.server.application.ApplicationCall import io.ktor.server.response.respondText import io.ktor.http.ContentType internal data class AuthContext( val user: UserDto?, val token: String?, ) internal fun ApplicationCall.bearerToken(): String? { val raw = request.headers["Authorization"] ?: request.headers["X-Auth-Token"] ?: request.queryParameters["token"] ?: return null val trimmed = raw.trim() return if (trimmed.startsWith("Bearer ", ignoreCase = true)) { trimmed.substring(7).trim() } else { trimmed } } internal fun ApplicationCall.authContext(users: UserStore): AuthContext { val token = bearerToken() val user = users.userByToken(token) return AuthContext(user = user, token = token) } internal suspend fun ApplicationCall.unauthorized() { respondText( "{\"error\":\"unauthorized\"}", ContentType.Application.Json, HttpStatusCode.Unauthorized, ) } internal suspend fun ApplicationCall.forbidden(reason: String = "forbidden") { respondText( "{\"error\":\"$reason\"}", ContentType.Application.Json, HttpStatusCode.Forbidden, ) } internal suspend fun ApplicationCall.badRequest(reason: String = "bad_request") { respondText( "{\"error\":\"$reason\"}", ContentType.Application.Json, HttpStatusCode.BadRequest, ) } internal suspend fun ApplicationCall.notFound() { respondText( "{\"error\":\"not_found\"}", ContentType.Application.Json, HttpStatusCode.NotFound, ) } internal val ROLES_ALL = setOf("AGENT", "AGENCY_LEAD", "DEVELOPER", "MODERATOR", "INVESTOR") internal fun userHasAnyRole( user: UserDto?, roles: Set, ): Boolean { if (user == null) return false return user.role in roles }