<?php

namespace App\Http\Controllers\User;

use App\Http\Controllers\Controller;
use App\Services\CryptoService;
use Illuminate\Http\Request;
use App\Models\CryptoAsset;
use App\Models\User;
use App\Models\Transaction;
use App\Models\Notification;
use App\Mail\TransactionEmail;
use Illuminate\Support\Facades\Mail;
use Illuminate\Http\RedirectResponse;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\DB;

class SendController extends Controller
{
    private $cryptoService;

    public function __construct(CryptoService $cryptoService)
    {
        $this->cryptoService = $cryptoService;
    }

    private function formatAsset(
        $symbol,
        $name,
        $coinId,
        $balance,
        $network = null,
        $networkSymbol = null
    ) {
        $prices = $this->cryptoService->getPrices();
        $price = $prices[$coinId]["usd"] ?? 0;
        $change = $prices[$coinId]["usd_24h_change"] ?? 0;

        $asset = [
            "symbol" => $symbol,
            "name" => $name . ($network ? " ($network)" : ""),
            "balance" => $balance,
            "value" => $balance * $price,
            "price" => $price,
            "change" =>
            $change < 0
                ? number_format($change, 2)
                : "+" . number_format($change, 2),
            "icon_url" => $this->cryptoService->getIconUrl($coinId),
            "network" => $network,
        ];

        if ($networkSymbol) {
            $asset["network_url"] = $this->cryptoService->getIconUrl(
                $networkSymbol
            );
        }

        return $asset;
    }

    private function mapCryptoAssets(CryptoAsset $cryptoAsset)
    {
        $assets = [];

        // Bitcoin
        if ($cryptoAsset->btc_status) {
            $assets[] = $this->formatAsset(
                "BTC",
                "Bitcoin",
                "bitcoin",
                $cryptoAsset->btc_balance
            );
        }

        // USDT with different networks
        $usdtNetworks = [
            "trc20" => [
                "status" => "usdt_trc20_status",
                "balance" => "usdt_trc20_balance",
                "network" => "TRC20",
                "symbol" => "tron",
            ],
            "bep20" => [
                "status" => "usdt_bep20_status",
                "balance" => "usdt_bep20_balance",
                "network" => "BNB",
                "symbol" => "binancecoin",
            ],
            "erc20" => [
                "status" => "usdt_erc20_status",
                "balance" => "usdt_erc20_balance",
                "network" => "ERC20",
                "symbol" => "ethereum",
            ],
        ];

        foreach ($usdtNetworks as $network => $config) {
            if ($cryptoAsset->{$config["status"]}) {
                $assets[] = $this->formatAsset(
                    "USDT",
                    "Tether",
                    "tether",
                    $cryptoAsset->{$config["balance"]},
                    $config["network"],
                    $config["symbol"]
                );
            }
        }

        // Other cryptocurrencies mapping
        $cryptoMapping = [
            "eth" => [
                "symbol" => "ETH",
                "name" => "Ethereum",
                "id" => "ethereum",
            ],
            "trx" => ["symbol" => "TRX", "name" => "Tron", "id" => "tron"],
            "bnb" => [
                "symbol" => "BNB",
                "name" => "Binance Coin",
                "id" => "binancecoin",
            ],
            "dot" => [
                "symbol" => "DOT",
                "name" => "Polkadot",
                "id" => "polkadot",
            ],
            "bch" => [
                "symbol" => "BCH",
                "name" => "Bitcoin Cash",
                "id" => "bitcoin-cash",
            ],
            "ltc" => [
                "symbol" => "LTC",
                "name" => "Litecoin",
                "id" => "litecoin",
            ],
            "xlm" => [
                "symbol" => "XLM",
                "name" => "Stellar",
                "id" => "stellar",
            ],
            "dash" => ["symbol" => "DASH", "name" => "Dash", "id" => "dash"],
            "sol" => ["symbol" => "SOL", "name" => "Solana", "id" => "solana"],
        ];

        foreach ($cryptoMapping as $key => $crypto) {
            $statusField = "{$key}_status";
            $balanceField = "{$key}_balance";

            if ($cryptoAsset->$statusField) {
                $assets[] = $this->formatAsset(
                    $crypto["symbol"],
                    $crypto["name"],
                    $crypto["id"],
                    $cryptoAsset->$balanceField
                );
            }
        }

        return $assets;
    }

    public function payidAssets()
    {
        $user = Auth::user();
        $cryptoAsset = CryptoAsset::where("user_id", $user->id)->first();

        if (!$cryptoAsset) {
            return redirect()
                ->route("dashboard")
                ->with("error", "No crypto assets found");
        }

        return view("user.send.assets-payid", [
            "assets" => $this->mapCryptoAssets($cryptoAsset),
        ]);
    }

    public function externalAssets()
    {
        $user = Auth::user();
        $cryptoAsset = CryptoAsset::where("user_id", $user->id)->first();

        if (!$cryptoAsset) {
            return redirect()
                ->route("dashboard")
                ->with("error", "No crypto assets found");
        }

        return view("user.send.assets-external", [
            "assets" => $this->mapCryptoAssets($cryptoAsset),
        ]);
    }

    public function payidDetails($symbol, $network = "native")
    {
        $user = Auth::user();
        $cryptoAsset = CryptoAsset::where("user_id", $user->id)->first();

        if ($user->require_kyc && $user->kyc_status !== 'approved') {
            return redirect()
                ->route('kyc')
                ->with('error', 'Please verify your KYC to send crypto');
        }

        if (!$cryptoAsset) {
            return redirect()
                ->route("dashboard")
                ->with("error", "No crypto assets found");
        }

        if ($network === "BNB") {
            $network = "BEP20";
        }

        $asset = $this->getAssetDetails($cryptoAsset, $symbol, $network);

        if (!$asset) {
            return redirect()
                ->route("dashboard")
                ->with("error", "Asset not found");
        }

        // Get the fee field name based on symbol and network
        $feeField = $this->getBalanceField($symbol, $network);
        $feeField = str_replace('balance', 'fee', $feeField);

        // Add fee to asset array
        $asset['fee'] = $cryptoAsset->$feeField ?? 0;

        return view("user.send.payid-details", [
            "asset" => $asset,
        ]);
    }

    public function externalDetails($symbol, $network = "native")
    {
        $user = Auth::user();
        $cryptoAsset = CryptoAsset::where("user_id", $user->id)->first();

        if ($user->require_kyc && $user->kyc_status !== 'approved') {
            return redirect()
                ->route('kyc')
                ->with('error', 'Please verify your KYC to send crypto');
        }

        if (!$cryptoAsset) {
            return redirect()
                ->route("dashboard")
                ->with("error", "No crypto assets found");
        }

        if ($network === "BNB") {
            $network = "BEP20";
        }

        $asset = $this->getAssetDetails($cryptoAsset, $symbol, $network, true);

        if (!$asset) {
            return redirect()
                ->route("dashboard")
                ->with("error", "Asset not found");
        }

        // Add network fee to asset array for external transfers
        $asset['fee'] = $this->getNetworkFee($symbol, $network);

        return view("user.send.external-details", [
            "asset" => $asset,
        ]);
    }


    public function success(
        Request $request,
        $symbol,
        $network = "native",
        $transactionId
    ) {
        // Verify the transaction belongs to the authenticated user
        $transaction = Transaction::where('id', $transactionId)
            ->where('user_id', Auth::id())
            ->firstOrFail();

        return view("user.send.payid-success", [
            "transaction" => $transaction,
            "symbol" => $symbol,
            "network" => $network,
        ]);
    }

    public function failed(Request $request, $symbol, $network = "native")
    {
        $error = session('error', 'Transaction failed');
        $errorCode = session('error_code', 'UNKNOWN_ERROR');
        $amount = session('amount', 0);

        return view("user.send.external-failed", [
            "symbol" => $symbol,
            "network" => $network,
            "error" => $error,
            "error_code" => $errorCode,
            "amount" => $amount,
            "available_balance" => session('available_balance', 0)
        ]);
    }

    public function verifyPayId(Request $request)
    {
        $request->validate([
            "payid" => "required|string",
        ]);

        $uuid = $request->payid;

        $recipient = User::where("uuid", $uuid)->first();

        if (!$recipient) {
            return response()->json([
                "success" => false,
                "message" => "PayID not found",
            ]);
        }

        return response()->json([
            "success" => true,
            "user" => [
                "name" => $recipient->name,
                "uuid" => $recipient->uuid,
            ],
        ]);
    }

    public function processPayId(Request $request, $symbol, $network = 'native')
    {
        $validated = $request->validate([
            "payid" => "required|string",
            "amount" => "required|numeric|min:0",
        ]);


        DB::beginTransaction();
        try {
            $sender = Auth::user();
            $uuid = $request->payid;
            $recipient = User::where("uuid", $uuid)->first();

            if (!$sender->enable_crypto_sending) {
                DB::rollBack();
                return redirect()->route('send.payid.details', [
                    'symbol' => $symbol,
                    'network' => $network
                ])->with([
                    'error' => 'Crypto sending is currently disabled. Please make a transaction to enable sending or contact support.',
                    'error_code' => 'SENDING_DISABLED',
                    'amount' => $request->amount
                ]);
            }

            if (!$recipient) {
                DB::rollBack();
                return redirect()->route('send.payid.details', [
                    'symbol' => $symbol,
                    'network' => $network
                ])->with([
                    'error' => 'PayID not found',
                    'error_code' => 'RECIPIENT_NOT_FOUND',
                    'amount' => $request->amount
                ]);
            }

            if ($sender->uuid === $uuid) {
                DB::rollBack();
                return redirect()->route('send.payid.details', [
                    'symbol' => $symbol,
                    'network' => $network
                ])->with([
                    'error' => 'Cannot send to yourself',
                    'error_code' => 'SELF_TRANSFER',
                    'amount' => $request->amount
                ]);
            }

            // Get crypto assets
            $senderAsset = CryptoAsset::where("user_id", $sender->id)->first();
            $recipientAsset = CryptoAsset::where("user_id", $recipient->id)->first();

            // Determine balance field
            $balanceField = $this->getBalanceField($symbol, $network);

            // Check sender balance
            if ($senderAsset->$balanceField < $request->amount) {
                DB::rollBack();
                return redirect()->route('send.payid.details', [
                    'symbol' => $symbol,
                    'network' => $network
                ])->with([
                    'error' => 'Insufficient balance',
                    'error_code' => 'INSUFFICIENT_FUNDS',
                    'amount' => $request->amount,
                    'available_balance' => $senderAsset->$balanceField
                ]);
            }

            // Process transfer
            $senderAsset->$balanceField -= $request->amount;
            $recipientAsset->$balanceField += $request->amount;

            $senderAsset->save();
            $recipientAsset->save();

            // Create transaction records
            $which_crypto = strtolower($symbol);
            if ($network !== "native") {
                $which_crypto .= "_" . strtolower($network);
            }

            // Create sender's transaction
            $transaction = Transaction::create([
                "user_id" => $sender->id,
                "cryptoasset_id" => $senderAsset->id,
                "type" => "withdrawal",
                "which_crypto" => $which_crypto,
                "amount_out" => $request->amount,
                "status" => Transaction::STATUS_COMPLETED,
                "metadata" => [
                    "recipient_id" => $recipient->id,
                    "recipient_name" => $recipient->name,
                    "recipient_payid" => $request->payid,
                    "network_fee" => 0,
                ],
                "processed_at" => now(),
            ]);

            // Create recipient's transaction
            $recipientTransaction = Transaction::create([
                "user_id" => $recipient->id,
                "cryptoasset_id" => $recipientAsset->id,
                "type" => "deposit",
                "which_crypto" => $which_crypto,
                "amount_in" => $request->amount,
                "status" => Transaction::STATUS_COMPLETED,
                "metadata" => [
                    "sender_id" => $sender->id,
                    "sender_name" => $sender->name,
                    "sender_payid" => $sender->uuid,
                ],
                "processed_at" => now(),
            ]);

            // Create notifications for sender and recipient
            Notification::create([
                'user_id' => $sender->id,
                'type' => 'send_crypto',
                'title' => 'Crypto Sent',
                'message' => sprintf(
                    'You sent %s %s to %s',
                    number_format($request->amount, 4),
                    strtoupper($which_crypto),
                    $recipient->name
                ),
                'is_read' => false,
                'extra_data' => json_encode([
                    'transaction_id' => $transaction->id,
                    'amount' => $request->amount,
                    'crypto' => $which_crypto,
                    'recipient_id' => $recipient->id
                ])
            ]);

            Notification::create([
                'user_id' => $recipient->id,
                'type' => 'receive_crypto',
                'title' => 'Crypto Received',
                'message' => sprintf(
                    'You received %s %s from %s',
                    number_format($request->amount, 4),
                    strtoupper($which_crypto),
                    $sender->name
                ),
                'is_read' => false,
                'extra_data' => json_encode([
                    'transaction_id' => $recipientTransaction->id,
                    'amount' => $request->amount,
                    'crypto' => $which_crypto,
                    'sender_id' => $sender->id
                ])
            ]);

            Mail::to($sender->email)->queue(new TransactionEmail($transaction));
            Mail::to($recipient->email)->queue(new TransactionEmail($recipientTransaction));

            DB::commit();

            return redirect()->route('send.payid.success', [
                'symbol' => $symbol,
                'network' => $network,
                'transaction' => $transaction->id
            ])->with('success', 'Transaction completed successfully');
        } catch (\Exception $e) {
            DB::rollBack();
            \Log::error("PayID transfer failed: " . $e->getMessage());

            return redirect()->route('send.payid.details', [
                'symbol' => $symbol,
                'network' => $network
            ])->with([
                'error' => 'Transaction failed. Please try again.',
                'error_code' => 'TRANSACTION_FAILED',
                'amount' => $request->amount
            ]);
        }
    }

    /**
     * Verify External Address
     */
    public function verifyExternal(Request $request)
    {
        $request->validate([
            'address' => 'required|string',
            'symbol' => 'required|string',
            'network' => 'nullable|string'
        ]);

        // Get the address, symbol, and network from the request
        $address = $request->address;
        $symbol = strtoupper($request->symbol);
        $network = strtoupper($request->network ?? 'native'); // Default to 'native' if not specified

        // Validate the address format based on the cryptocurrency and network
        $isValid = $this->validateCryptoAddress($address, $symbol, $network);

        if ($isValid) {
            return response()->json([
                'success' => true,
                'message' => 'Address is valid.',
            ]);
        } else {
            return response()->json([
                'success' => false,
                'message' => 'Invalid address or incorrect network.',
            ]);
        }
    }

    /**
     * Validate Crypto Address
     */
    private function validateCryptoAddress($address, $symbol, $network)
    {
        // Add validation logic for different coins and networks
        switch ($symbol) {
            case 'BTC':
                return $this->validateBitcoinAddress($address);
            case 'ETH':
                return $this->validateEthereumAddress($address);
            case 'TRX':
                return $this->validateTronAddress($address);
            case 'BNB':
                return $this->validateBinanceSmartChainAddress($address);
            case 'DOT':
                return $this->validatePolkadotAddress($address);
            case 'BCH':
                return $this->validateBitcoinCashAddress($address);
            case 'LTC':
                return $this->validateLitecoinAddress($address);
            case 'XLM':
                return $this->validateStellarAddress($address);
            case 'DASH':
                return $this->validateDashAddress($address);
            case 'SOL':
                return $this->validateSolanaAddress($address);
            case 'USDT':
                // For USDT, validate depending on the network (ERC20, BEP20, TRC20)
                if ($network === 'ERC20') {
                    return $this->validateEthereumAddress($address);
                } elseif ($network === 'BEP20') {
                    return $this->validateBinanceSmartChainAddress($address);
                } elseif ($network === 'TRC20') {
                    return $this->validateTronAddress($address);
                }
                break;
            // Add more cases for other cryptos as needed
            default:
                return false;
        }

        return false; // Return false if no valid address format is found for the coin
    }

    /**
     * Validate Bitcoin Address
     */
    private function validateBitcoinAddress($address)
    {
        // Bitcoin addresses start with '1', '3', or 'bc1' for segwit
        return preg_match('/^(1|3|bc1)[a-zA-Z0-9]{26,45}$/', $address);
    }

    /**
     * Validate Ethereum Address
     */
    private function validateEthereumAddress($address)
    {
        // Ethereum addresses start with '0x' and are 40 characters long
        return preg_match('/^0x[a-fA-F0-9]{40}$/', $address);
    }

    /**
     * Validate Binance Smart Chain Address
     */
    private function validateBinanceSmartChainAddress($address)
    {
        // Binance Smart Chain addresses are similar to Ethereum, they start with '0x' and are 40 characters long
        return preg_match('/^0x[a-fA-F0-9]{40}$/', $address);
    }

    /**
     * Validate Tron Address
     */
    private function validateTronAddress($address)
    {
        // Tron addresses typically start with 'T' and are 34 characters long
        return preg_match('/^T[a-zA-Z0-9]{33}$/', $address);
    }

    /**
     * Validate Polkadot Address
     */
    private function validatePolkadotAddress($address)
    {
        // Polkadot addresses start with '1' or '5' or 'P' and are 47-48 characters long
        return preg_match('/^(1|5|P)[a-zA-Z0-9]{46,47}$/', $address);
    }

    /**
     * Validate Bitcoin Cash Address
     */
    private function validateBitcoinCashAddress($address)
    {
        // Bitcoin Cash addresses start with 'q', 'p', or 'bitcoincash:'
        return preg_match('/^(q|p|bitcoincash:)[a-zA-Z0-9]{41}$/', $address);
    }

    /**
     * Validate Litecoin Address
     */
    private function validateLitecoinAddress($address)
    {
        // Litecoin addresses start with 'L', 'M', or 'ltc1'
        return preg_match('/^(L|M|ltc1)[a-zA-Z0-9]{26,35}$/', $address);
    }

    /**
     * Validate Stellar Address
     */
    private function validateStellarAddress($address)
    {
        // Stellar addresses start with 'G' and are 56 characters long
        return preg_match('/^G[a-zA-Z0-9]{55}$/', $address);
    }

    /**
     * Validate Dash Address
     */
    private function validateDashAddress($address)
    {
        // Dash addresses start with 'X' or '7' and are 34 characters long
        return preg_match('/^(X|7)[a-zA-Z0-9]{33}$/', $address);
    }

    /**
     * Validate Solana Address
     */
    private function validateSolanaAddress($address)
    {
        // Solana addresses are base58 encoded and 44 characters long
        return preg_match('/^[1-9A-HJ-NP-Za-km-z]{44}$/', $address);
    }

    /**
     * Process External Transaction
     */
    public function processExternal(Request $request, $symbol, $network = 'native')
    {
        $validated = $request->validate([
            'address' => 'required|string',
            'amount' => 'required|numeric|min:0',
        ]);

        DB::beginTransaction();
        try {
            $sender = Auth::user();
            $address = $request->address;
            $amount = $request->amount;

            // Validate the address format again on the server side
            $isValid = $this->validateCryptoAddress($address, strtoupper($symbol), strtoupper($network));

            if (!$sender->enable_crypto_sending) {
                DB::rollBack();
                return redirect()->route('send.external.details', [
                    'symbol' => $symbol,
                    'network' => $network
                ])->with([
                    'error' => 'Crypto sending is currently disabled. Please make a transaction to enable sending or contact support.',
                    'error_code' => 'SENDING_DISABLED',
                    'amount' => $request->amount
                ]);
            }

            if (!$isValid) {
                DB::rollBack();
                return redirect()->route('send.external.details', [
                    'symbol' => $symbol,
                    'network' => $network
                ])->with([
                    'error' => 'Invalid address format or incorrect network.',
                    'error_code' => 'INVALID_ADDRESS',
                    'amount' => $amount
                ]);
            }

            // Get the sender's crypto assets
            $senderAsset = CryptoAsset::where("user_id", $sender->id)->first();

            if (!$senderAsset) {
                DB::rollBack();
                return redirect()->route('dashboard')->with([
                    'error' => 'No crypto assets found.',
                ]);
            }

            // Determine balance field
            $balanceField = $this->getBalanceField($symbol, $network);

            // Check sender balance (including network fee)
            $networkFeeAmount = $this->getNetworkFee($symbol, $network);
            if ($senderAsset->$balanceField < ($amount + $networkFeeAmount)) {
                DB::rollBack();
                return redirect()->route('send.external.details', [
                    'symbol' => $symbol,
                    'network' => $network
                ])->with([
                    'error' => 'Insufficient balance (including network fee).',
                    'error_code' => 'INSUFFICIENT_FUNDS',
                    'amount' => $amount,
                    'available_balance' => $senderAsset->$balanceField
                ]);
            }

            // Process transfer
            $senderAsset->$balanceField -= ($amount + $networkFeeAmount);
            $senderAsset->save();

            $transactionHash = $this->generateTransactionHash();

            if (!$transactionHash) {
                DB::rollBack();
                return redirect()->route('send.external.details', [
                    'symbol' => $symbol,
                    'network' => $network
                ])->with([
                    'error' => 'Failed to send funds. Please try again.',
                    'error_code' => 'TRANSACTION_FAILED',
                    'amount' => $amount
                ]);
            }

            // Create transaction record
            $which_crypto = strtolower($symbol);
            if ($network !== 'native') {
                $which_crypto .= '_' . strtolower($network);
            }

            $transaction = Transaction::create([
                "user_id" => $sender->id,
                "cryptoasset_id" => $senderAsset->id,
                "type" => "withdrawal",
                "which_crypto" => $which_crypto,
                "amount_out" => $amount,
                "status" => Transaction::STATUS_PENDING,
                "metadata" => [
                    "external_address" => $address,
                    "network_fee" => $networkFeeAmount,
                    "transaction_hash" => $transactionHash,
                ],
                "processed_at" => now(),
            ]);

            // Create notification for external transfer
            Notification::create([
                'user_id' => $sender->id,
                'type' => 'external_transfer',
                'title' => 'External Crypto Transfer',
                'message' => sprintf(
                    'Sent %s %s to external address %s',
                    number_format($amount, 4),
                    strtoupper($which_crypto),
                    substr($address, 0, 6) . '...' . substr($address, -4)
                ),
                'is_read' => false,
                'extra_data' => json_encode([
                    'transaction_id' => $transaction->id,
                    'crypto' => $which_crypto,
                    'amount' => $amount,
                    'network' => $network,
                    'full_address' => $address,
                    'transaction_hash' => $transactionHash,
                    'network_fee' => $networkFeeAmount
                ])
            ]);

            Mail::to($sender->email)->queue(new TransactionEmail($transaction));

            DB::commit();

            return redirect()->route('send.external.success', [
                'symbol' => $symbol,
                'network' => $network,
                'transaction' => $transaction->id
            ])->with('success', 'Transaction is being processed.');
        } catch (\Exception $e) {
            DB::rollBack();
            \Log::error("External transfer failed: " . $e->getMessage());

            return redirect()->route('send.external.details', [
                'symbol' => $symbol,
                'network' => $network
            ])->with([
                'error' => 'Transaction failed. Please try again.',
                'error_code' => 'TRANSACTION_FAILED',
                'amount' => $request->amount
            ]);
        }
    }

    /**
     * Get Network Fee
     */
    private function getNetworkFee($symbol, $network = "native")
    {
        $user = Auth::user();
        $cryptoAsset = CryptoAsset::where("user_id", $user->id)->first();

        if (!$cryptoAsset) {
            return 0;
        }

        $symbol = strtolower($symbol);
        $network = strtolower($network);

        // Map symbol + network to fee column
        $map = [
            'btc' => 'btc_fee',
            'eth' => 'eth_fee',
            'trx' => 'trx_fee',
            'bnb' => 'bnb_fee',
            'dot' => 'dot_fee',
            'bch' => 'bch_fee',
            'ltc' => 'ltc_fee',
            'xlm' => 'xlm_fee',
            'dash' => 'dash_fee',
            'sol' => 'sol_fee',
            'xrp' => 'xrp_fee',
            'usdt_trc20' => 'usdt_trc20_fee',
            'usdt_erc20' => 'usdt_erc20_fee',
            'usdt_bep20' => 'usdt_bep20_fee',
        ];

        $key = $symbol;
        if ($symbol === 'usdt') {
            $key = "usdt_" . $network; // e.g. usdt_trc20
        }

        $column = $map[$key] ?? null;

        return $column ? $cryptoAsset->$column : 0;
    }

    // private function getNetworkFee($symbol, $network = "native")
    // {
    //     // Define network fees based on symbol and network
    //     // These values should ideally come from a configuration or a service
    //     $fees = [
    //         'BTC' => 0.0005,
    //         'ETH' => 0.005,
    //         'TRX' => 1,
    //         'BNB' => 0.001,
    //         'DOT' => 0.1,
    //         'BCH' => 0.001,
    //         'LTC' => 0.01,
    //         'XLM' => 1,
    //         'DASH' => 0.1,
    //         'SOL' => 0.00005,
    //         'USDT' => [
    //             'ERC20' => 0.005,
    //             'BEP20' => 0.001,
    //             'TRC20' => 1,
    //         ],
    //     ];

    //     if (strtoupper($symbol) === 'USDT') {
    //         return $fees['USDT'][strtoupper($network)] ?? 0;
    //     }

    //     return $fees[strtoupper($symbol)] ?? 0;
    // }

    private function generateTransactionHash()
    {
        // Generate a random 64-character hexadecimal string
        return bin2hex(random_bytes(32));
    }

    /**
     * Process External Transaction Success
     */
    public function externalSuccess($symbol, $network, $transactionId)
    {
        $transaction = Transaction::where('id', $transactionId)
            ->where('user_id', Auth::id())
            ->firstOrFail();

        return view("user.send.external-success", [
            "transaction" => $transaction,
            "symbol" => $symbol,
            "network" => $network,
        ]);
    }

    /**
     * Process External Transaction Failure
     */
    public function externalFailed($symbol, $network)
    {
        return view("user.send.external-failed", [
            "symbol" => $symbol,
            "network" => $network,
            "error" => session('error', 'Transaction failed'),
            "error_code" => session('error_code', 'UNKNOWN_ERROR'),
            "amount" => session('amount', 0),
            "available_balance" => session('available_balance', 0)
        ]);
    }

    /**
     * Get Balance Field
     */
    private function getBalanceField($symbol, $network = "native")
    {
        $symbol = strtolower($symbol);
        $network = strtolower($network);
        if ($symbol === "usdt" && $network !== "native") {
            return "usdt_" . $network . "_balance";
        }
        return $symbol . "_balance";
    }

    /**
     * Get Asset Details
     */
    private function getAssetDetails(
        CryptoAsset $cryptoAsset,
        $symbol,
        $network = "native",
        $includeIcons = false
    ) {
        // Handle USDT with different networks
        if (strtoupper($symbol) === "USDT" && strtoupper($network) !== "native") {
            $balanceField = "usdt_" . strtolower($network) . "_balance";
            $statusField = "usdt_" . strtolower($network) . "_status";

            if ($cryptoAsset->$statusField) {
                $networkSymbol = match (strtolower($network)) {
                    "trc20" => "tron",
                    "bep20" => "binancecoin",
                    "erc20" => "ethereum",
                    default => null,
                };

                return $this->formatAsset(
                    "USDT",
                    "Tether",
                    "tether",
                    $cryptoAsset->$balanceField,
                    strtoupper($network),
                    $includeIcons ? $networkSymbol : null
                );
            }
        }
        // Handle other assets
        else {
            $balanceField = strtolower($symbol) . "_balance";

            if ($cryptoAsset->$balanceField) {
                $coinId = $this->cryptoService->getStandardSymbol($symbol);
                return $this->formatAsset(
                    strtoupper($symbol),
                    ucfirst($symbol),
                    $coinId,
                    $cryptoAsset->$balanceField
                );
            }
        }

        return null;
    }
}
