package com.emonster.taroaichat.web.rest;

import com.emonster.taroaichat.web.rest.vm.PhoneAuthenticationVM;
import com.emonster.taroaichat.service.PhoneAuthenticationService;
import com.emonster.taroaichat.service.dto.PhoneVerificationCheckDTO;
import com.emonster.taroaichat.service.dto.PhoneVerificationStartDTO;
import jakarta.validation.Valid;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.http.HttpHeaders;
import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.*;

import java.util.HashMap;
import java.util.Map;

/**
 * REST controller for phone-based authentication.
 */
@RestController
@RequestMapping("/api/v1")
public class PhoneAuthenticationResource {

    private static final Logger log = LoggerFactory.getLogger(PhoneAuthenticationResource.class);

    private final PhoneAuthenticationService phoneAuthenticationService;

    public PhoneAuthenticationResource(PhoneAuthenticationService phoneAuthenticationService) {
        this.phoneAuthenticationService = phoneAuthenticationService;
    }

    /**
     * {@code POST  /authenticate/phone/start} : Start phone verification process
     *
     * @param startDTO the phone number to verify
     * @return the {@link ResponseEntity} with status {@code 200 (OK)} and success message,
     * or status {@code 400 (Bad Request)} if verification failed
     */
    @PostMapping("/auth/send-verification")
    public ResponseEntity<Map<String, Object>> startPhoneVerification(@Valid @RequestBody PhoneVerificationStartDTO startDTO) {
        log.debug("REST request to start phone verification for: {}", startDTO.getPhoneNumber());

        Map<String, Object> response = new HashMap<>();

        boolean sent = phoneAuthenticationService.sendVerificationCode(startDTO.getPhoneNumber());

        if (sent) {
            response.put("success", true);
            response.put("message", "Verification code sent");
            // Note: Twilio Verify doesn't return verificationSid for security
            return ResponseEntity.ok(response);
        } else {
            response.put("success", false);
            response.put("message", "Failed to send verification code");
            return ResponseEntity.badRequest().body(response);
        }
    }

    /**
     * {@code POST  /authenticate/phone/verify} : Verify phone number and authenticate
     *
     * @param checkDTO the phone number and verification code
     * @return the {@link ResponseEntity} with status {@code 200 (OK)} and JWT tokens in body,
     * or status {@code 401 (Unauthorized)} if verification failed
     */
    @PostMapping("/auth/verify-code")
    public ResponseEntity<Map<String, Object>> verifyPhoneAndAuthenticate(@Valid @RequestBody PhoneVerificationCheckDTO checkDTO) {
        log.debug("REST request to verify phone: {}", checkDTO.getPhoneNumber());

        var result = phoneAuthenticationService.verifyAndAuthenticateWithProfile(
            checkDTO.getPhoneNumber(),
            checkDTO.getCode(),
            checkDTO.isRememberMe()
        );

        if (result.isPresent()) {
            PhoneAuthenticationVM authResult = result.get();
            Map<String, Object> response = new HashMap<>();
            response.put("id_token", authResult.getAccessToken());
            response.put("refresh_token", authResult.getRefreshToken());
            response.put("expires_in", 1800); // 30 minutes default

            // Add user profile info
            Map<String, Object> userProfile = new HashMap<>();
            userProfile.put("id", authResult.getUserProfile().getId());
            userProfile.put("phone", authResult.getUserProfile().getPhone());
            userProfile.put("isNewUser", authResult.isNewUser());
            response.put("userProfile", userProfile);

            HttpHeaders httpHeaders = new HttpHeaders();
            httpHeaders.setBearerAuth(authResult.getAccessToken());
            return new ResponseEntity<>(response, httpHeaders, HttpStatus.OK);
        } else {
            return ResponseEntity.status(HttpStatus.UNAUTHORIZED).build();
        }
    }
}
