const loginView=document.getElementById('loginView'),adminView=document.getElementById('adminView'),rows=document.getElementById('sponsorRows'),toast=document.getElementById('toast');let state=null;
const LEVELS=['Scintilla','Ascensus','Fabrica','Culmen','Apex','Fastigium','Vertex','Corona'];
function levelSelect(s){const opts=(LEVELS.includes(s.level)?LEVELS:[s.level,...LEVELS]).map(l=>`${esc(l)} `).join('');return `${opts} `}
function showToast(msg){toast.textContent=msg;toast.classList.add('show');setTimeout(()=>toast.classList.remove('show'),1800)}
async function api(url,opts={}){const r=await fetch(url,{headers:{'Content-Type':'application/json',...(opts.headers||{})},...opts});const d=await r.json().catch(()=>({}));if(!r.ok)throw new Error(d.error||'Request failed');return d}
async function loadState(){try{state=await api('/api/admin/state');loginView.classList.add('hidden');adminView.classList.remove('hidden');render()}catch(e){loginView.classList.remove('hidden');adminView.classList.add('hidden')}}
function statusClass(s){return `status status-${s}`}
function pct(n,d){return d?`${Math.round((n/d)*100)}%`:'—'}
function renderAnalytics(){
const src=(state.analytics&&state.analytics.sources)||{};
const tot={bridge:0,start:0,click:0,training:0,postback:0,purchase:0};
const list=Object.entries(src).map(([name,r])=>{tot.bridge+=r.bridge||0;tot.start+=r.start||0;tot.click+=r.click||0;tot.training+=r.training||0;tot.postback+=r.postback||0;tot.purchase+=r.purchase||0;return{name,bridge:r.bridge||0,start:r.start||0,click:r.click||0,training:r.training||0}})
.sort((a,b)=>b.click-a.click||b.start-a.start||b.bridge-a.bridge);
document.getElementById('funnelStats').innerHTML=
`
Bridge views ${tot.bridge}
`+
`Start views ${tot.start}
`+
`Join clicks ${tot.click}
`+
`Bridge → Start ${pct(tot.start,tot.bridge)}
`+
`Start → Join ${pct(tot.click,tot.start)}
`+
(tot.purchase?`Confirmed joins ${tot.purchase}
`:'')+
(tot.postback?`BeMob postbacks ${tot.postback}
`:'');
const subs=state.submissions||[];
document.getElementById('submissionRows').innerHTML=subs.map(s=>`${esc((s.ts||'').replace('T',' ').slice(0,16))} ${esc(s.memberName||'—')} ${esc(s.newId)} ID ${esc(s.sponsorId)} ${esc(s.source)} `).join('')||'No submissions yet. ';
document.getElementById('trafficRows').innerHTML=list.map(r=>`${esc(r.name)} ${r.bridge} ${r.start} ${r.training} ${r.click} ${pct(r.click,r.start)} `).join('')||'No traffic recorded yet. ';
}
function esc(s){return String(s??'').replace(/[&<>'"]/g,c=>({'&':'&','<':'<','>':'>',"'":''','"':'"'}[c]))}
function render(){
const sponsors=[...state.sponsors].sort((a,b)=>a.sortOrder-b.sortOrder);rows.innerHTML=sponsors.map((s,i)=>`${i+1} ${esc(s.name)} ID ${esc(s.id)}
${esc(s.parentId||'—')} ${s.directs}/2 ${levelSelect(s)} ${esc(s.status)} ${s.clicks||0} ${s.status!=='qualified'?`+1 Direct Qualified `:`Reset `}${s.status==='waiting'?`Make Active `:''}↑ ↓ ×
`).join('')||'No sponsors in the queue. ';
renderAnalytics();
const ai=state.aiChat||{};document.getElementById('aiModel').textContent=ai.model||'OpenRouter';document.getElementById('aiStatus').innerHTML=ai.configured?'● AI chat is ON — key is set':'○ AI chat is OFF — using built-in answers';
const f=document.getElementById('configForm'),c=state.config;for(const k of ['siteName','programName','bridgeHeadline','bridgeSubheadline','premiumEntryPol','dappReferralBaseUrl','telegramUrl','supportLabel','bemobPostbackUrl','telegramBotToken','telegramChatId','telegramTopicId'])if(f.elements[k])f.elements[k].value=c[k]??'';f.elements.showSponsorName.checked=!!c.showSponsorName;f.elements.showQueueProgress.checked=!!c.showQueueProgress;
}
document.getElementById('loginForm').addEventListener('submit',async e=>{e.preventDefault();const err=document.getElementById('loginError');err.textContent='';try{await api('/api/admin/login',{method:'POST',body:JSON.stringify({password:document.getElementById('password').value})});document.getElementById('password').value='';await loadState()}catch(x){err.textContent=x.message}});
document.getElementById('logoutBtn').addEventListener('click',async()=>{await api('/api/admin/logout',{method:'POST'});location.reload()});
document.getElementById('addSponsorForm').addEventListener('submit',async e=>{e.preventDefault();const form=e.currentTarget,obj=Object.fromEntries(new FormData(form));try{const d=await api('/api/admin/sponsors',{method:'POST',body:JSON.stringify(obj)});state.sponsors=d.sponsors;form.reset();render();showToast('Sponsor added')}catch(x){showToast(x.message)}});
document.getElementById('configForm').addEventListener('submit',async e=>{e.preventDefault();const f=e.currentTarget,obj=Object.fromEntries(new FormData(f));obj.showSponsorName=f.elements.showSponsorName.checked;obj.showQueueProgress=f.elements.showQueueProgress.checked;obj.premiumEntryPol=Number(obj.premiumEntryPol);try{const d=await api('/api/admin/config',{method:'PATCH',body:JSON.stringify(obj)});state.config=d.config;render();showToast('Settings saved')}catch(x){showToast(x.message)}});
rows.addEventListener('click',async e=>{const b=e.target.closest('button[data-action]');if(!b)return;const id=b.dataset.id,a=b.dataset.action;try{let d;if(a==='delete'){if(!confirm(`Delete sponsor ID ${id}?`))return;d=await api(`/api/admin/sponsors/${id}`,{method:'DELETE'})}else if(a==='inc')d=await api(`/api/admin/sponsors/${id}/increment`,{method:'POST'});else if(a==='qualify')d=await api(`/api/admin/sponsors/${id}/qualify`,{method:'POST'});else if(a==='activate')d=await api(`/api/admin/sponsors/${id}/activate`,{method:'POST'});else if(a==='reset')d=await api(`/api/admin/sponsors/${id}/reset`,{method:'POST'});else if(a==='up'||a==='down')d=await api(`/api/admin/sponsors/${id}/move`,{method:'POST',body:JSON.stringify({direction:a})});if(d&&d.sponsors){state.sponsors=d.sponsors;render();showToast('Updated')}}catch(x){showToast(x.message)}});
document.getElementById('aiKeyForm').addEventListener('submit',async e=>{e.preventDefault();const inp=e.currentTarget.elements.key,key=inp.value.trim();if(!key){showToast('Paste a key first');return}try{const d=await api('/api/admin/openrouter-key',{method:'POST',body:JSON.stringify({key})});state.aiChat={...(state.aiChat||{}),configured:d.configured};inp.value='';render();showToast('AI chat enabled')}catch(x){showToast(x.message)}});
document.getElementById('aiKeyClear').addEventListener('click',async()=>{if(!confirm('Turn off AI chat and go back to built-in answers?'))return;try{const d=await api('/api/admin/openrouter-key',{method:'POST',body:JSON.stringify({key:''})});state.aiChat={...(state.aiChat||{}),configured:d.configured};render();showToast('AI chat disabled')}catch(x){showToast(x.message)}});
rows.addEventListener('change',async e=>{const sel=e.target.closest('select[data-action="level"]');if(!sel)return;try{const d=await api(`/api/admin/sponsors/${sel.dataset.id}`,{method:'PATCH',body:JSON.stringify({level:sel.value})});state.sponsors=d.sponsors;render();showToast('Level updated')}catch(x){showToast(x.message);render()}});
loadState();