<?php

namespace App\Http\Controllers\Api;

use App\Http\Controllers\Controller;
use App\Models\User;
use App\Models\Referral;
use App\Models\Setting;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Cache;
use Illuminate\Support\Facades\Hash;
use Illuminate\Support\Str;

class AuthController extends Controller
{
    private function sendOtp(string $phone, string $otp): bool
    {
        $text = "Welcome to the Magmau powered by SMSINDIAHUB. Your OTP for registration is {$otp}";
        $url = 'http://cloud.smsindiahub.in/api/mt/SendSMS?'
            . 'APIKey=' . env('SMS_API_KEY')
            . '&senderid=' . env('SMS_SENDER_ID', 'SMSHUB')
            . '&channel=Trans'
            . '&DCS=0'
            . '&flashsms=0'
            . '&number=91' . ltrim($phone, '0')
            . '&text=' . urlencode($text);

        try {
            $ch = curl_init($url);
            curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
            curl_setopt($ch, CURLOPT_TIMEOUT, 10);
            $response = curl_exec($ch);
            curl_close($ch);
            $data = json_decode($response, true);
            $success = isset($data['ErrorCode']) && $data['ErrorCode'] === '000';
            if (!$success) \Log::warning('SMS OTP failed: ' . $response);
            return $success;
        } catch (\Exception $e) {
            \Log::warning('SMS OTP failed: ' . $e->getMessage());
            return false;
        }
    }

    private function otpCacheKey(string $phone): string
    {
        return 'otp_' . preg_replace('/\D/', '', $phone);
    }

    // Step 1: Send OTP to phone
    public function sendOtpRequest(Request $request)
    {
        $request->validate([
            'phone' => 'required|string|min:10|max:15',
            'name'  => 'sometimes|string|max:255',
        ]);

        $phone = preg_replace('/\D/', '', $request->phone);
        if (strlen($phone) < 10) {
            return response()->json(['success' => false, 'message' => 'Invalid phone number'], 422);
        }

        $otp = str_pad(random_int(1000, 9999), 4, '0', STR_PAD_LEFT);

        // Store OTP + name for 10 minutes
        Cache::put($this->otpCacheKey($phone), [
            'otp'  => $otp,
            'name' => $request->name,
        ], now()->addMinutes(10));

        $sent = $this->sendOtp($phone, $otp);

        // In non-production, always return success so dev can test
        return response()->json([
            'success' => true,
            'message' => 'OTP sent to ' . $phone,
            // Expose OTP only in local/dev env for easy testing
            'otp'     => app()->environment('local') ? $otp : null,
        ]);
    }

    // Step 2: Verify OTP → register or login
    public function verifyOtp(Request $request)
    {
        $request->validate([
            'phone' => 'required|string',
            'otp'   => 'required|string|size:4',
            'name'  => 'sometimes|string|max:255',
        ]);

        $phone   = preg_replace('/\D/', '', $request->phone);
        $cacheKey = $this->otpCacheKey($phone);
        $cached  = Cache::get($cacheKey);

        if (!$cached) {
            return response()->json(['success' => false, 'message' => 'OTP expired. Please request a new one.'], 410);
        }

        if ($cached['otp'] !== $request->otp) {
            return response()->json(['success' => false, 'message' => 'Invalid OTP. Please try again.'], 422);
        }

        Cache::forget($cacheKey);

        // Find or create user
        $user = User::where('phone', $phone)->first();

        if (!$user) {
            $name = $request->name ?? $cached['name'] ?? 'User';
            $user = User::create([
                'name'             => $name,
                'phone'            => $phone,
                'email'            => null,
                'password'         => Hash::make(Str::random(32)),
                'role'             => 'customer',
                'referral_code'    => strtoupper(Str::random(8)),
                'referred_by'      => $request->referral_code,
                'is_active'        => true,
                'email_verified_at'=> now(), // phone-verified counts as verified
            ]);

            if ($request->referral_code) {
                $referrer = User::where('referral_code', $request->referral_code)->first();
                if ($referrer) {
                    $rewardAmount = (float) Setting::get('referral_reward', 100);
                    Referral::create([
                        'referrer_id'   => $referrer->id,
                        'referred_id'   => $user->id,
                        'reward_amount' => $rewardAmount,
                        'status'        => 'pending',
                    ]);
                }
            }
        }

        if (!$user->is_active) {
            return response()->json(['success' => false, 'message' => 'Account is deactivated'], 403);
        }

        $token = $user->createToken('auth-token')->plainTextToken;

        return response()->json([
            'success'    => true,
            'is_new_user'=> $user->wasRecentlyCreated,
            'data'       => ['user' => $user, 'token' => $token],
            'message'    => $user->wasRecentlyCreated ? 'Account created successfully' : 'Login successful',
        ]);
    }

    public function adminLogin(Request $request)
    {
        $request->validate([
            'email'    => 'required|email',
            'password' => 'required|string',
        ]);

        $user = User::where('email', $request->email)->first();

        if (!$user || !Hash::check($request->password, $user->password)) {
            return response()->json(['success' => false, 'message' => 'Invalid email or password'], 401);
        }

        if ($user->role !== 'admin') {
            return response()->json(['success' => false, 'message' => 'Admin access required'], 403);
        }

        if (!$user->is_active) {
            return response()->json(['success' => false, 'message' => 'Account is deactivated'], 403);
        }

        $token = $user->createToken('admin-token')->plainTextToken;

        return response()->json([
            'success' => true,
            'data'    => ['user' => $user, 'token' => $token],
            'message' => 'Login successful',
        ]);
    }

    public function me(Request $request)
    {
        return response()->json(['success' => true, 'data' => $request->user()]);
    }

    public function logout(Request $request)
    {
        $request->user()->currentAccessToken()->delete();
        return response()->json(['success' => true, 'message' => 'Logged out']);
    }

    public function updateProfile(Request $request)
    {
        $request->validate([
            'name'  => 'sometimes|string|max:255',
            'email' => 'sometimes|email|unique:users,email,' . $request->user()->id,
        ]);

        $user = $request->user();
        $user->update($request->only(['name', 'email']));

        return response()->json(['success' => true, 'data' => $user]);
    }
}
