{% extends "base.html" %}
{% from "macros/icons.html" import icon %}

{% block title_extra %} — {{ _('nav_settings') }}{% endblock %}

{% block content %}
<div class="section-title">
    <span class="icon">{{ icon('settings') }}</span>
    {{ _('settings_title') }}
</div>

<div class="grid"
    style="display: grid; grid-template-columns: repeat(auto-fit, minmax(400px, 1fr)); gap: var(--space-lg); align-items: start;">
    <!-- LEFT COLUMN -->
    <div style="display: flex; flex-direction: column; gap: var(--space-lg);">
        <!-- BLOCK 1: Appearance -->
        <div class="card">
            <h3 class="card-title" style="margin-bottom: var(--space-lg);">{{ _('appearance') }}</h3>
            <form id="appearanceForm">
                <div class="form-group">
                    <label class="form-label">{{ _('title_label') }}</label>
                    <input type="text" class="form-input" name="title" value="{{ settings.appearance.title }}" required>
                </div>
                <div class="form-group">
                    <label class="form-label">{{ _('logo_label') }}</label>
                    <input type="text" class="form-input" name="logo" value="{{ settings.appearance.logo }}" required>
                </div>
                <div class="form-group">
                    <label class="form-label">{{ _('subtitle_label') }}</label>
                    <input type="text" class="form-input" name="subtitle" value="{{ settings.appearance.subtitle }}"
                        required>
                </div>
            </form>
        </div>

        <!-- BLOCK Captcha -->
        <div class="card">
            <h3 class="card-title" style="margin-bottom: var(--space-lg);">{{ _('captcha_title') }}</h3>
            <form id="captchaForm">
                <div class="form-group">
                    <label class="form-label">
                        <input type="checkbox" id="captcha_enabled" {% if captcha_settings.enabled %}checked{% endif %}>
                        {{ _('enable_captcha') }}
                    </label>
                </div>
            </form>
        </div>

        <!-- BLOCK Guest Access -->
        <div class="card">
            <h3 class="card-title" style="margin-bottom: var(--space-lg);">{{ _('guest_settings_title') }}</h3>
            <form id="guestForm">
                <div class="form-group">
                    <label style="display: flex; align-items: center; gap: var(--space-sm); cursor: pointer;">
                        <input type="checkbox" id="guest_enabled" {% if settings.guest.enabled %}checked{% endif %}
                            onchange="document.getElementById('guestFields').style.display = this.checked ? 'block' : 'none'">
                        {{ _('guest_enable') }}
                    </label>
                    <div class="form-hint">{{ _('guest_enable_hint') }}</div>
                </div>

                <div id="guestFields" style="{% if not settings.guest.enabled %}display:none;{% endif %}">
                    <div class="form-group">
                        <label class="form-label">{{ _('guest_link_label') }}</label>
                        <div style="display:flex; gap: var(--space-sm);">
                            <input type="text" class="form-input" id="guest_link_display" readonly
                                value="{% if settings.guest.token %}{{ request.url.scheme }}://{{ request.url.netloc }}/guest/{{ settings.guest.token }}{% endif %}"
                                placeholder="{{ _('guest_link_placeholder') }}">
                            <button type="button" class="btn btn-secondary btn-sm btn-icon" onclick="copyGuestLink()" title="{{ _('copy') }}">{{ icon('copy') }}</button>
                            <button type="button" class="btn btn-secondary btn-sm" onclick="regenGuestToken()" title="{{ _('guest_regen_token') }}">🔄</button>
                        </div>
                        <input type="hidden" id="guest_token" value="{{ settings.guest.token or '' }}">
                    </div>

                    <div class="form-group">
                        <label class="form-label">{{ _('guest_user_label') }}</label>
                        <select class="form-select" id="guest_user_id">
                            <option value="">{{ _('guest_user_none') }}</option>
                            {% for u in users %}
                            <option value="{{ u.id }}" {% if settings.guest.user_id == u.id %}selected{% endif %}>
                                {{ u.username }} ({{ u.role }})
                            </option>
                            {% endfor %}
                        </select>
                        <div class="form-hint">{{ _('guest_user_hint') }}</div>
                    </div>

                    <div class="form-group">
                        <label class="form-label">{{ _('guest_password_label') }}</label>
                        <input type="password" class="form-input" id="guest_password"
                            placeholder="{% if settings.guest.password_hash %}{{ _('guest_password_keep') }}{% else %}{{ _('share_password_hint') }}{% endif %}"
                            autocomplete="new-password">
                        {% if settings.guest.password_hash %}
                        <label style="display:flex; align-items:center; gap:var(--space-sm); margin-top:var(--space-xs); cursor:pointer;">
                            <input type="checkbox" id="guest_clear_password">
                            {{ _('guest_clear_password') }}
                        </label>
                        {% endif %}
                    </div>

                    <div class="form-group">
                        <label style="display: flex; align-items: center; gap: var(--space-sm); cursor: pointer;">
                            <input type="checkbox" id="guest_allow_create" {% if settings.guest.allow_create %}checked{% endif %}
                                onchange="document.getElementById('guestCreateFields').style.display = this.checked ? 'block' : 'none'">
                            {{ _('guest_allow_create') }}
                        </label>
                        <div class="form-hint">{{ _('guest_allow_create_hint') }}</div>
                    </div>

                    <div id="guestCreateFields"
                        style="{% if not settings.guest.allow_create %}display:none;{% endif %} background: var(--bg-primary); padding: var(--space-md); border-radius: var(--radius-md);">
                        <div class="form-group">
                            <label class="form-label">{{ _('server_label') }}</label>
                            <select class="form-select" id="guest_create_server" onchange="fillGuestProtocols()">
                                {% if xui_servers %}
                                <option value="xui" {% if settings.guest.create_protocol == 'xui' %}selected{% endif %}>3x-ui</option>
                                {% endif %}
                                {% for s in servers %}
                                <option value="{{ loop.index0 }}"
                                    {% if settings.guest.create_protocol != 'xui' and settings.guest.create_server_id == loop.index0 %}selected{% endif %}>
                                    {{ s.name or s.host }} ({{ s.host }})
                                </option>
                                {% endfor %}
                            </select>
                            <div class="form-hint">{{ _('server_then_protocol_hint') }}</div>
                        </div>
                        <div class="form-group">
                            <label class="form-label">{{ _('protocol_label') }}</label>
                            <select class="form-select" id="guest_create_protocol" onchange="updateGuestCreateFields()">
                                <!-- filled by JS -->
                            </select>
                            <input type="hidden" id="guest_create_protocol_pref" value="{{ settings.guest.create_protocol or '' }}">
                        </div>
                        <div class="form-group" id="guestInboundGroup" style="{% if settings.guest.create_protocol != 'xui' %}display:none;{% endif %}">
                            <label class="form-label">{{ _('xui_server_select_label') }}</label>
                            <select class="form-select" id="guest_create_xui_panel" onchange="loadGuestInbounds()">
                                {% for s in xui_servers %}
                                <option value="{{ s.id }}" {% if settings.guest.create_xui_panel_id == s.id %}selected{% endif %}>{{ s.name }}</option>
                                {% endfor %}
                            </select>
                            <label class="form-label" style="margin-top:var(--space-sm);">{{ _('xui_inbound_label') }}</label>
                            <select class="form-select" id="guest_create_inbound_id">
                                <option value="0">{{ _('invite_inbound_loading') }}</option>
                            </select>
                            <div class="form-hint">{{ _('xui_inbound_hint') }}</div>
                        </div>
                    </div>
                </div>
            </form>
        </div>

        <!-- BLOCK Telegram Bot -->
        <div class="card">
            <h3 class="card-title" style="margin-bottom: var(--space-lg);">{{ _('telegram_bot_title') }}</h3>
            <form id="telegramForm">
                <div class="form-group">
                    <label class="form-label">{{ _('bot_token_label') }}</label>
                    <input type="text" class="form-input" id="tg_token" value="{{ telegram_settings.token or '' }}"
                        placeholder="123456:ABC-DEF1234ghIkl-zyx57W2v1u123ew11">
                </div>
                <div style="display: flex; align-items: center; gap: var(--space-md); margin-top: var(--space-md);">
                    <div style="display: flex; align-items: center; gap: var(--space-sm);">
                        <span style="font-size: 0.85rem; color: var(--text-muted);">{{ _('bot_status') }}:</span>
                        {% if bot_running %}
                        <span class="badge badge-success" id="botStatusBadge">{{ _('bot_running') }}</span>
                        {% else %}
                        <span class="badge badge-secondary" id="botStatusBadge">{{ _('bot_stopped') }}</span>
                        {% endif %}
                    </div>
                    <button type="button" class="btn btn-secondary btn-sm" onclick="toggleBot()" id="toggleBotBtn">
                        <span id="toggleBotBtnText">{% if bot_running %}{{ _('bot_stop_btn') }}{% else %}{{
                            _('bot_start_btn') }}{% endif %}</span>
                        <div class="spinner hidden" id="toggleBotSpinner" style="width:14px;height:14px;"></div>
                    </button>
                </div>
                <p class="form-hint" style="margin-top: var(--space-sm);">
                    {{ _('bot_hint') }}
                </p>
            </form>
        </div>

        <!-- BLOCK 4: API Docs -->
        <div class="card">
            <h3 class="card-title" style="margin-bottom: var(--space-lg);">{{ _('api_docs_title') }}</h3>
            <div style="display: flex; flex-direction: column; gap: var(--space-md);">
                <a href="/docs" target="_blank" class="btn btn-secondary"
                    style="justify-content: flex-start; text-decoration: none;">
                    <span style="font-size: 1.2rem; margin-right: 10px;">📖</span>
                    <div style="text-align: left;">
                        <div style="font-weight: 600;">Swagger UI</div>
                        <div style="font-size: 0.75rem; opacity: 0.7;">{{ _('api_docs_hint') }}</div>
                    </div>
                </a>
                <a href="/redoc" target="_blank" class="btn btn-secondary"
                    style="justify-content: flex-start; text-decoration: none;">
                    <span style="font-size: 1.2rem; margin-right: 10px;">📑</span>
                    <div style="text-align: left;">
                        <div style="font-weight: 600;">ReDoc</div>
                        <div style="font-size: 0.75rem; opacity: 0.7;">{{ _('api_docs_hint') }}</div>
                    </div>
                </a>
            </div>
            <p class="form-hint" style="margin-top: var(--space-md);">{{ _('api_docs_hint') }}</p>
        </div>

        <!-- BLOCK Tunnels -->
        <div class="card tunnels-card">
            <div class="tunnels-header">
                <h3 class="card-title">🌍 {{ _('tunnels_title') }}</h3>
                <p class="tunnels-subtitle">{{ _('tunnels_subtitle') }}</p>
            </div>

            <div class="tunnels-local">
                <div class="tunnels-local-icon" aria-hidden="true">🏠</div>
                <div class="tunnels-local-body">
                    <div class="tunnels-local-label">{{ _('local_server') }}</div>
                    <div class="tunnels-local-url">
                        <code id="localServerUrl">{{ request.url.scheme }}://{{ request.url.netloc }}</code>
                        <button type="button" class="btn btn-secondary btn-sm" onclick="copyElementText('localServerUrl')">{{ _('copy') }}</button>
                    </div>
                </div>
                <span class="tunnel-status-pill tunnel-status-pill--ok">{{ _('active') }}</span>
            </div>

            <div class="tunnels-section">
                <h4 class="tunnels-section-title">{{ _('tunnels_section_inbound') }}</h4>
                <div class="tunnels-grid">
                    <article class="tunnel-card tunnel-row" data-provider="cloudflare" id="tunnelCard-cloudflare">
                        <div class="tunnel-card-head">
                            <div class="tunnel-card-icon tunnel-card-icon--cloudflare" aria-hidden="true">☁</div>
                            <div class="tunnel-card-meta">
                                <h5 class="tunnel-card-title">Cloudflare Quick Tunnel</h5>
                                <p class="tunnel-card-desc">{{ _('tunnel_cloudflare_desc') }}</p>
                            </div>
                            <span class="tunnel-status-pill" id="cloudflareInstallBadge">{{ _('not_installed') }}</span>
                        </div>
                        <div class="tunnel-card-body">
                            <div id="cloudflarePublicUrls" class="tunnel-url-box tunnel-url-box--empty">{{ _('tunnel_no_public_url') }}</div>
                        </div>
                        <div class="tunnel-card-actions tunnel-card-actions--triple">
                            <button type="button" class="btn btn-primary btn-sm" id="cloudflareTunnelBtn" onclick="enableTunnel('cloudflare')">
                                <span id="cloudflareTunnelBtnText">{{ _('tunnel_install_enable') }}</span>
                                <div class="spinner hidden" id="cloudflareTunnelSpinner" style="width:14px; height:14px;"></div>
                            </button>
                            <button type="button" class="btn btn-secondary btn-sm hidden" id="cloudflareStopBtn" onclick="stopTunnel('cloudflare')">
                                <span id="cloudflareStopBtnText">{{ _('tunnel_stop') }}</span>
                                <div class="spinner hidden" id="cloudflareStopSpinner" style="width:14px; height:14px;"></div>
                            </button>
                            <button type="button" class="btn btn-danger btn-sm hidden" id="cloudflareDeleteBtn" onclick="deleteTunnel('cloudflare')">
                                <span id="cloudflareDeleteBtnText">{{ _('tunnel_delete') }}</span>
                                <div class="spinner hidden" id="cloudflareDeleteSpinner" style="width:14px; height:14px;"></div>
                            </button>
                        </div>
                    </article>

                    <article class="tunnel-card tunnel-row" data-provider="ngrok" id="tunnelCard-ngrok">
                        <div class="tunnel-card-head">
                            <div class="tunnel-card-icon tunnel-card-icon--ngrok" aria-hidden="true">N</div>
                            <div class="tunnel-card-meta">
                                <h5 class="tunnel-card-title">ngrok</h5>
                                <p class="tunnel-card-desc">{{ _('tunnel_ngrok_desc') }}</p>
                            </div>
                            <span class="tunnel-status-pill" id="ngrokInstallBadge">{{ _('not_installed') }}</span>
                        </div>
                        <div class="tunnel-card-body">
                            <input type="password" class="form-input" id="ngrokAuthtoken" placeholder="{{ _('ngrok_authtoken_placeholder') }}" autocomplete="off">
                            <div id="ngrokPublicUrls" class="tunnel-url-box tunnel-url-box--empty">{{ _('tunnel_no_public_url') }}</div>
                        </div>
                        <div class="tunnel-card-actions tunnel-card-actions--triple">
                            <button type="button" class="btn btn-primary btn-sm" id="ngrokTunnelBtn" onclick="enableTunnel('ngrok')">
                                <span id="ngrokTunnelBtnText">{{ _('tunnel_install_enable') }}</span>
                                <div class="spinner hidden" id="ngrokTunnelSpinner" style="width:14px; height:14px;"></div>
                            </button>
                            <button type="button" class="btn btn-secondary btn-sm hidden" id="ngrokStopBtn" onclick="stopTunnel('ngrok')">
                                <span id="ngrokStopBtnText">{{ _('tunnel_stop') }}</span>
                                <div class="spinner hidden" id="ngrokStopSpinner" style="width:14px; height:14px;"></div>
                            </button>
                            <button type="button" class="btn btn-danger btn-sm hidden" id="ngrokDeleteBtn" onclick="deleteTunnel('ngrok')">
                                <span id="ngrokDeleteBtnText">{{ _('tunnel_delete') }}</span>
                                <div class="spinner hidden" id="ngrokDeleteSpinner" style="width:14px; height:14px;"></div>
                            </button>
                        </div>
                    </article>
                </div>
            </div>

            <div class="tunnels-section">
                <h4 class="tunnels-section-title">{{ _('tunnels_section_outbound') }}</h4>
                <div class="tunnels-grid">
                    <article class="tunnel-card tunnel-row" data-provider="warp" id="tunnelCard-warp">
                        <div class="tunnel-card-head">
                            <div class="tunnel-card-icon tunnel-card-icon--warp" aria-hidden="true">W</div>
                            <div class="tunnel-card-meta">
                                <h5 class="tunnel-card-title">Cloudflare WARP</h5>
                                <p class="tunnel-card-desc">{{ _('tunnel_warp_desc') }}</p>
                            </div>
                            <span class="tunnel-status-pill" id="warpInstallBadge">{{ _('not_installed') }}</span>
                        </div>
                        <div class="tunnel-card-body">
                            <p id="warpStatusText" class="tunnel-status-line">{{ _('warp_status_unknown') }}</p>
                            <p id="warpHintText" class="tunnel-hint">{{ _('warp_hint') }}</p>
                        </div>
                        <div class="tunnel-card-actions">
                            <button type="button" class="btn btn-primary btn-sm" id="warpConnectBtn" onclick="connectWarp()">
                                <span id="warpConnectBtnText">{{ _('warp_connect') }}</span>
                                <div class="spinner hidden" id="warpConnectSpinner" style="width:14px; height:14px;"></div>
                            </button>
                            <button type="button" class="btn btn-secondary btn-sm hidden" id="warpDisconnectBtn" onclick="disconnectWarp()">
                                <span id="warpDisconnectBtnText">{{ _('warp_disconnect') }}</span>
                                <div class="spinner hidden" id="warpDisconnectSpinner" style="width:14px; height:14px;"></div>
                            </button>
                        </div>
                    </article>

                    <article class="tunnel-card tunnel-row" data-provider="nordvpn" id="tunnelCard-nordvpn">
                        <div class="tunnel-card-head">
                            <div class="tunnel-card-icon tunnel-card-icon--nordvpn" aria-hidden="true">N</div>
                            <div class="tunnel-card-meta">
                                <h5 class="tunnel-card-title">NordVPN</h5>
                                <p class="tunnel-card-desc">{{ _('tunnel_nordvpn_desc') }}</p>
                            </div>
                            <span class="tunnel-status-pill" id="nordvpnInstallBadge">{{ _('not_installed') }}</span>
                        </div>
                        <div class="tunnel-card-body">
                            <p id="nordvpnStatusText" class="tunnel-status-line">{{ _('nordvpn_status_unknown') }}</p>
                            <p id="nordvpnServerText" class="tunnel-status-line tunnel-status-line--server hidden"></p>
                            <p id="nordvpnHintText" class="tunnel-hint">{{ _('nordvpn_hint') }}</p>
                            <div class="tunnel-nordvpn-fields">
                                <input type="text" class="form-input" id="nordvpnCountry" placeholder="{{ _('nordvpn_country_placeholder') }}" autocomplete="off">
                                <input type="text" class="form-input" id="nordvpnCity" placeholder="{{ _('nordvpn_city_placeholder') }}" autocomplete="off">
                            </div>
                        </div>
                        <div class="tunnel-card-actions">
                            <button type="button" class="btn btn-primary btn-sm" id="nordvpnConnectBtn" onclick="connectNordvpn()">
                                <span id="nordvpnConnectBtnText">{{ _('nordvpn_connect') }}</span>
                                <div class="spinner hidden" id="nordvpnConnectSpinner" style="width:14px; height:14px;"></div>
                            </button>
                            <button type="button" class="btn btn-secondary btn-sm hidden" id="nordvpnDisconnectBtn" onclick="disconnectNordvpn()">
                                <span id="nordvpnDisconnectBtnText">{{ _('nordvpn_disconnect') }}</span>
                                <div class="spinner hidden" id="nordvpnDisconnectSpinner" style="width:14px; height:14px;"></div>
                            </button>
                        </div>
                    </article>
                </div>
            </div>

            <p class="tunnels-footnote">{{ _('tunnels_hint') }}</p>
        </div>

        <!-- BLOCK SSL/HTTPS -->
        <div class="card">
            <h3 class="card-title" style="margin-bottom: var(--space-lg);">🔒 {{ _('ssl_title') }}</h3>
            <form id="sslForm">
                <div class="form-group">
                    <label class="form-label">
                        <input type="checkbox" id="ssl_enabled" {% if settings.get('ssl', {}).get('enabled') %}checked{% endif %}>
                        {{ _('enable_https') }}
                    </label>
                </div>
                <div class="form-group" style="margin-top: var(--space-md);">
                    <label class="form-label">{{ _('panel_port_label') }}</label>
                    <input type="number" class="form-input" id="panel_port" value="{{ settings.get('ssl', {}).get('panel_port', 5000) }}" placeholder="5000">
                </div>
                <div id="sslFields" style="{% if not settings.get('ssl', {}).get('enabled') %}display:none;{% endif %} margin-top: var(--space-md);">
                    <div class="form-group">
                        <label class="form-label">{{ _('domain_label') }}</label>
                        <input type="text" class="form-input" id="ssl_domain" value="{{ settings.get('ssl', {}).get('domain', '') }}" placeholder="vpn.example.com">
                    </div>

                    <div style="display: grid; grid-template-columns: 1fr 1fr; gap: var(--space-md);">
                        <div class="form-group">
                            <label class="form-label">{{ _('cert_path_label') }}</label>
                            <input type="text" class="form-input" id="ssl_cert_path" value="{{ settings.get('ssl', {}).get('cert_path', '') }}" placeholder="/etc/amnezia/cert.pem">
                        </div>
                        <div class="form-group">
                            <label class="form-label">{{ _('key_path_label') }}</label>
                            <input type="text" class="form-input" id="ssl_key_path" value="{{ settings.get('ssl', {}).get('key_path', '') }}" placeholder="/etc/amnezia/key.pem">
                        </div>
                    </div>

                    <div class="divider" style="margin: var(--space-md) 0;">{{ _('or_paste_text') }}</div>

                    <div class="form-group">
                        <label class="form-label">{{ _('cert_text_label') }}</label>
                        <textarea class="form-input" id="ssl_cert_text" rows="4" placeholder="-----BEGIN CERTIFICATE----- ...">{{ settings.get('ssl', {}).get('cert_text', '') }}</textarea>
                    </div>
                    <div class="form-group">
                        <label class="form-label">{{ _('key_text_label') }}</label>
                        <textarea class="form-input" id="ssl_key_text" rows="4" placeholder="-----BEGIN PRIVATE KEY----- ...">{{ settings.get('ssl', {}).get('key_text', '') }}</textarea>
                    </div>

                    <p class="form-hint">{{ _('ssl_hint') }}</p>
                </div>
            </form>
        </div>
    </div>

    <!-- RIGHT COLUMN -->
    <div style="display: flex; flex-direction: column; gap: var(--space-lg);">
        <!-- BLOCK 3: Import Users -->
        <div class="card">
            <h3 class="card-title" style="margin-bottom: var(--space-lg);">{{ _('import_users_title') }}</h3>
            <form id="syncForm">
                <div class="form-group" style="margin-bottom: var(--space-lg);">
                    <label class="form-label">{{ _('import_source_label') }}</label>
                    <div style="display: grid; grid-template-columns: 1fr 1fr; gap: var(--space-sm);">
                        <label style="display: flex; align-items: center; gap: var(--space-sm); cursor: pointer;">
                            <input type="checkbox" name="remnawave_sync" {% if settings.sync.remnawave_sync %}checked{%
                                endif %}> Remnawave
                        </label>
                        <label
                            style="display: flex; align-items: center; gap: var(--space-sm); cursor: not-allowed; color: var(--text-muted);">
                            <input type="checkbox" disabled> Marzban
                        </label>
                        <label style="display: flex; align-items: center; gap: var(--space-sm); cursor: pointer;">
                            <input type="checkbox" name="xui_sync" {% if settings.sync.xui_sync %}checked{% endif %}>
                            3x-ui
                        </label>
                        <label
                            style="display: flex; align-items: center; gap: var(--space-sm); cursor: not-allowed; color: var(--text-muted);">
                            <input type="checkbox" disabled> Hiddify
                        </label>
                        <label
                            style="display: flex; align-items: center; gap: var(--space-sm); cursor: not-allowed; color: var(--text-muted);">
                            <input type="checkbox" disabled> LDAP
                        </label>
                    </div>
                </div>

                <div id="remnawaveFields"
                    style="{% if not settings.sync.remnawave_sync %}display:none;{% endif %} border-top: 1px solid var(--border-color); padding-top: var(--space-md);">
                    <div class="form-group">
                        <label class="form-label">{{ _('remnawave_url_label') }}</label>
                        <input type="url" class="form-input" name="remnawave_url"
                            value="{{ settings.sync.remnawave_url }}" placeholder="https://vpn.example.com">
                    </div>
                    <div class="form-group">
                        <label class="form-label">{{ _('api_key_label') }}</label>
                        <input type="password" class="form-input" name="remnawave_api_key"
                            value="{{ settings.sync.remnawave_api_key }}" placeholder="Your secret key">
                    </div>

                    <div class="form-group">
                        <label
                            style="display: flex; align-items: center; gap: var(--space-sm); cursor: pointer; margin-bottom: var(--space-xs);">
                            <input type="checkbox" name="remnawave_sync_users" {% if settings.sync.remnawave_sync_users
                                %}checked{% endif %}>
                            {{ _('enable_sync') }}
                        </label>
                        <div class="form-hint"
                            style="margin-left: var(--space-lg); line-height: 1.4; margin-bottom: var(--space-sm);">
                            {{ _('sync_hint') }}
                        </div>
                        <div style="display: flex; gap: var(--space-sm); margin-left: var(--space-lg);">
                            <button type="button" class="btn btn-secondary btn-sm" onclick="syncRemnawaveNow()"
                                id="syncNowBtn">
                                <span id="syncNowBtnText">🔄 {{ _('sync_now_btn') }}</span>
                                <div class="spinner hidden" id="syncNowSpinner" style="width:14px; height:14px;"></div>
                            </button>
                            <button type="button" class="btn btn-danger btn-sm" onclick="deleteSyncRemnawave()"
                                id="syncDelBtn">
                                <span id="syncDelBtnText">{{ icon('trash') }} {{ _('delete_sync_btn') }}</span>
                                <div class="spinner hidden" id="syncDelSpinner" style="width:14px; height:14px;"></div>
                            </button>
                        </div>
                    </div>

                    <div class="form-group">
                        <label style="display: flex; align-items: center; gap: var(--space-sm); cursor: pointer;">
                            <input type="checkbox" name="remnawave_create_conns" id="syncCreateConns" {% if
                                settings.sync.remnawave_create_conns %}checked{% endif %}>
                            {{ _('auto_create_conns') }}
                        </label>
                    </div>

                    <div id="autoConnFields"
                        style="{% if not settings.sync.remnawave_create_conns %}display:none;{% endif %} background: var(--bg-primary); padding: var(--space-md); border-radius: var(--radius-md); margin-top: var(--space-sm);">
                        <div class="form-group">
                            <label class="form-label">{{ _('sync_server_label') }}</label>
                            <select class="form-select" name="remnawave_server_id" onchange="updateProtocolsForSync()">
                                {% for s in servers %}
                                <option value="{{ loop.index0 }}" {% if settings.sync.remnawave_server_id==loop.index0
                                    %}selected{% endif %}>{{ s.name or s.host }}</option>
                                {% endfor %}
                            </select>
                        </div>
                        <div class="form-group">
                            <label class="form-label">{{ _('protocol_label') }}</label>
                            <select class="form-select" name="remnawave_protocol" id="syncProtocolSelect">
                                <option value="awg" {% if settings.sync.remnawave_protocol=='awg' %}selected{% endif %}>
                                    AmneziaWG</option>
                                <option value="awg2" {% if settings.sync.remnawave_protocol=='awg2' %}selected{% endif %}>
                                    AmneziaWG 2.0</option>
                                <option value="awg_legacy" {% if settings.sync.remnawave_protocol=='awg_legacy' %}selected{% endif %}>
                                    AWG Legacy</option>
                                <option value="xray" {% if settings.sync.remnawave_protocol=='xray' %}selected{% endif %}>
                                    Xray</option>
                            </select>
                        </div>
                    </div>
                </div>

                <div id="xuiFields"
                    style="{% if not settings.sync.xui_sync %}display:none;{% endif %} border-top: 1px solid var(--border-color); padding-top: var(--space-md); margin-top: var(--space-md);">
                    <div class="form-hint" style="margin-bottom: var(--space-md);">
                        {{ _('xui_servers_manage_hint') }}
                    </div>

                    <div class="form-group">
                        <label
                            style="display: flex; align-items: center; gap: var(--space-sm); cursor: pointer; margin-bottom: var(--space-xs);">
                            <input type="checkbox" name="xui_sync_users" {% if settings.sync.xui_sync_users %}checked{% endif %}>
                            {{ _('enable_sync') }}
                        </label>
                        <div class="form-hint"
                            style="margin-left: var(--space-lg); line-height: 1.4; margin-bottom: var(--space-sm);">
                            {{ _('xui_sync_hint') }}
                        </div>
                        <div style="display: flex; gap: var(--space-sm); margin-left: var(--space-lg);">
                            <button type="button" class="btn btn-secondary btn-sm" onclick="syncXuiNow()" id="xuiSyncNowBtn">
                                <span id="xuiSyncNowBtnText">🔄 {{ _('sync_now_btn') }}</span>
                                <div class="spinner hidden" id="xuiSyncNowSpinner" style="width:14px; height:14px;"></div>
                            </button>
                            <button type="button" class="btn btn-danger btn-sm" onclick="deleteSyncXui()" id="xuiSyncDelBtn">
                                <span id="xuiSyncDelBtnText">{{ icon('trash') }} {{ _('delete_sync_btn') }}</span>
                                <div class="spinner hidden" id="xuiSyncDelSpinner" style="width:14px; height:14px;"></div>
                            </button>
                        </div>
                    </div>

                    <div class="form-group">
                        <label style="display: flex; align-items: center; gap: var(--space-sm); cursor: pointer;">
                            <input type="checkbox" name="xui_create_conns" id="xuiSyncCreateConns" {% if
                                settings.sync.xui_create_conns %}checked{% endif %}>
                            {{ _('auto_create_conns') }}
                        </label>
                    </div>

                    <div id="xuiAutoConnFields"
                        style="{% if not settings.sync.xui_create_conns %}display:none;{% endif %} background: var(--bg-primary); padding: var(--space-md); border-radius: var(--radius-md); margin-top: var(--space-sm);">
                        <div class="form-group">
                            <label class="form-label">{{ _('sync_server_label') }}</label>
                            <select class="form-select" name="xui_server_id" onchange="updateProtocolsForXuiSync()">
                                {% for s in servers %}
                                <option value="{{ loop.index0 }}" {% if settings.sync.xui_server_id==loop.index0
                                    %}selected{% endif %}>{{ s.name or s.host }}</option>
                                {% endfor %}
                            </select>
                        </div>
                        <div class="form-group">
                            <label class="form-label">{{ _('protocol_label') }}</label>
                            <select class="form-select" name="xui_protocol" id="xuiSyncProtocolSelect">
                                <option value="xray" {% if settings.sync.xui_protocol=='xray' %}selected{% endif %}>Xray</option>
                                <option value="awg" {% if settings.sync.xui_protocol=='awg' %}selected{% endif %}>AmneziaWG</option>
                                <option value="awg2" {% if settings.sync.xui_protocol=='awg2' %}selected{% endif %}>AmneziaWG 2.0</option>
                            </select>
                        </div>
                    </div>
                    <input type="hidden" name="xui_url" value="{{ settings.sync.xui_url or '' }}">
                    <input type="hidden" name="xui_sub_url" value="{{ settings.sync.xui_sub_url or '' }}">
                    <input type="hidden" name="xui_api_token" value="{{ settings.sync.xui_api_token or '' }}">
                    <input type="hidden" name="xui_username" value="{{ settings.sync.xui_username or '' }}">
                    <input type="hidden" name="xui_password" value="{{ settings.sync.xui_password or '' }}">
                    <input type="hidden" name="xui_inbound_id" value="{{ settings.sync.xui_inbound_id or 0 }}">
                </div>

            </form>
        </div>

        <!-- BLOCK: 3x-ui servers (multi) -->
        <div class="card" style="margin-top: var(--space-lg);">
            <div style="display:flex; align-items:center; justify-content:space-between; gap:var(--space-md); margin-bottom: var(--space-lg);">
                <h3 class="card-title" style="margin:0;">{{ _('xui_servers_title') }}</h3>
                <button type="button" class="btn btn-primary btn-sm" onclick="openXuiServerModal()">+ {{ _('xui_server_add') }}</button>
            </div>
            <div class="form-hint" style="margin-bottom: var(--space-md);">{{ _('xui_servers_hint') }}</div>
            <div id="xuiServersList">
                {% if xui_servers %}
                {% for s in xui_servers %}
                <div class="client-item" style="margin-bottom:var(--space-sm);" data-xui-id="{{ s.id }}">
                    <div class="client-info" style="flex:1; min-width:0;">
                        <div class="client-avatar">🌐</div>
                        <div style="min-width:0;">
                            <div class="client-name">{{ s.name }}</div>
                            <div class="client-meta" style="word-break:break-all;">
                                <span>{{ s.url }}</span>
                                {% if s.sub_url %}<span>· sub: {{ s.sub_url }}</span>{% endif %}
                            </div>
                        </div>
                    </div>
                    <div class="client-actions">
                        <button class="btn btn-secondary btn-sm" type="button" onclick='editXuiServer({{ s | tojson }})'>{{ _('edit') }}</button>
                        <button class="btn btn-danger btn-sm" type="button" onclick="deleteXuiServer('{{ s.id }}')">{{ _('delete') }}</button>
                    </div>
                </div>
                {% endfor %}
                {% else %}
                <div style="text-align:center; padding:var(--space-lg); color:var(--text-muted);">{{ _('xui_servers_empty') }}</div>
                {% endif %}
            </div>
        </div>

        <!-- BLOCK: Simple Backup -->
        <div class="card" style="margin-top: var(--space-lg);">
            <h3 class="card-title" style="margin-bottom: var(--space-lg);">📤 {{ _('backup_title') }}</h3>
            <div style="display: flex; flex-direction: column; gap: var(--space-md);">
                <div style="display: flex; gap: var(--space-sm);">
                    <a href="/api/settings/backup/download" class="btn btn-secondary"
                        style="flex:1; text-decoration:none; display:flex; align-items:center; justify-content:center; gap:var(--space-sm);">
                        <span>⬇️</span> {{ _('download_backup') }}
                    </a>
                </div>
                <div style="border-top: 1px solid var(--border-color); padding-top: var(--space-md);">
                    <div style="display: flex; flex-direction: column; gap: var(--space-sm);">
                        <input type="file" id="backupFile" accept=".json" style="display: none;"
                            onchange="handleRestore(event)">
                        <button type="button" class="btn btn-secondary"
                            onclick="document.getElementById('backupFile').click()" id="restoreBtn"
                            style="gap:var(--space-sm);">
                            <span>⬆️</span> {{ _('restore_backup') }}
                        </button>
                    </div>
                </div>
            </div>
            <p class="form-hint" style="margin-top: var(--space-sm);">
                {{ _('restore_confirm') }}
            </p>
        </div>

        <!-- BLOCK: API Tokens -->
        <div class="card" style="margin-top: var(--space-lg);">
            <div style="display:flex; align-items:center; justify-content:space-between; margin-bottom: var(--space-md);">
                <h3 class="card-title" style="margin:0;">🔑 {{ _('api_tokens_title') }}</h3>
                <button type="button" class="btn btn-primary btn-sm" onclick="openCreateTokenModal()">
                    {{ icon('plus') }} {{ _('api_tokens_create') }}
                </button>
            </div>
            <p class="form-hint" style="margin-bottom: var(--space-md);">
                {{ _('api_tokens_hint') }}
            </p>
            <div id="tokensList">
                <div class="form-hint" id="tokensEmptyState">{{ _('api_tokens_empty') }}</div>
            </div>
        </div>

        <!-- BLOCK: About & Updates -->
        <div class="card" style="margin-top: var(--space-lg);">
            <h3 class="card-title" style="margin-bottom: var(--space-lg);">ℹ️ {{ _('about_title') }}</h3>
            <div style="display: flex; flex-direction: column; gap: var(--space-md);">
                <div style="display: flex; justify-content: space-between; align-items: center; padding: var(--space-sm) 0; border-bottom: 1px solid var(--border-color);">
                    <span style="font-weight: 500;">{{ _('current_version') }}</span>
                    <span class="badge badge-info" id="currentVersionBadge" style="font-size: 0.95rem;">{{ current_version }}</span>
                </div>
                
                <div id="updateStatus" class="hidden" style="padding: var(--space-md); border-radius: var(--radius-md); background: var(--bg-primary); text-align: center;">
                    <!-- Updated via JS -->
                </div>

                <div style="display: flex; gap: var(--space-sm); margin-top: var(--space-sm); flex-wrap: wrap;">
                    <button type="button" class="btn btn-primary" onclick="upgradePanel()" id="upgradePanelBtn" style="flex:1; min-width:180px;">
                        <span id="upgradePanelBtnText">⬆ {{ _('upgrade_panel') }}</span>
                        <div class="spinner hidden" id="upgradePanelSpinner" style="width:14px; height:14px;"></div>
                    </button>
                    <button type="button" class="btn btn-secondary" onclick="checkForUpdates()" id="checkUpdateBtn" style="flex:1; min-width:140px;">
                        <span id="checkUpdateBtnText">🔄 {{ _('check_updates') }}</span>
                        <div class="spinner hidden" id="checkUpdateSpinner" style="width:14px; height:14px;"></div>
                    </button>
                    <button type="button" class="btn btn-secondary hidden" onclick="applyPanelUpdate()" id="applyUpdateBtn" style="flex:1; min-width:140px;">
                        <span id="applyUpdateBtnText">⬆ {{ _('apply_update') }}</span>
                        <div class="spinner hidden" id="applyUpdateSpinner" style="width:14px; height:14px;"></div>
                    </button>
                    <a href="https://git.evilfox.cc/test2/Amnezia-Web-Panel-main/releases" target="_blank" class="btn btn-secondary hidden" id="downloadUpdateBtn" style="flex:1; min-width:140px; text-decoration: none; justify-content: center;">
                        ⬇️ {{ _('download_update') }}
                    </a>
                </div>
                <p class="form-hint" id="updateModeHint" style="margin:0;">{{ _('auto_update_hint') }}</p>
            </div>
        </div>
    </div>
</div>

<div style="margin-top: var(--space-xl); text-align: right;">
    <button class="btn btn-primary btn-lg" onclick="saveSettings()" id="saveBtn">
        <span>{{ _('save_changes') }}</span>
        <div class="spinner hidden" id="saveSpinner"></div>
    </button>
</div>

</div>

<!-- ===== 3x-ui Server Modal ===== -->
<div class="modal-backdrop" id="xuiServerModal">
    <div class="modal" style="max-width:520px;">
        <div class="modal-header">
            <h2 class="modal-title" id="xuiServerModalTitle">{{ _('xui_server_add') }}</h2>
            <button class="modal-close" onclick="closeModal('xuiServerModal')">×</button>
        </div>
        <input type="hidden" id="xuiServerEditId" value="">
        <div class="form-group">
            <label class="form-label">{{ _('xui_server_name_label') }}</label>
            <input class="form-input" type="text" id="xuiServerName" placeholder="US / NL / Home">
            <div class="form-hint">{{ _('xui_server_name_hint') }}</div>
        </div>
        <div class="form-group">
            <label class="form-label">{{ _('xui_url_label') }}</label>
            <input class="form-input" type="url" id="xuiServerUrl" placeholder="https://panel.example.com:2053/path">
            <div class="form-hint">{{ _('xui_url_hint') }}</div>
        </div>
        <div class="form-group">
            <label class="form-label">{{ _('xui_sub_url_label') }}</label>
            <input class="form-input" type="url" id="xuiServerSubUrl" placeholder="https://sub.example.com:2096/sub">
            <div class="form-hint">{{ _('xui_sub_url_hint') }}</div>
        </div>
        <div class="form-group">
            <label class="form-label">{{ _('xui_api_token_label') }}</label>
            <input class="form-input" type="password" id="xuiServerToken" placeholder="{{ _('xui_api_token_placeholder') }}" autocomplete="off">
            <div class="form-hint">{{ _('xui_api_token_hint') }}</div>
        </div>
        <div style="display:grid; grid-template-columns:1fr 1fr; gap:var(--space-sm);">
            <div class="form-group">
                <label class="form-label">{{ _('xui_username_label') }}</label>
                <input class="form-input" type="text" id="xuiServerUser" autocomplete="off">
            </div>
            <div class="form-group">
                <label class="form-label">{{ _('xui_password_label') }}</label>
                <input class="form-input" type="password" id="xuiServerPass" autocomplete="off">
            </div>
        </div>
        <div class="form-group">
            <label style="display:flex; align-items:center; gap:var(--space-sm); cursor:pointer;">
                <input type="checkbox" id="xuiServerEnabled" checked> {{ _('enabled') if False else 'Enabled' }}
            </label>
        </div>
        <div class="form-group">
            <label style="display:flex; align-items:center; gap:var(--space-sm); cursor:pointer;">
                <input type="checkbox" id="xuiServerSyncUsers"> {{ _('enable_sync') }}
            </label>
        </div>
        <div class="modal-footer">
            <button class="btn btn-secondary" onclick="closeModal('xuiServerModal')">{{ _('cancel') }}</button>
            <button class="btn btn-primary" onclick="saveXuiServer()" id="xuiServerSaveBtn">
                <span id="xuiServerSaveText">{{ _('save') }}</span>
                <div class="spinner hidden" id="xuiServerSaveSpinner" style="width:14px;height:14px;"></div>
            </button>
        </div>
    </div>
</div>

<!-- ===== Create API Token Modal ===== -->
<div class="modal-backdrop" id="createTokenModal">
    <div class="modal" style="max-width: 460px;">
        <div class="modal-header">
            <h2 class="modal-title">{{ _('api_tokens_create_title') }}</h2>
            <button class="modal-close" onclick="closeModal('createTokenModal')">×</button>
        </div>
        <div class="form-group">
            <label class="form-label">{{ _('api_tokens_name_label') }}</label>
            <input class="form-input" type="text" id="createTokenName"
                placeholder="{{ _('api_tokens_name_placeholder') }}" maxlength="100">
            <div class="form-hint">{{ _('api_tokens_name_hint') }}</div>
        </div>
        <div id="createTokenError" style="color: var(--danger, #ef4444); font-size: 0.85rem; margin-bottom: var(--space-sm);"></div>
        <div class="modal-footer">
            <button class="btn btn-secondary" onclick="closeModal('createTokenModal')">{{ _('cancel') }}</button>
            <button class="btn btn-primary" onclick="submitCreateToken()" id="createTokenBtn">
                {{ _('api_tokens_create') }}
            </button>
        </div>
    </div>
</div>

<!-- ===== Newly-Created Token Modal (one-time display) ===== -->
<div class="modal-backdrop" id="newTokenModal">
    <div class="modal" style="max-width: 560px;">
        <div class="modal-header">
            <h2 class="modal-title">{{ _('api_tokens_created_title') }}</h2>
            <button class="modal-close" onclick="closeModal('newTokenModal')">×</button>
        </div>
        <div class="form-group">
            <label class="form-label">{{ _('api_tokens_name_label') }}</label>
            <div id="newTokenName" style="font-weight: 600;"></div>
        </div>
        <div class="form-group">
            <label class="form-label">{{ _('api_tokens_value_label') }}</label>
            <input class="form-input" type="text" id="newTokenValue" readonly
                style="font-family: 'SF Mono', monospace; font-size: 0.85rem;">
        </div>
        <div style="background: rgba(245, 158, 11, 0.12); border: 1px solid rgba(245, 158, 11, 0.4); border-radius: var(--radius-md); padding: var(--space-md); margin-bottom: var(--space-md);">
            ⚠️ <strong>{{ _('api_tokens_warning_title') }}</strong>
            <div class="form-hint" style="margin-top: 4px;">{{ _('api_tokens_warning_body') }}</div>
        </div>
        <div class="form-hint" style="margin-bottom: var(--space-sm); font-family: 'SF Mono', monospace; font-size: 0.78rem; padding: var(--space-sm); background: var(--bg-primary); border-radius: var(--radius-sm);">
            curl -H "Authorization: Bearer &lt;your_token&gt;" {{ request.url.scheme }}://{{ request.url.netloc }}/api/users
        </div>
        <div class="modal-footer">
            <button class="btn btn-secondary" onclick="copyNewToken()">{{ icon('copy') }} {{ _('copy') }}</button>
            <button class="btn btn-primary" onclick="closeModal('newTokenModal')">{{ _('done') }}</button>
        </div>
    </div>
</div>

<script>
    const serversData = {{ servers | tojson }};
    const botCurrentlyRunning = {{ 'true' if bot_running else 'false' }};

    function updateProtocolsForSync() {
        const serverIdx = document.querySelector('[name="remnawave_server_id"]').value;
        const protoSelect = document.getElementById('syncProtocolSelect');
        protoSelect.innerHTML = '';

        if (serverIdx === '' || !serversData[serverIdx]) return;

        const protocols = serversData[serverIdx].protocols || {};
        let count = 0;

        for (const [key, info] of Object.entries(protocols)) {
            if (info.installed) {
                const opt = document.createElement('option');
                opt.value = key;
                opt.textContent = key === 'awg' ? 'AmneziaWG' : (key === 'awg2' ? 'AmneziaWG 2.0' : (key === 'awg_legacy' ? 'AWG Legacy' : (key === 'xray' ? 'Xray' : key.toUpperCase())));
                if (key === "{{ settings.sync.remnawave_protocol }}") opt.selected = true;
                protoSelect.appendChild(opt);
                count++;
            }
        }

        if (count === 0) {
            const opt = document.createElement('option');
            opt.textContent = _('no_protocols');
            opt.disabled = true;
            protoSelect.appendChild(opt);
        }
    }

    document.querySelector('[name="remnawave_sync"]').addEventListener('change', (e) => {
        document.getElementById('remnawaveFields').style.display = e.target.checked ? 'block' : 'none';
    });

    document.querySelector('[name="xui_sync"]').addEventListener('change', (e) => {
        document.getElementById('xuiFields').style.display = e.target.checked ? 'block' : 'none';
    });

    function updateProtocolsForXuiSync() {
        const serverIdx = document.querySelector('[name="xui_server_id"]').value;
        const protoSelect = document.getElementById('xuiSyncProtocolSelect');
        protoSelect.innerHTML = '';

        if (serverIdx === '' || !serversData[serverIdx]) return;

        const protocols = serversData[serverIdx].protocols || {};
        let count = 0;

        for (const [key, info] of Object.entries(protocols)) {
            if (info.installed) {
                const opt = document.createElement('option');
                opt.value = key;
                opt.textContent = key === 'awg' ? 'AmneziaWG' : (key === 'awg2' ? 'AmneziaWG 2.0' : (key === 'awg_legacy' ? 'AWG Legacy' : (key === 'xray' ? 'Xray' : key.toUpperCase())));
                if (key === "{{ settings.sync.xui_protocol }}") opt.selected = true;
                protoSelect.appendChild(opt);
                count++;
            }
        }

        if (count === 0) {
            const opt = document.createElement('option');
            opt.textContent = _('no_protocols');
            opt.disabled = true;
            protoSelect.appendChild(opt);
        }
    }

    function openXuiServerModal(server) {
        document.getElementById('xuiServerEditId').value = server?.id || '';
        document.getElementById('xuiServerModalTitle').textContent = server?.id ? (_('edit') + ' — 3x-ui') : _('xui_server_add');
        document.getElementById('xuiServerName').value = server?.name || '';
        document.getElementById('xuiServerUrl').value = server?.url || '';
        document.getElementById('xuiServerSubUrl').value = server?.sub_url || '';
        document.getElementById('xuiServerToken').value = '';
        document.getElementById('xuiServerUser').value = server?.username || '';
        document.getElementById('xuiServerPass').value = '';
        document.getElementById('xuiServerEnabled').checked = server ? !!server.enabled : true;
        document.getElementById('xuiServerSyncUsers').checked = !!(server && server.sync_users);
        openModal('xuiServerModal');
    }

    function editXuiServer(server) { openXuiServerModal(server); }

    async function saveXuiServer() {
        const id = document.getElementById('xuiServerEditId').value;
        const body = {
            name: document.getElementById('xuiServerName').value.trim(),
            url: document.getElementById('xuiServerUrl').value.trim(),
            sub_url: document.getElementById('xuiServerSubUrl').value.trim(),
            api_token: document.getElementById('xuiServerToken').value,
            username: document.getElementById('xuiServerUser').value.trim(),
            password: document.getElementById('xuiServerPass').value,
            enabled: document.getElementById('xuiServerEnabled').checked,
            sync_users: document.getElementById('xuiServerSyncUsers').checked,
            default_inbound_id: 0,
        };
        if (!body.url) { showToast(_('error') + ': URL', 'error'); return; }
        const btn = document.getElementById('xuiServerSaveBtn');
        const text = document.getElementById('xuiServerSaveText');
        const spinner = document.getElementById('xuiServerSaveSpinner');
        btn.disabled = true; text.textContent = _('saving') || 'Saving...'; spinner.classList.remove('hidden');
        try {
            if (id) await apiCall(`/api/settings/xui/servers/${encodeURIComponent(id)}`, 'PUT', body);
            else await apiCall('/api/settings/xui/servers', 'POST', body);
            showToast(_('saved') || 'OK', 'success');
            closeModal('xuiServerModal');
            setTimeout(() => location.reload(), 400);
        } catch (err) {
            showToast(_('error') + ': ' + err.message, 'error');
        } finally {
            btn.disabled = false; text.textContent = _('save'); spinner.classList.add('hidden');
        }
    }

    async function deleteXuiServer(id) {
        if (!confirm(_('xui_server_delete_confirm') || 'Delete this 3x-ui server?')) return;
        try {
            await apiCall(`/api/settings/xui/servers/${encodeURIComponent(id)}`, 'DELETE');
            showToast(_('deleted') || 'OK', 'success');
            setTimeout(() => location.reload(), 400);
        } catch (err) {
            showToast(_('error') + ': ' + err.message, 'error');
        }
    }

    async function loadGuestInbounds() {
        const select = document.getElementById('guest_create_inbound_id');
        if (!select) return;
        const preferred = {{ settings.guest.create_inbound_id | default(0) | int }};
        select.innerHTML = `<option value="">${_('invite_inbound_loading')}</option>`;
        try {
            const panelSel = document.getElementById('guest_create_xui_panel');
            const panelId = panelSel ? panelSel.value : '';
            const q = panelId ? `?panel_id=${encodeURIComponent(panelId)}` : '';
            const res = await fetch('/api/settings/xui/inbounds' + q);
            const data = await res.json();
            if (!res.ok) throw new Error(data.error || 'Failed to load inbounds');
            const list = data.inbounds || [];
            if (!list.length) {
                select.innerHTML = `<option value="">${_('invite_inbound_empty')}</option>`;
                return;
            }
            select.innerHTML = '';
            list.forEach((ib, idx) => {
                const opt = document.createElement('option');
                opt.value = ib.id;
                opt.textContent = `${ib.remark || 'VLESS'} (:${ib.port})`;
                if (preferred && String(ib.id) === String(preferred)) opt.selected = true;
                else if (!preferred && idx === 0) opt.selected = true;
                select.appendChild(opt);
            });
        } catch (err) {
            console.warn('loadGuestInbounds:', err);
            select.innerHTML = `<option value="">${_('error')}: ${err.message}</option>`;
        }
    }

    document.getElementById('syncCreateConns').addEventListener('change', (e) => {
        document.getElementById('autoConnFields').style.display = e.target.checked ? 'block' : 'none';
        if (e.target.checked) updateProtocolsForSync();
    });

    document.getElementById('xuiSyncCreateConns').addEventListener('change', (e) => {
        document.getElementById('xuiAutoConnFields').style.display = e.target.checked ? 'block' : 'none';
        if (e.target.checked) updateProtocolsForXuiSync();
    });

    document.getElementById('ssl_enabled').addEventListener('change', (e) => {
        document.getElementById('sslFields').style.display = e.target.checked ? 'block' : 'none';
    });

    let tunnelStatusTimer = null;

    function copyElementText(id) {
        const el = document.getElementById(id);
        if (el) copyToClipboard(el.textContent.trim());
    }

    function renderTunnelUrls(provider, urls) {
        const el = document.getElementById(`${provider}PublicUrls`);
        if (!el) return;
        if (!urls || !urls.length) {
            el.className = 'tunnel-url-box tunnel-url-box--empty';
            el.textContent = _('tunnel_no_public_url');
            return;
        }
        el.className = 'tunnel-url-box';
        el.innerHTML = urls.map((url, idx) => `
            <div class="tunnel-url-row">
                <code id="${provider}PublicUrl${idx}">${escapeHTML(url)}</code>
                <button type="button" class="btn btn-secondary btn-sm" onclick="copyElementText('${provider}PublicUrl${idx}')">${_('copy')}</button>
            </div>
        `).join('');
    }

    function setTunnelStatusPill(badge, { ok, info, text }) {
        if (!badge) return;
        badge.className = 'tunnel-status-pill' + (ok ? ' tunnel-status-pill--ok' : (info ? ' tunnel-status-pill--info' : ''));
        badge.textContent = text;
    }

    function updateTunnelProvider(provider, status) {
        const badge = document.getElementById(`${provider}InstallBadge`);
        const text = document.getElementById(`${provider}TunnelBtnText`);
        const startBtn = document.getElementById(`${provider}TunnelBtn`);
        const stopBtn = document.getElementById(`${provider}StopBtn`);
        const deleteBtn = document.getElementById(`${provider}DeleteBtn`);
        const card = document.getElementById(`tunnelCard-${provider}`);
        if (!badge || !text) return;

        const running = !!status.running;
        setTunnelStatusPill(badge, {
            ok: running,
            info: !running && status.installed,
            text: running ? _('tunnel_running') : (status.installed ? _('installed') : _('not_installed')),
        });
        text.textContent = running ? _('tunnel_running') : (status.installed ? _('tunnel_enable') : _('tunnel_install_enable'));
        if (startBtn) startBtn.disabled = running;
        if (stopBtn) stopBtn.classList.toggle('hidden', !running);
        if (deleteBtn) deleteBtn.classList.toggle('hidden', !status.installed);
        if (card) card.classList.toggle('tunnel-card--running', running);
        renderTunnelUrls(provider, status.public_urls || (status.public_url ? [status.public_url] : []));
    }

    async function loadTunnelStatus() {
        try {
            const data = await apiCall('/api/settings/tunnels/status');
            if (data.local_server) document.getElementById('localServerUrl').textContent = data.local_server;
            updateTunnelProvider('cloudflare', data.cloudflare || {});
            updateTunnelProvider('ngrok', data.ngrok || {});
            updateWarpStatus(data.warp || {});
            updateNordvpnStatus(data.nordvpn || {});
        } catch (err) {
            showToast(`${_('error')}: ` + err.message, 'error');
        }
    }

    function updateWarpStatus(status) {
        const badge = document.getElementById('warpInstallBadge');
        const statusText = document.getElementById('warpStatusText');
        const hintText = document.getElementById('warpHintText');
        const connectBtn = document.getElementById('warpConnectBtn');
        const disconnectBtn = document.getElementById('warpDisconnectBtn');
        const connectText = document.getElementById('warpConnectBtnText');
        const card = document.getElementById('tunnelCard-warp');
        if (!badge || !statusText || !connectBtn || !disconnectBtn || !connectText) return;

        const installed = !!status.installed;
        const connected = !!status.connected || status.status === 'connected';
        setTunnelStatusPill(badge, {
            ok: connected,
            info: !connected && installed,
            text: connected ? _('warp_connected') : (installed ? _('installed') : _('not_installed')),
        });

        const statusKey = `warp_status_${status.status || 'unknown'}`;
        statusText.textContent = _(statusKey) || status.status || _('warp_status_unknown');
        hintText.textContent = status.last_error || (installed ? _('warp_hint') : (status.install_hint || _('warp_install_hint')));
        connectText.textContent = installed ? _('warp_connect') : _('warp_install_required');
        connectBtn.disabled = connected;
        disconnectBtn.classList.toggle('hidden', !connected);
        if (card) card.classList.toggle('tunnel-card--connected', connected);
    }

    async function connectWarp() {
        const btn = document.getElementById('warpConnectBtn');
        const spinner = document.getElementById('warpConnectSpinner');
        const text = document.getElementById('warpConnectBtnText');
        btn.disabled = true;
        spinner.classList.remove('hidden');
        text.textContent = _('loading');

        try {
            const status = await apiCall('/api/settings/warp/connect', 'POST');
            updateWarpStatus(status);
            showToast(_('warp_connected'), 'success');
        } catch (err) {
            showToast(`${_('error')}: ` + err.message, 'error');
            await loadTunnelStatus();
        } finally {
            spinner.classList.add('hidden');
        }
    }

    async function disconnectWarp() {
        const btn = document.getElementById('warpDisconnectBtn');
        const spinner = document.getElementById('warpDisconnectSpinner');
        const text = document.getElementById('warpDisconnectBtnText');
        btn.disabled = true;
        spinner.classList.remove('hidden');
        text.textContent = _('loading');

        try {
            const status = await apiCall('/api/settings/warp/disconnect', 'POST');
            updateWarpStatus(status);
            showToast(_('warp_disconnected'), 'success');
        } catch (err) {
            showToast(`${_('error')}: ` + err.message, 'error');
            await loadTunnelStatus();
        } finally {
            btn.disabled = false;
            text.textContent = _('warp_disconnect');
            spinner.classList.add('hidden');
        }
    }

    function updateNordvpnStatus(status) {
        const badge = document.getElementById('nordvpnInstallBadge');
        const statusText = document.getElementById('nordvpnStatusText');
        const serverText = document.getElementById('nordvpnServerText');
        const hintText = document.getElementById('nordvpnHintText');
        const connectBtn = document.getElementById('nordvpnConnectBtn');
        const disconnectBtn = document.getElementById('nordvpnDisconnectBtn');
        const connectText = document.getElementById('nordvpnConnectBtnText');
        const card = document.getElementById('tunnelCard-nordvpn');
        if (!badge || !statusText || !connectBtn || !disconnectBtn || !connectText) return;

        const installed = !!status.installed;
        const connected = !!status.connected || status.status === 'connected';
        setTunnelStatusPill(badge, {
            ok: connected,
            info: !connected && installed,
            text: connected ? _('nordvpn_connected') : (installed ? _('installed') : _('not_installed')),
        });

        const statusKey = `nordvpn_status_${status.status || 'unknown'}`;
        statusText.textContent = _(statusKey) || status.status || _('nordvpn_status_unknown');
        if (serverText) {
            const serverLine = status.server || '';
            serverText.textContent = serverLine;
            serverText.classList.toggle('hidden', !serverLine);
        }
        hintText.textContent = status.last_error || (installed ? _('nordvpn_hint') : (status.install_hint || _('nordvpn_install_hint')));
        connectText.textContent = installed ? _('nordvpn_connect') : _('nordvpn_install_required');
        connectBtn.disabled = connected;
        disconnectBtn.classList.toggle('hidden', !connected);
        if (card) card.classList.toggle('tunnel-card--connected', connected);
    }

    async function connectNordvpn() {
        const btn = document.getElementById('nordvpnConnectBtn');
        const spinner = document.getElementById('nordvpnConnectSpinner');
        const text = document.getElementById('nordvpnConnectBtnText');
        btn.disabled = true;
        spinner.classList.remove('hidden');
        text.textContent = _('loading');

        try {
            const country = (document.getElementById('nordvpnCountry') || {}).value || '';
            const city = (document.getElementById('nordvpnCity') || {}).value || '';
            const status = await apiCall('/api/settings/nordvpn/connect', 'POST', {
                country: country.trim(),
                city: city.trim(),
            });
            updateNordvpnStatus(status);
            showToast(_('nordvpn_connected'), 'success');
        } catch (err) {
            showToast(`${_('error')}: ` + err.message, 'error');
            await loadTunnelStatus();
        } finally {
            spinner.classList.add('hidden');
        }
    }

    async function disconnectNordvpn() {
        const btn = document.getElementById('nordvpnDisconnectBtn');
        const spinner = document.getElementById('nordvpnDisconnectSpinner');
        const text = document.getElementById('nordvpnDisconnectBtnText');
        btn.disabled = true;
        spinner.classList.remove('hidden');
        text.textContent = _('loading');

        try {
            const status = await apiCall('/api/settings/nordvpn/disconnect', 'POST');
            updateNordvpnStatus(status);
            showToast(_('nordvpn_disconnected'), 'success');
        } catch (err) {
            showToast(`${_('error')}: ` + err.message, 'error');
            await loadTunnelStatus();
        } finally {
            btn.disabled = false;
            text.textContent = _('nordvpn_disconnect');
            spinner.classList.add('hidden');
        }
    }

    async function enableTunnel(provider) {
        const btn = document.getElementById(`${provider}TunnelBtn`);
        const spinner = document.getElementById(`${provider}TunnelSpinner`);
        const text = document.getElementById(`${provider}TunnelBtnText`);
        btn.disabled = true;
        spinner.classList.remove('hidden');
        text.textContent = _('loading');

        try {
            const current = await apiCall('/api/settings/tunnels/status');
            const providerStatus = current[provider] || {};
            if (!providerStatus.installed) {
                text.textContent = _('installing');
                await apiCall(`/api/settings/tunnels/${provider}/install`, 'POST');
            }

            text.textContent = _('tunnel_starting');
            const body = provider === 'ngrok' ? { authtoken: document.getElementById('ngrokAuthtoken').value.trim() } : {};
            const status = await apiCall(`/api/settings/tunnels/${provider}/start`, 'POST', body);
            updateTunnelProvider(provider, status);
            showToast(status.public_url ? _('tunnel_started') : _('tunnel_waiting_url'), 'success');
            if (!tunnelStatusTimer) tunnelStatusTimer = setInterval(loadTunnelStatus, 5000);
        } catch (err) {
            showToast(`${_('error')}: ` + err.message, 'error');
            await loadTunnelStatus();
        } finally {
            btn.disabled = false;
            spinner.classList.add('hidden');
        }
    }

    async function stopTunnel(provider) {
        const btn = document.getElementById(`${provider}StopBtn`);
        const spinner = document.getElementById(`${provider}StopSpinner`);
        const text = document.getElementById(`${provider}StopBtnText`);
        btn.disabled = true;
        spinner.classList.remove('hidden');
        text.textContent = _('tunnel_stopping');

        try {
            const status = await apiCall(`/api/settings/tunnels/${provider}/stop`, 'POST');
            updateTunnelProvider(provider, status);
            showToast(_('tunnel_stopped'), 'success');
        } catch (err) {
            showToast(`${_('error')}: ` + err.message, 'error');
            await loadTunnelStatus();
        } finally {
            btn.disabled = false;
            text.textContent = _('tunnel_stop');
            spinner.classList.add('hidden');
        }
    }

    async function deleteTunnel(provider) {
        if (!confirm(_('tunnel_delete_confirm'))) return;
        const btn = document.getElementById(`${provider}DeleteBtn`);
        const spinner = document.getElementById(`${provider}DeleteSpinner`);
        const text = document.getElementById(`${provider}DeleteBtnText`);
        btn.disabled = true;
        spinner.classList.remove('hidden');
        text.textContent = _('deleting');

        try {
            const status = await apiCall(`/api/settings/tunnels/${provider}`, 'DELETE');
            updateTunnelProvider(provider, status);
            showToast(_('tunnel_deleted'), 'success');
        } catch (err) {
            showToast(`${_('error')}: ` + err.message, 'error');
            await loadTunnelStatus();
        } finally {
            btn.disabled = false;
            text.textContent = _('tunnel_delete');
            spinner.classList.add('hidden');
        }
    }

    async function syncRemnawaveNow() {
        const btn = document.getElementById('syncNowBtn');
        const text = document.getElementById('syncNowBtnText');
        const spinner = document.getElementById('syncNowSpinner');

        btn.disabled = true;
        text.textContent = _('sync_running');
        spinner.classList.remove('hidden');

        try {
            const res = await fetch('/api/settings/sync_now', { method: 'POST' });
            const data = await res.json();
            if (data.status === 'success') {
                showToast(_('sync_success').replace('{}', data.count), 'success');
                setTimeout(() => window.location.reload(), 1500);
            } else {
                throw new Error(data.message || 'Error occurred');
            }
        } catch (err) {
            showToast(`${_('error')}: ` + err.message, 'error');
        } finally {
            btn.disabled = false;
            text.textContent = `🔄 ${_('sync_now_btn')}`;
            spinner.classList.add('hidden');
        }
    }

    async function deleteSyncRemnawave() {
        if (!confirm(_('delete_sync_confirm'))) return;

        const btn = document.getElementById('syncDelBtn');
        const text = document.getElementById('syncDelBtnText');
        const spinner = document.getElementById('syncDelSpinner');

        btn.disabled = true;
        text.textContent = _('deleting');
        spinner.classList.remove('hidden');

        try {
            const res = await fetch('/api/settings/sync_delete', { method: 'POST' });
            const data = await res.json();
            if (data.status === 'success') {
                showToast(_('sync_deleted').replace('{}', data.count), 'success');
                setTimeout(() => window.location.reload(), 1500);
            }
        } catch (err) {
            showToast(`${_('error')}: ` + err.message, 'error');
        } finally {
            btn.disabled = false;
            text.innerHTML = `${uiIcon('trash')} ${_('delete_sync_btn')}`;
            spinner.classList.add('hidden');
        }
    }

    async function syncXuiNow() {
        const btn = document.getElementById('xuiSyncNowBtn');
        const text = document.getElementById('xuiSyncNowBtnText');
        const spinner = document.getElementById('xuiSyncNowSpinner');
        const syncForm = document.getElementById('syncForm');

        btn.disabled = true;
        text.textContent = _('sync_running');
        spinner.classList.remove('hidden');

        try {
            const payload = {
                xui_sync: true,
                xui_sync_users: true,
                xui_url: syncForm.xui_url.value.trim(),
                xui_username: syncForm.xui_username.value.trim(),
                xui_password: syncForm.xui_password.value,
                xui_api_token: syncForm.xui_api_token.value.trim(),
                xui_create_conns: syncForm.xui_create_conns.checked,
                xui_server_id: parseInt(syncForm.xui_server_id.value || '0'),
                xui_protocol: syncForm.xui_protocol.value,
                xui_inbound_id: parseInt(syncForm.xui_inbound_id.value || '0'),
                xui_sub_url: (syncForm.xui_sub_url && syncForm.xui_sub_url.value || '').trim()
            };
            const res = await fetch('/api/settings/xui_sync_now', {
                method: 'POST',
                headers: { 'Content-Type': 'application/json' },
                body: JSON.stringify(payload)
            });
            const data = await res.json();
            if (data.status === 'success') {
                showToast(_('sync_success').replace('{}', data.count), 'success');
                setTimeout(() => window.location.reload(), 1500);
            } else {
                throw new Error(data.message || data.error || 'Error occurred');
            }
        } catch (err) {
            showToast(`${_('error')}: ` + err.message, 'error');
        } finally {
            btn.disabled = false;
            text.textContent = `🔄 ${_('sync_now_btn')}`;
            spinner.classList.add('hidden');
        }
    }

    async function deleteSyncXui() {
        if (!confirm(_('delete_sync_confirm'))) return;

        const btn = document.getElementById('xuiSyncDelBtn');
        const text = document.getElementById('xuiSyncDelBtnText');
        const spinner = document.getElementById('xuiSyncDelSpinner');

        btn.disabled = true;
        text.textContent = _('deleting');
        spinner.classList.remove('hidden');

        try {
            const res = await fetch('/api/settings/xui_sync_delete', { method: 'POST' });
            const data = await res.json();
            if (data.status === 'success') {
                showToast(_('sync_deleted').replace('{}', data.count), 'success');
                setTimeout(() => window.location.reload(), 1500);
            }
        } catch (err) {
            showToast(`${_('error')}: ` + err.message, 'error');
        } finally {
            btn.disabled = false;
            text.innerHTML = `${uiIcon('trash')} ${_('delete_sync_btn')}`;
            spinner.classList.add('hidden');
        }
    }

    async function saveSettings() {
        const btn = document.getElementById('saveBtn');
        const spinner = document.getElementById('saveSpinner');
        btn.disabled = true;
        spinner.classList.remove('hidden');

        const appForm = document.getElementById('appearanceForm');
        const syncForm = document.getElementById('syncForm');

        const appearance = {
            title: appForm.title.value,
            logo: appForm.logo.value,
            subtitle: appForm.subtitle.value
        };

        const sync = {
            remnawave_url: syncForm.remnawave_url.value,
            remnawave_api_key: syncForm.remnawave_api_key.value,
            remnawave_sync: syncForm.remnawave_sync.checked,
            remnawave_sync_users: syncForm.remnawave_sync_users.checked,
            remnawave_create_conns: syncForm.remnawave_create_conns.checked,
            remnawave_server_id: parseInt(syncForm.remnawave_server_id.value || '0'),
            remnawave_protocol: syncForm.remnawave_protocol.value,
            xui_sync: syncForm.xui_sync.checked,
            xui_url: syncForm.xui_url.value,
            xui_username: syncForm.xui_username.value,
            xui_password: syncForm.xui_password.value,
            xui_api_token: syncForm.xui_api_token.value,
            xui_sync_users: syncForm.xui_sync_users.checked,
            xui_create_conns: syncForm.xui_create_conns.checked,
            xui_server_id: parseInt(syncForm.xui_server_id.value || '0'),
            xui_protocol: syncForm.xui_protocol.value,
            xui_inbound_id: parseInt(syncForm.xui_inbound_id.value || '0'),
            xui_sub_url: (syncForm.xui_sub_url && syncForm.xui_sub_url.value || '').trim()
        };


        const captcha = {
            enabled: document.getElementById('captcha_enabled').checked
        };

        const telegram = {
            token: document.getElementById('tg_token').value.trim(),
            enabled: botCurrentlyRunning
        };

        const ssl = {
            enabled: document.getElementById('ssl_enabled').checked,
            domain: document.getElementById('ssl_domain').value.trim(),
            cert_path: document.getElementById('ssl_cert_path').value.trim(),
            key_path: document.getElementById('ssl_key_path').value.trim(),
            cert_text: document.getElementById('ssl_cert_text').value.trim(),
            key_text: document.getElementById('ssl_key_text').value.trim(),
            panel_port: parseInt(document.getElementById('panel_port').value || '5000')
        };

        let createProtocol = 'xui';
        let createServerId = 0;
        const guestServerVal = document.getElementById('guest_create_server')?.value || 'xui';
        const guestProtoVal = document.getElementById('guest_create_protocol')?.value || '';
        if (guestServerVal === 'xui' || guestProtoVal === 'xui') {
            createProtocol = 'xui';
            createServerId = 0;
        } else {
            createProtocol = guestProtoVal;
            createServerId = parseInt(guestServerVal || '0', 10) || 0;
        }

        const guest = {
            enabled: document.getElementById('guest_enabled').checked,
            token: document.getElementById('guest_token').value || '',
            password: document.getElementById('guest_password').value || '',
            clear_password: !!(document.getElementById('guest_clear_password') && document.getElementById('guest_clear_password').checked),
            user_id: document.getElementById('guest_user_id').value || '',
            allow_create: document.getElementById('guest_allow_create').checked,
            create_protocol: createProtocol,
            create_server_id: createServerId,
            create_inbound_id: parseInt(document.getElementById('guest_create_inbound_id').value || '0'),
            create_xui_panel_id: document.getElementById('guest_create_xui_panel')?.value || '',
        };

        try {
            const res = await fetch('/api/settings/save', {
                method: 'POST',
                headers: { 'Content-Type': 'application/json' },
                body: JSON.stringify({ appearance, sync, captcha, telegram, ssl, guest })
            });
            if (!res.ok) throw new Error(_('error'));
            showToast(_('settings_saved'), 'success');
            setTimeout(() => window.location.reload(), 1000);
        } catch (err) {
            showToast(err.message, 'error');
        } finally {
            btn.disabled = false;
            spinner.classList.add('hidden');
        }
    }

    const guestServersData = {{ servers | default([]) | tojson }};
    const VPN_PROTO_ORDER = ['awg2', 'awg', 'awg_legacy', 'wireguard', 'xray', 'telemt', 'hysteria', 'naiveproxy'];
    const PROTO_TITLES = {
        awg2: 'AmneziaWG 2.0',
        awg: 'AmneziaWG',
        awg_legacy: 'AWG Legacy',
        wireguard: 'WireGuard',
        xray: 'Xray (VLESS-Reality)',
        telemt: 'Telemt',
        hysteria: 'Hysteria 2',
        naiveproxy: 'NaiveProxy',
        xui: '3x-ui VLESS',
    };
    function protoTitle(key) {
        const raw = String(key || '');
        const base = raw.split('__')[0];
        const title = PROTO_TITLES[base] || base.toUpperCase();
        const m = raw.match(/__(\d+)$/);
        return m ? `${title} #${m[1]}` : title;
    }

    function fillGuestProtocols() {
        const serverSel = document.getElementById('guest_create_server');
        const protoSel = document.getElementById('guest_create_protocol');
        if (!serverSel || !protoSel) return;
        const prefer = document.getElementById('guest_create_protocol_pref')?.value || protoSel.value || '';
        const serverVal = serverSel.value;
        protoSel.innerHTML = '';
        if (serverVal === 'xui') {
            const opt = document.createElement('option');
            opt.value = 'xui';
            opt.textContent = PROTO_TITLES.xui;
            protoSel.appendChild(opt);
            updateGuestCreateFields();
            return;
        }
        const server = guestServersData[parseInt(serverVal, 10)];
        const protocols = (server && server.protocols) || {};
        const installed = Object.keys(protocols).filter(k => {
            const info = protocols[k] || {};
            return !!info.installed && VPN_PROTO_ORDER.includes(k.split('__')[0]);
        }).sort((a, b) => {
            const ia = VPN_PROTO_ORDER.indexOf(a.split('__')[0]);
            const ib = VPN_PROTO_ORDER.indexOf(b.split('__')[0]);
            return (ia < 0 ? 99 : ia) - (ib < 0 ? 99 : ib) || a.localeCompare(b);
        });
        if (!installed.length) {
            const opt = document.createElement('option');
            opt.value = '';
            opt.disabled = true;
            opt.textContent = _('no_protocols');
            protoSel.appendChild(opt);
        } else {
            installed.forEach(key => {
                const opt = document.createElement('option');
                opt.value = key;
                opt.textContent = protoTitle(key);
                if (prefer && prefer === key) opt.selected = true;
                protoSel.appendChild(opt);
            });
        }
        updateGuestCreateFields();
    }

    function updateGuestCreateFields() {
        const v = document.getElementById('guest_create_protocol')?.value;
        const group = document.getElementById('guestInboundGroup');
        if (group) group.style.display = (v === 'xui') ? 'block' : 'none';
        if (v === 'xui') loadGuestInbounds();
    }

    fillGuestProtocols();
    if (document.getElementById('guest_create_protocol')?.value === 'xui') {
        loadGuestInbounds();
    }

    function copyGuestLink() {
        const el = document.getElementById('guest_link_display');
        if (el && el.value) copyToClipboard(el.value);
    }

    async function regenGuestToken() {
        if (!confirm(_('guest_regen_confirm'))) return;
        try {
            const res = await fetch('/api/settings/guest/regenerate_token', { method: 'POST' });
            const data = await res.json();
            if (!res.ok) throw new Error(data.error || _('error'));
            document.getElementById('guest_token').value = data.token;
            const link = `${window.location.origin}/guest/${data.token}`;
            document.getElementById('guest_link_display').value = link;
            showToast(_('guest_token_updated'), 'success');
        } catch (err) {
            showToast(`${_('error')}: ` + err.message, 'error');
        }
    }

    async function toggleBot() {
        const btn = document.getElementById('toggleBotBtn');
        const text = document.getElementById('toggleBotBtnText');
        const spinner = document.getElementById('toggleBotSpinner');
        btn.disabled = true;
        spinner.classList.remove('hidden');
        try {
            const res = await fetch('/api/settings/telegram/toggle', { method: 'POST' });
            const data = await res.json();
            if (!res.ok) throw new Error(data.error || _('error'));
            const running = data.bot_running;
            document.getElementById('botStatusBadge').className = running ? 'badge badge-success' : 'badge badge-secondary';
            document.getElementById('botStatusBadge').textContent = running ? _('bot_running') : _('bot_stopped');
            text.textContent = running ? _('bot_stop_btn') : _('bot_start_btn');
            showToast(running ? _('bot_started') : _('bot_stopped_msg'), 'success');
        } catch (err) {
            showToast(`${_('error')}: ` + err.message, 'error');
        } finally {
            btn.disabled = false;
            spinner.classList.add('hidden');
        }
    }

    async function handleRestore(e) {
        const file = e.target.files[0];
        if (!file) return;

        if (!confirm(_('restore_confirm'))) {
            e.target.value = '';
            return;
        }

        const btn = document.getElementById('restoreBtn');
        btn.disabled = true;
        const originalText = btn.innerHTML;
        btn.innerHTML = `<div class="spinner" style="width:14px; height:14px;"></div> ${_('loading')}`;

        const formData = new FormData();
        formData.append('file', file);

        try {
            const res = await fetch('/api/settings/backup/restore', {
                method: 'POST',
                body: formData
            });
            const data = await res.json();
            if (data.status === 'success') {
                showToast(_('restore_success'), 'success');
                setTimeout(() => window.location.reload(), 2000);
            } else {
                showToast(data.error || _('invalid_backup_file'), 'error');
            }
        } catch (err) {
            showToast(`${_('error')}: ` + err.message, 'error');
        } finally {
            btn.disabled = false;
            btn.innerHTML = originalText;
            e.target.value = '';
        }
    }

    // Init protocols on load
    if (document.getElementById('syncCreateConns').checked) {
        updateProtocolsForSync();
    }

    let latestUpdateInfo = null;

    async function checkForUpdates(silent) {
        const btn = document.getElementById('checkUpdateBtn');
        const text = document.getElementById('checkUpdateBtnText');
        const spinner = document.getElementById('checkUpdateSpinner');
        const statusDiv = document.getElementById('updateStatus');
        const downloadBtn = document.getElementById('downloadUpdateBtn');
        const applyBtn = document.getElementById('applyUpdateBtn');
        const modeHint = document.getElementById('updateModeHint');

        if (!silent) {
            btn.disabled = true;
            text.textContent = "{{ _('checking_updates')|default('Checking...') }}";
            spinner.classList.remove('hidden');
        }
        statusDiv.classList.add('hidden');
        downloadBtn.classList.add('hidden');
        applyBtn.classList.add('hidden');

        try {
            const data = await apiCall('/api/settings/check_updates');
            latestUpdateInfo = data;
            const latestVersion = data.latest_version || '';
            statusDiv.classList.remove('hidden');

            if (modeHint) {
                const method = data.update_mode || (data.mode && data.mode.update_method) || (data.mode && data.mode.mode) || '';
                if (!data.can_auto_update) {
                    if (method === 'docker') {
                        modeHint.textContent = "{{ _('auto_update_docker')|default('Docker: on the host run git pull && docker compose up -d --build.') }}";
                    } else {
                        modeHint.textContent = "{{ _('auto_update_manual')|default('One-click update needs a writable install directory or git clone.') }}";
                    }
                } else if (method === 'archive') {
                    modeHint.textContent = "{{ _('auto_update_archive')|default('One-click update downloads the release ZIP from git.evilfox.cc and restarts the panel.') }}";
                } else {
                    modeHint.textContent = "{{ _('auto_update_ready')|default('Git auto-update is available for this install.') }}";
                }
            }

            const upgradeBtn = document.getElementById('upgradePanelBtn');
            if (upgradeBtn) {
                upgradeBtn.disabled = false;
                upgradeBtn.title = data.can_auto_update ? '' : (modeHint ? modeHint.textContent : '');
            }

            if (data.update_available && latestVersion) {
                statusDiv.innerHTML = `<span style="color: var(--success); font-weight: bold;">{{ _('update_available')|default('Update available') }}: ${latestVersion}</span>`;
                statusDiv.style.border = '1px solid var(--success)';
                downloadBtn.href = data.html_url || data.releases_url || 'https://git.evilfox.cc/test2/Amnezia-Web-Panel-main/releases';
                downloadBtn.classList.remove('hidden');
                applyBtn.classList.remove('hidden');
            } else {
                statusDiv.innerHTML = `<span style="color: var(--text-muted);">{{ _('up_to_date')|default('Up to date') }}</span>`;
                statusDiv.style.border = '1px solid var(--border-color)';
            }
        } catch (err) {
            if (!silent) showToast('Failed to check for updates: ' + err.message, 'error');
        } finally {
            if (!silent) {
                btn.disabled = false;
                text.textContent = "🔄 {{ _('check_updates')|default('Check for updates') }}";
                spinner.classList.add('hidden');
            }
        }
    }

    async function waitForPanelRestart(timeoutMs = 120000, panelUrl) {
        const base = String(panelUrl || window.location.origin || '').replace(/\/$/, '');
        const started = Date.now();
        while (Date.now() - started < timeoutMs) {
            try {
                const res = await fetch(`${base}/api/health`, { cache: 'no-store' });
                if (res.ok) {
                    window.location.href = base + '/';
                    return true;
                }
            } catch (_) {}
            await new Promise((resolve) => setTimeout(resolve, 2000));
        }
        const hint = base ? ` ${base}` : '';
        showToast("{{ _('update_restart_timeout')|default('Panel did not come back in time. Refresh the page manually.') }}" + hint, 'error');
        return false;
    }

    async function applyPanelUpdate() {
        const applyBtn = document.getElementById('applyUpdateBtn');
        const applyText = document.getElementById('applyUpdateBtnText');
        const applySpinner = document.getElementById('applyUpdateSpinner');
        const target = (latestUpdateInfo && latestUpdateInfo.latest_version) || '';
        if (!target) {
            showToast("{{ _('update_no_target')|default('No target version. Check for updates first.') }}", 'error');
            return;
        }
        if (!confirm("{{ _('apply_update_confirm')|default('Install update from git.evilfox.cc and restart the panel?') }} " + target)) {
            return;
        }
        applyBtn.disabled = true;
        applyText.textContent = "{{ _('applying_update')|default('Updating…') }}";
        applySpinner.classList.remove('hidden');
        let restarting = false;
        try {
            const data = await apiCall('/api/settings/apply_update', 'POST', {
                target_version: target,
                allow_dirty: true,
            });
            showToast(data.message || "{{ _('update_restarting')|default('Updated. Restarting…') }}", 'success');
            restarting = true;
            applyText.textContent = "{{ _('update_waiting_restart')|default('Waiting for panel…') }}";
            await waitForPanelRestart(120000, data.panel_url);
        } catch (err) {
            showToast(_('error') + ': ' + err.message, 'error');
        } finally {
            if (!restarting) {
                applyBtn.disabled = false;
                applyText.textContent = "⬆ {{ _('apply_update')|default('Install update') }}";
                applySpinner.classList.add('hidden');
            }
        }
    }

    async function upgradePanel() {
        const btn = document.getElementById('upgradePanelBtn');
        const text = document.getElementById('upgradePanelBtnText');
        const spinner = document.getElementById('upgradePanelSpinner');
        const latest = (latestUpdateInfo && latestUpdateInfo.latest_version) || '';
        const confirmMsg = latest
            ? ("{{ _('upgrade_panel_confirm')|default('Download and install') }} " + latest + "?")
            : "{{ _('upgrade_panel_confirm_latest')|default('Check for updates and install the latest release?') }}";
        if (!confirm(confirmMsg)) return;

        btn.disabled = true;
        spinner.classList.remove('hidden');
        text.textContent = "{{ _('upgrade_panel_working')|default('Updating panel…') }}";
        let restarting = false;
        try {
            const data = await apiCall('/api/settings/upgrade_panel', 'POST', {});
            if (data.up_to_date) {
                showToast("{{ _('upgrade_panel_up_to_date')|default('Already on the latest version') }}", 'info');
                await checkForUpdates(true);
                return;
            }
            showToast(data.message || "{{ _('update_restarting')|default('Updated. Restarting…') }}", 'success');
            restarting = true;
            text.textContent = "{{ _('update_waiting_restart')|default('Waiting for panel…') }}";
            await waitForPanelRestart(120000, data.panel_url);
        } catch (err) {
            showToast(_('error') + ': ' + err.message, 'error');
            await checkForUpdates(true);
        } finally {
            if (!restarting) {
                btn.disabled = false;
                spinner.classList.add('hidden');
                text.textContent = "⬆ {{ _('upgrade_panel')|default('Update panel') }}";
            }
        }
    }

    // Auto-check once on Settings load
    setTimeout(() => checkForUpdates(true), 800);

    /* ========== API Tokens ========== */

    function fmtTokenDate(iso) {
        if (!iso) return _('api_tokens_never');
        const d = new Date(iso);
        return isNaN(d) ? iso : d.toLocaleString();
    }

    async function loadTokens() {
        try {
            const data = await apiCall('/api/settings/tokens');
            renderTokens(data.tokens || []);
        } catch (err) {
            showToast(err.message, 'error');
        }
    }

    function renderTokens(tokens) {
        const container = document.getElementById('tokensList');
        if (!container) return;
        if (!tokens.length) {
            container.innerHTML = `<div class="form-hint" id="tokensEmptyState">${_('api_tokens_empty')}</div>`;
            return;
        }
        container.innerHTML = tokens.map(t => `
            <div class="token-row" style="display:flex; align-items:center; justify-content:space-between; gap:var(--space-md); padding:var(--space-sm) 0; border-bottom:1px solid var(--border-color);">
                <div style="min-width:0; flex:1;">
                    <div style="font-weight:600;">${escapeHTML(t.name)}</div>
                    <div class="text-muted" style="font-size:0.78rem; font-family: 'SF Mono', monospace;">
                        <span>${escapeHTML(t.token_prefix || '')}…</span>
                        <span style="margin-left:var(--space-md);">${_('api_tokens_created')}: ${fmtTokenDate(t.created_at)}</span>
                        <span style="margin-left:var(--space-md);">${_('api_tokens_last_used')}: ${fmtTokenDate(t.last_used_at)}</span>
                        ${t.owner ? `<span style="margin-left:var(--space-md);">${_('api_tokens_owner')}: ${escapeHTML(t.owner)}</span>` : ''}
                    </div>
                </div>
                <button class="btn btn-danger btn-sm" onclick="revokeToken('${t.id}', '${escapeHTML(t.name)}')">
                    ${_('api_tokens_revoke')}
                </button>
            </div>
        `).join('');
    }

    function escapeHTML(s) {
        return String(s ?? '').replace(/[&<>"']/g, c => ({
            '&': '&amp;', '<': '&lt;', '>': '&gt;', '"': '&quot;', "'": '&#39;'
        }[c]));
    }

    function openCreateTokenModal() {
        document.getElementById('createTokenName').value = '';
        document.getElementById('createTokenError').textContent = '';
        openModal('createTokenModal');
        setTimeout(() => document.getElementById('createTokenName').focus(), 50);
    }

    async function submitCreateToken() {
        const name = document.getElementById('createTokenName').value.trim();
        const errEl = document.getElementById('createTokenError');
        if (!name) {
            errEl.textContent = _('api_tokens_name_required');
            return;
        }
        const btn = document.getElementById('createTokenBtn');
        btn.disabled = true;
        try {
            const res = await apiCall('/api/settings/tokens', 'POST', { name });
            closeModal('createTokenModal');
            // Show the raw token exactly once. The user must copy it now —
            // we cannot retrieve it after this point.
            document.getElementById('newTokenValue').value = res.token || '';
            document.getElementById('newTokenName').textContent = res.name || '';
            openModal('newTokenModal');
            loadTokens();
        } catch (err) {
            errEl.textContent = err.message;
        } finally {
            btn.disabled = false;
        }
    }

    function copyNewToken() {
        const input = document.getElementById('newTokenValue');
        input.select();
        copyToClipboard(input.value);
    }

    async function revokeToken(id, name) {
        if (!confirm(_('api_tokens_revoke_confirm').replace('{}', name))) return;
        try {
            await apiCall(`/api/settings/tokens/${id}`, 'DELETE');
            showToast(_('api_tokens_revoked'), 'success');
            loadTokens();
        } catch (err) {
            showToast(err.message, 'error');
        }
    }

    document.addEventListener('DOMContentLoaded', () => {
        loadTokens();
        loadTunnelStatus();
        tunnelStatusTimer = setInterval(loadTunnelStatus, 10000);
    });
</script>
{% endblock %}
