package library.routes;

import java.sql.SQLException;
import java.util.Optional;

import io.javalin.config.JavalinConfig;
import io.javalin.http.Context;
import io.javalin.http.UnauthorizedResponse;
import library.dto.LoginRequest;
import library.dto.TokenResponse;
import library.service.MemberService;
import library.service.SessionService;

/**
 * POST /login and POST /logout.
 */
public class AuthRoutes {

	private final MemberService members;
	private final SessionService sessions;

	public AuthRoutes(MemberService members, SessionService sessions) {
		this.members = members;
		this.sessions = sessions;
	}

	public void register(JavalinConfig config) {
		config.routes.post("/login", ctx -> login(ctx)); // public (AuthFilter.isPublic)
		config.routes.post("/logout", ctx -> logout(ctx)); // needs a token
	}

	// POST /login { "username": "...", "password": "..." } → 200 { "token": "..." }
	private void login(Context ctx) throws SQLException {
		LoginRequest body = ctx.bodyAsClass(LoginRequest.class);
		Optional<String> token = members.login(body.username(), body.password());
		if (token.isEmpty()) {
			// One message for both failures: don't reveal which usernames exist
			throw new UnauthorizedResponse("Invalid username or password");
		}
		ctx.json(new TokenResponse(token.get()));
	}

	// POST /logout → 204. The filter already checked the token; this deletes its
	// session.
	private void logout(Context ctx) throws SQLException {
		Optional<String> token = Auth.bearerToken(ctx);
		if (token.isPresent()) {
			sessions.end(token.get());
		}
		ctx.status(204);
	}
}
