package com.hepl.tunefortwo.service.impl;

import java.util.Base64;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Optional;

import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
import org.springframework.security.core.Authentication;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
import org.springframework.stereotype.Service;

import com.hepl.tunefortwo.dto.AuthResponse;
import com.hepl.tunefortwo.dto.LoginRequestDto;
import com.hepl.tunefortwo.entity.Users;
import com.hepl.tunefortwo.repository.AuthRepository;
import com.hepl.tunefortwo.service.AuthService;
import com.hepl.tunefortwo.utils.JwtUtils;

@Service
public class AuthServiceImpl implements AuthService {

    private final AuthRepository authRepository;
	private final BCryptPasswordEncoder passwordEncoder;
	private final JwtUtils jwtUtils;
	
	public AuthServiceImpl(AuthRepository authRepository,BCryptPasswordEncoder passwordEncoder,JwtUtils jwtUtils) {
		this.authRepository = authRepository;
		this.passwordEncoder = passwordEncoder;
		this.jwtUtils = jwtUtils;
	}

	@Override
	public String extractJwtToken(Authentication authentication) {
		
		return authentication.getCredentials().toString();
	}

	@Override
	public String extractRoleIdFromJwt(String jwtToken) {
		 try {
           
           String[] jwtParts = jwtToken.split("\\.");

           
           String encodedPayload = jwtParts[1];
           String payload = new String(Base64.getUrlDecoder().decode(encodedPayload));

           
           return extractRoleIdFromPayload(payload);
       } catch (Exception e) {
           throw new RuntimeException("Error decoding/parsing JWT token: " + e.getMessage());
       }
	}

	@Override
	public String extractRoleIdFromPayload(String payload) {
		 return payload.contains("roleId") ? payload.substring(payload.indexOf("roleId") + 8, payload.indexOf("roleName") - 2) : "-";
	}

	@Override
	public ResponseEntity<?> autheticateUser(LoginRequestDto loginRequestDto) {
	    // Retrieve the user by email from the repository
	    Optional<Users> userOptional = authRepository.findByEmail(loginRequestDto.getEmail().toLowerCase());

	   
	    if (userOptional.isEmpty()) {
	        
	        AuthResponse apiResponse = new AuthResponse(false, "Invalid email or password", null);
	        return ResponseEntity.status(HttpStatus.UNAUTHORIZED).body(apiResponse);
	    }

	    Users user = userOptional.get();

	    
	    boolean isPasswordValid = passwordEncoder.matches(loginRequestDto.getPassword(), user.getPassword());

	    if (!isPasswordValid) {
	       
	        AuthResponse apiResponse = new AuthResponse(false, "Invalid email or password", null);
	        return ResponseEntity.status(HttpStatus.UNAUTHORIZED).body(apiResponse);
	    }

	   
	    Map<String, Object> userDetails = new HashMap<>();
	    for (String privilege : loginRequestDto.getPrivilege()) {
	        switch (privilege) {
	            case "_id":
	                userDetails.put("_id", user.getId());
	                break;
	            case "email":
	                userDetails.put("email", user.getEmail());
	                break;
	            case "mobile":
	                userDetails.put("mobile", user.getMobile());
	                break;
	            case "roleId":
	                userDetails.put("roleId", user.getRoleId());
	                break;
	            case "username":
	                userDetails.put("username", user.getUsername());
	                break;
	            
	            default:
	                
	                break;
	        }
	    }

	    
	    String generatedToken = jwtUtils.generateTokenFromUsernamefromMap(loginRequestDto.getEmail(), userDetails);

	    
	    Map<String, Object> tokenMap = new HashMap<>();
	    tokenMap.put("accessToken", generatedToken);
	    tokenMap.put("userDetails", userDetails);

	   
	    AuthResponse apiResponse = new AuthResponse(true, "Login Successfully", tokenMap);

	    return ResponseEntity.ok(apiResponse);
	}

	@Override
	public ResponseEntity<?> getAllUsers() {
		
		List<Users> allUsers = authRepository.findAll();
		 Map<String, Object> userListMap = new HashMap<>();
		 userListMap.put("users", allUsers);
		 
		 AuthResponse allUserResponse = new AuthResponse(true,"Users Found",userListMap);
		
		return ResponseEntity.ok(allUsers);
	}

   
}
