package com.rngooglefreesignin;

import android.app.Activity;
import android.util.Log;

import androidx.credentials.CredentialManager;
import androidx.credentials.CredentialManagerCallback;
import androidx.credentials.GetCredentialRequest;
import androidx.credentials.GetCredentialResponse;
import androidx.credentials.exceptions.GetCredentialException;

import com.facebook.react.bridge.Arguments;
import com.facebook.react.bridge.Promise;
import com.facebook.react.bridge.ReactApplicationContext;
import com.facebook.react.bridge.ReactContextBaseJavaModule;
import com.facebook.react.bridge.ReactMethod;
import com.facebook.react.bridge.WritableMap;

import com.google.android.libraries.identity.googleid.GetGoogleIdOption;
import com.google.android.libraries.identity.googleid.GoogleIdTokenCredential;

import java.util.concurrent.Executor;
import java.util.concurrent.Executors;

public class GoogleSignInModule extends ReactContextBaseJavaModule {

    private static final String TAG = "GoogleSignInModule";
    
    private CredentialManager credentialManager;
    private String webClientId;
    private final Executor executor = Executors.newSingleThreadExecutor();

    public GoogleSignInModule(ReactApplicationContext context) {
        super(context);
        credentialManager = CredentialManager.create(context);
    }

    @Override
    public String getName() {
        return "GoogleSignInModule";
    }

    @ReactMethod
    public void configure(String webClientId, Promise promise) {
        try {
            this.webClientId = webClientId;
            promise.resolve(null);
        } catch (Exception e) {
            Log.e(TAG, "Error configuring Google Sign In", e);
            promise.reject("CONFIGURE_ERROR", "Failed to configure Google Sign In", e);
        }
    }

    @ReactMethod
    public void signIn(Promise promise) {
        if (webClientId == null) {
            promise.reject("NOT_CONFIGURED", "Google Sign In not configured");
            return;
        }

        Activity currentActivity = getCurrentActivity();
        if (currentActivity == null) {
            promise.reject("NO_ACTIVITY", "Current activity is null");
            return;
        }

        try {
            GetGoogleIdOption googleIdOption = new GetGoogleIdOption.Builder()
                    .setServerClientId(webClientId)
                    .setAutoSelectEnabled(true)
                    .build();

            GetCredentialRequest request = new GetCredentialRequest.Builder()
                    .addCredentialOption(googleIdOption)
                    .build();

            credentialManager.getCredentialAsync(
                    currentActivity,
                    request,
                    null,
                    executor,
                    new CredentialManagerCallback<GetCredentialResponse, GetCredentialException>() {
                        @Override
                        public void onResult(GetCredentialResponse result) {
                            try {
                                GoogleIdTokenCredential googleIdTokenCredential = 
                                    GoogleIdTokenCredential.createFrom(result.getCredential().getData());
                                
                                WritableMap userMap = Arguments.createMap();
                                userMap.putString("id", googleIdTokenCredential.getId());
                                userMap.putString("name", googleIdTokenCredential.getDisplayName());
                                userMap.putString("email", googleIdTokenCredential.getId());
                                userMap.putString("photo", googleIdTokenCredential.getProfilePictureUri() != null 
                                    ? googleIdTokenCredential.getProfilePictureUri().toString() : null);
                                userMap.putString("idToken", googleIdTokenCredential.getIdToken());
                                
                                promise.resolve(userMap);
                            } catch (Exception e) {
                                Log.e(TAG, "Error parsing Google ID token", e);
                                promise.reject("PARSE_ERROR", "Failed to parse Google ID token", e);
                            }
                        }

                        @Override
                        public void onError(GetCredentialException e) {
                            Log.e(TAG, "Get credential failed", e);
                            
                            String errorCode = "UNKNOWN_ERROR";
                            String message = e.getMessage();
                            
                            if (message != null) {
                                if (message.contains("16")) {
                                    errorCode = "SIGN_IN_CANCELLED";
                                } else if (message.contains("network")) {
                                    errorCode = "NETWORK_ERROR";
                                }
                            }
                            
                            promise.reject(errorCode, "Google Sign In failed: " + message, e);
                        }
                    }
            );
        } catch (Exception e) {
            Log.e(TAG, "Error starting sign in", e);
            promise.reject("SIGN_IN_ERROR", "Failed to start sign in", e);
        }
    }

    @ReactMethod
    public void signOut(Promise promise) {
        // Google Identity Services doesn't have a signOut method
        // The sign out is handled by clearing local credentials
        promise.resolve(null);
    }

    @ReactMethod
    public void revokeAccess(Promise promise) {
        // Google Identity Services doesn't have a revokeAccess method
        // This needs to be handled on the server side
        promise.resolve(null);
    }

    @ReactMethod
    public void getCurrentUser(Promise promise) {
        // Google Identity Services doesn't store user state locally
        // Always return null to force a new sign in
        promise.resolve(null);
    }
}