package library.service;

import java.security.SecureRandom;
import java.sql.SQLException;
import java.time.Duration;
import java.time.LocalDateTime;
import java.util.Base64;
import java.util.Optional;

import library.dao.SessionDao;
import library.domain.Member;

/**
 * Session tokens stored in SESSIONS.
 */
public class SessionService {

	private static final SecureRandom RANDOM = new SecureRandom(); // not Random: tokens must be unguessable
	private static final Duration SESSION_LENGTH = Duration.ofHours(8);

	private final SessionDao sessionDao;

	public SessionService(SessionDao sessionDao) {
		this.sessionDao = sessionDao;
	}

	// Login: a new random token for this member
	public String start(Member m) throws SQLException {
		byte[] bytes = new byte[32];
		RANDOM.nextBytes(bytes);
		String token = Base64.getUrlEncoder().withoutPadding().encodeToString(bytes);
		sessionDao.insert(token, m.memberId(), LocalDateTime.now().plus(SESSION_LENGTH));
		return token;
	}

	// Every request (AuthFilter): who does this token belong to?
	public Optional<Member> memberForToken(String token) throws SQLException {
		return sessionDao.findMember(token); // JOIN MEMBERS, only if not expired
	}

	// Logout
	public void end(String token) throws SQLException {
		sessionDao.delete(token);
	}
}
