package com.example.pap_findu;

import android.Manifest;
import android.content.pm.PackageManager;
import android.content.pm.ServiceInfo;
import androidx.core.content.ContextCompat;

import android.app.Notification;
import android.app.NotificationChannel;
import android.app.NotificationManager;
import android.app.Service;
import android.content.Intent;
import android.location.Location;
import android.os.Build;
import android.os.IBinder;
import android.os.Looper;

import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.core.app.NotificationCompat;

import com.google.android.gms.location.FusedLocationProviderClient;
import com.google.android.gms.location.LocationCallback;
import com.google.android.gms.location.LocationRequest;
import com.google.android.gms.location.LocationResult;
import com.google.android.gms.location.LocationServices;
import com.google.android.gms.location.Priority;

// IMPORTAÇÕES ADICIONADAS PARA A AUTENTICAÇÃO AUTOMÁTICA
import com.google.firebase.auth.FirebaseAuth;
import com.google.firebase.auth.FirebaseUser;
import com.google.firebase.database.DatabaseReference;
import com.google.firebase.database.FirebaseDatabase;

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

public class LocationService extends Service {

    private FusedLocationProviderClient fusedLocationClient;
    private LocationCallback locationCallback;
    private DatabaseReference databaseReference;

    @Nullable
    @Override
    public IBinder onBind(Intent intent) {
        return null;
    }

    @Override
    public void onCreate() {
        super.onCreate();

        // Inicializa o cliente de GPS
        fusedLocationClient = LocationServices.getFusedLocationProviderClient(this);

        // =================================================================
        // AUTOMAÇÃO: Vai buscar o ID do Filho que está logado neste telemóvel
        // =================================================================
        FirebaseUser currentUser = FirebaseAuth.getInstance().getCurrentUser();

        if (currentUser != null) {
            String myUid = currentUser.getUid(); // Pega o ID único gerado pelo Firebase

            // Cria a referência da base de dados usando este ID dinâmico
            databaseReference = FirebaseDatabase.getInstance().getReference("users/" + myUid + "/live_location");
        }
    }

    @Override
    public int onStartCommand(Intent intent, int flags, int startId) {
        // 1. Cria o Canal e a Notificação IMEDIATAMENTE
        createNotificationChannel();
        Notification notification = new NotificationCompat.Builder(this, "LocationChannel")
                .setContentTitle("FindU Ativo")
                .setContentText("A monitorizar a localização em tempo real...")
                .setSmallIcon(R.mipmap.ic_launcher)
                .build();

        // 2. ENVOLVER TUDO NUM TRY-CATCH PARA EVITAR CRASHES NO ANDROID 14
        try {
            // O Android Q (API 29) e superior permite/exige especificar o tipo de serviço no código
            if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.Q) {
                startForeground(1, notification, ServiceInfo.FOREGROUND_SERVICE_TYPE_LOCATION);
            } else {
                startForeground(1, notification);
            }

            // 3. Verifica permissão ANTES de ligar o motor de GPS
            if (ContextCompat.checkSelfPermission(this, Manifest.permission.ACCESS_FINE_LOCATION) == PackageManager.PERMISSION_GRANTED) {
                // Se tem permissão, arranca com a recolha de coordenadas!
                requestLocationUpdates();
            } else {
                // Se por acaso a permissão falhou, desliga-se silenciosamente
                stopForeground(true);
                stopSelf();
            }

        } catch (Exception e) {
            // Se o sistema operativo forçar uma paragem (muito comum em emuladores), apanhamos o erro aqui!
            e.printStackTrace();
            stopSelf();
        }

        return START_STICKY;
    }

    @SuppressWarnings("MissingPermission")
    private void requestLocationUpdates() {
        // Configura a frequência do GPS (a cada 10 segundos, só se mover 5 metros)
        LocationRequest locationRequest = new LocationRequest.Builder(Priority.PRIORITY_HIGH_ACCURACY, 10000)
                .setMinUpdateDistanceMeters(5.0f)
                .build();

        locationCallback = new LocationCallback() {
            @Override
            public void onLocationResult(@NonNull LocationResult locationResult) {
                super.onLocationResult(locationResult);
                for (Location location : locationResult.getLocations()) {
                    // Prepara os dados
                    Map<String, Object> locationData = new HashMap<>();
                    locationData.put("latitude", location.getLatitude());
                    locationData.put("longitude", location.getLongitude());
                    locationData.put("last_updated", System.currentTimeMillis());

                    // Verifica se o utilizador não é nulo antes de enviar para o Firebase
                    if (databaseReference != null) {
                        databaseReference.setValue(locationData);
                    }
                }
            }
        };

        // Outro try-catch de segurança para a comunicação com os serviços do Google (GMS)
        try {
            fusedLocationClient.requestLocationUpdates(locationRequest, locationCallback, Looper.getMainLooper());
        } catch (SecurityException e) {
            e.printStackTrace();
        }
    }

    @Override
    public void onDestroy() {
        super.onDestroy();
        // Quando o serviço for desligado, para de usar o GPS para poupar bateria
        if (fusedLocationClient != null && locationCallback != null) {
            fusedLocationClient.removeLocationUpdates(locationCallback);
        }
    }

    // Cria o Canal de Notificação (obrigatório a partir do Android 8.0)
    private void createNotificationChannel() {
        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
            NotificationChannel channel = new NotificationChannel(
                    "LocationChannel",
                    "Monitoramento de Localização",
                    NotificationManager.IMPORTANCE_LOW // Low para não fazer barulho nem vibrar
            );
            NotificationManager manager = getSystemService(NotificationManager.class);
            if (manager != null) {
                manager.createNotificationChannel(channel);
            }
        }
    }
}