/* global React, Icon, UI, LessonHighData */
// ============================================================
// I1 — 상담 → 등록 전환 강화
// Replaces AdminPages2.Consults. Adds funnel KPIs, channel ROI,
// D+3 무응답 ribbon, stage dropdown, UTM display.
// ============================================================
(function () {
const { useState, useMemo } = React;
const D = LessonHighData;

const STAGES = [
  { id: 'lead',      label: '리드',      tone: 'neutral' },
  { id: 'scheduled', label: '상담 예약', tone: 'warning' },
  { id: 'met',       label: '상담 완료', tone: 'accent'  },
  { id: 'enrolled',  label: '등록 완료', tone: 'success' },
  { id: 'lost',      label: '이탈',      tone: 'danger'  },
];

function ConsultsPro({ onOpenMember, onOpenRegister, onOpenConsultJournal }) {
  const [stageFilter, setStageFilter] = useState('all');
  const [stages, setStages] = useState(() => Object.fromEntries(D.consultations.map(c => [c.id, c.stage])));

  // ISO 8601 → { rel: '어제', full: '2025-11-19 19:00' }
  function relTime(iso) {
    if (!iso) return { rel: '—', full: '' };
    return { rel: D.fmt.relative(iso), full: D.fmt.timestamp(iso) };
  }

  // KPIs
  const all = D.consultations;
  const enrolled = all.filter(c => stages[c.id] === 'enrolled');
  const lost     = all.filter(c => stages[c.id] === 'lost');
  const open     = all.filter(c => !['enrolled','lost'].includes(stages[c.id]));
  const stale    = useMemo(() => all.filter(c => {
    if (['enrolled','lost'].includes(stages[c.id])) return false;
    // mocked check — any with lastTouchAt > 3 days ago (we just count leads)
    return stages[c.id] === 'lead';
  }), [stages]);
  const convRate = Math.round((enrolled.length / Math.max(1, enrolled.length + lost.length + open.length)) * 100);

  // filter
  const visible = stageFilter === 'all'
    ? all
    : all.filter(c => stages[c.id] === stageFilter);

  return (
    <React.Fragment>
      <header className="page-header">
        <div>
          <h1 className="page-title">상담</h1>
          <div className="page-sub">신규 {all.length}건 · 등록 전환 {convRate}% · 무응답 {stale.length}건</div>
        </div>
        <div className="page-actions">
          <UI.Button icon={Icon.Receipt} variant="ghost" onClick={() => window.toast && window.toast('월간 채널 리포트 PDF 생성 완료 — 이메일 발송', { tone: 'success' })}>월간 채널 리포트</UI.Button>
          <UI.Button icon={Icon.Plus} variant="primary" onClick={() => onOpenConsultJournal && onOpenConsultJournal('new')}>상담일지 작성</UI.Button>
        </div>
      </header>

      {/* KPI cards */}
      <div className="grid-4" style={{ marginBottom: 16 }}>
        <ConsultKpi label="신규 (이번 달)"   value={all.length}  sub="▲ 5 vs 10월" tone="accent"/>
        <ConsultKpi label="등록 전환"        value={`${convRate}%`} sub="▲ 4%p"     tone="success"/>
        <ConsultKpi label="평균 응답 시간"   value="4h"          sub="▼ 1h"        tone="success"/>
        <ConsultKpi label="D+3 무응답"      value={stale.length} sub="처리 필요"   tone="danger"/>
      </div>

      {/* D+3 무응답 ribbon */}
      {stale.length > 0 && (
        <div className="consult-ribbon">
          <span className="consult-ribbon__icon"><Icon.Warn size={16}/></span>
          <div className="consult-ribbon__body">
            <div className="t-body-strong" style={{ color: 'var(--status-danger)' }}>
              D+3 동안 응답 없는 상담 {stale.length}건
            </div>
            <div className="t-caption" style={{ fontSize: 12.5 }}>
              {stale.map(s => s.prospect).join(' · ')}
            </div>
          </div>
          <UI.Button size="sm" variant="primary" icon={Icon.Mail} onClick={() => window.toast && window.toast('보류중인 상담 4명에게 일괄 알림톡 발송 — 상담 이후 D+3 테플릿', { tone: 'success' })}>일괄 알림톡 보내기</UI.Button>
        </div>
      )}

      <div style={{ display: 'grid', gridTemplateColumns: '1fr 320px', gap: 16, marginTop: 16 }} className="consult-grid">
        {/* Left — Table */}
        <UI.Card>
          <UI.CardHeader
            title="상담 리스트"
            actions={
              <div className="row" style={{ background: 'var(--bg-subtle)', padding: 2, borderRadius: 'var(--radius-md)', gap: 0 }}>
                {[{ id: 'all', label: `전체 ${all.length}` }, ...STAGES.map(s => ({ id: s.id, label: `${s.label} ${all.filter(c => stages[c.id]===s.id).length}` }))].map(f => (
                  <button
                    key={f.id}
                    className={`btn is-sm ${stageFilter === f.id ? 'is-primary' : 'is-ghost'}`}
                    style={{ borderColor: 'transparent', height: 28 }}
                    onClick={() => setStageFilter(f.id)}
                  >{f.label}</button>
                ))}
              </div>
            }
          />
          <UI.CardBody flush>
            <table className="tbl">
              <thead><tr>
                <th>상담자</th>
                <th>유입 / UTM</th>
                <th>마지막 액션</th>
                <th>단계</th>
                <th style={{ width: 160 }}></th>
              </tr></thead>
              <tbody>
                {visible.map(c => {
                  const stage = stages[c.id];
                  const isStale = stage === 'lead';
                  return (
                    <tr key={c.id} className={isStale ? 'is-stale' : ''}>
                      <td className="cell-identity">
                        <div className="row" style={{ gap: 10 }}>
                          <UI.Avatar name={c.prospect} tone={stage === 'enrolled' ? 'tone-a' : stage === 'lost' ? 'tone-d' : 'tone-b'} size="md"/>
                          <div className="col" style={{ gap: 0 }}>
                            <span className="t-body-strong">{c.prospect}</span>
                            <span className="t-caption t-mono num" style={{ fontSize: 12 }}>{c.phone}</span>
                          </div>
                        </div>
                      </td>
                      <td data-label="유입">
                        <div className="col" style={{ gap: 2 }}>
                          <span style={{ fontSize: 13 }}>{c.source}</span>
                          {c.utm && (() => {
                            const srcLabel = D.utmDict?.src?.[c.utm.src] || c.utm.src;
                            const medLabel = D.utmDict?.med?.[c.utm.med] || c.utm.med;
                            const cmpInfo  = c.utm.cmp ? D.utmDict?.cmp?.[c.utm.cmp] : null;
                            const cmpLabel = cmpInfo?.label || c.utm.cmp;
                            return (
                              <span className="t-mono utm-line" style={{ fontSize: 10.5, color: 'var(--text-tertiary)' }}>
                                <span className="utm-token" title={`utm_source — 유입 채널\n${srcLabel}`}>{c.utm.src}</span>
                                <span className="utm-sep">/</span>
                                <span className="utm-token" title={`utm_medium — 광고 형식\n${medLabel}`}>{c.utm.med}</span>
                                {c.utm.cmp && (
                                  <React.Fragment>
                                    <span className="utm-sep"> · </span>
                                    <span className="utm-token" title={cmpInfo ? `utm_campaign — ${cmpInfo.label}\n${cmpInfo.desc}\n${cmpInfo.period}` : `utm_campaign — ${c.utm.cmp}`}>{c.utm.cmp}</span>
                                  </React.Fragment>
                                )}
                                {c.utm.ref && (
                                  <React.Fragment>
                                    <span className="utm-sep"> · </span>
                                    <span className="utm-token" title={`utm_ref — 추천인 회원 ID`}>ref={c.utm.ref}</span>
                                  </React.Fragment>
                                )}
                              </span>
                            );
                          })()}
                        </div>
                      </td>
                      <td data-label="마지막 액션" className="t-caption" style={{ fontSize: 12 }}>
                        {(() => {
                          const rt = relTime(c.lastTouchAt);
                          return <span title={rt.full} className="rel-time">{rt.rel}</span>;
                        })()}
                      </td>
                      <td data-label="단계">
                        <select
                          className="select"
                          style={{ height: 28, width: 120, fontSize: 12.5 }}
                          value={stage}
                          onChange={(e) => setStages(s => ({ ...s, [c.id]: e.target.value }))}
                        >
                          {STAGES.map(s => <option key={s.id} value={s.id}>{s.label}</option>)}
                        </select>
                      </td>
                      <td className="cell-actions" style={{ textAlign: 'right' }}>
                        {stage === 'enrolled' ? (
                          <UI.Button size="sm" variant="ghost" onClick={() => c.memberId && onOpenMember(c.memberId)}>회원 보기 →</UI.Button>
                        ) : stage === 'lost' ? (
                          <span className="t-caption" style={{ fontSize: 12 }}>사유: {c.lostReason || '—'}</span>
                        ) : (
                          <div className="row" style={{ justifyContent: 'flex-end', gap: 4 }}>
                            <UI.Button size="sm" variant="ghost" icon={Icon.Note} onClick={() => onOpenConsultJournal && onOpenConsultJournal(c.id)}>일지</UI.Button>
                            <UI.Button size="sm" icon={Icon.Mail} onClick={(e) => { e.stopPropagation(); window.toast && window.toast(`${c.prospect}님께 가입 안내 알림톡 발송`, { tone: 'success' }); }}>알림톡</UI.Button>
                            <UI.Button size="sm" variant="primary" onClick={onOpenRegister}>등록</UI.Button>
                          </div>
                        )}
                      </td>
                    </tr>
                  );
                })}
              </tbody>
            </table>
          </UI.CardBody>
        </UI.Card>

        {/* Right — Channel funnel + UTM legend */}
        <div className="col" style={{ gap: 16 }}>
          <UI.Card>
            <UI.CardHeader title="채널 × 등록 전환" subtitle="이번 달"/>
            <UI.CardBody>
              <div className="col" style={{ gap: 12 }}>
                {D.channelStats.map(ch => {
                  const widthPct = (ch.leads / 12) * 100;
                  const convPct  = Math.round((ch.enrolled / Math.max(1, ch.leads)) * 100);
                  return (
                    <div key={ch.src} className="col" style={{ gap: 4 }}>
                      <div className="row" style={{ gap: 6 }}>
                        <span style={{ fontSize: 12, fontWeight: 600 }}>{ch.label}</span>
                        <span className="t-caption t-mono num" style={{ fontSize: 11, marginLeft: 'auto' }}>전환 {convPct}%</span>
                      </div>
                      <div className="row" style={{ gap: 6, alignItems: 'center' }}>
                        <div style={{
                          height: 22, width: `${widthPct}%`, minWidth: 32,
                          background: ch.color, borderRadius: 3,
                          display: 'flex', alignItems: 'center', padding: '0 8px',
                          color: 'var(--text-on-accent)', fontFamily: 'var(--font-mono)',
                          fontSize: 11, fontWeight: 600,
                        }}>{ch.leads}건</div>
                      </div>
                      <span className="t-caption t-mono num" style={{ fontSize: 10.5 }}>
                        등록 {ch.enrolled} · 평균 LTV {(ch.ltv / 10000).toFixed(0)}만
                      </span>
                    </div>
                  );
                })}
              </div>
            </UI.CardBody>
          </UI.Card>

          <UI.Card>
            <UI.CardHeader title="이탈 사유 — 11월" />
            <UI.CardBody>
              <div className="col" style={{ gap: 8 }}>
                {[
                  { label: '비용',     n: 3, w: 60 },
                  { label: '시간',     n: 2, w: 40 },
                  { label: '타학원 선택', n: 1, w: 20 },
                  { label: '무응답',   n: 0, w: 0 },
                ].map(r => (
                  <div key={r.label} className="row" style={{ gap: 8, alignItems: 'center' }}>
                    <span style={{ fontSize: 12, width: 80, color: 'var(--text-secondary)' }}>{r.label}</span>
                    <div style={{ flex: 1, height: 8, background: 'var(--bg-inset)', borderRadius: 99, overflow: 'hidden' }}>
                      <div style={{ height: '100%', width: `${r.w}%`, background: 'var(--status-danger)', borderRadius: 99 }}/>
                    </div>
                    <span className="t-mono num" style={{ fontSize: 11, color: 'var(--text-tertiary)', width: 24, textAlign: 'right' }}>{r.n}</span>
                  </div>
                ))}
              </div>
            </UI.CardBody>
          </UI.Card>

          {/* UTM Campaign legend — explain what the codes mean */}
          <UI.Card>
            <UI.CardHeader
              title="UTM 캠페인 코드"
              subtitle="광고 링크에 붙여 유입을 추적"
              actions={<UI.Button size="sm" variant="ghost" onClick={() => window.toast && window.toast('UTM 캐페인 사전 편집 — 설정 → 캐페인 코드')}>관리</UI.Button>}
            />
            <UI.CardBody>
              <div className="col" style={{ gap: 10 }}>
                {Object.entries(D.utmDict?.cmp || {}).map(([code, info]) => (
                  <div key={code} className="utm-cmp-row">
                    <div className="utm-cmp-row__head">
                      <span className="t-mono utm-cmp-row__code">{code}</span>
                      <span className="utm-cmp-row__label">{info.label}</span>
                    </div>
                    <div className="t-caption utm-cmp-row__desc">{info.desc}</div>
                    <div className="row utm-cmp-row__meta">
                      <span className="t-mono num" style={{ fontSize: 11 }}>{info.period}</span>
                      {info.spend > 0 && (
                        <span className="t-mono num" style={{ fontSize: 11, marginLeft: 'auto', color: 'var(--text-secondary)' }}>
                          {(info.spend / 10000).toFixed(0)}만원
                        </span>
                      )}
                    </div>
                  </div>
                ))}
              </div>
              <div className="t-caption" style={{ marginTop: 12, fontSize: 11, lineHeight: 1.6 }}>
                광고 링크 예시:<br/>
                <code className="t-mono" style={{ fontSize: 10.5, color: 'var(--text-secondary)', wordBreak: 'break-all' }}>
                  lessonhigh.com/c/송유이?utm_source=instagram&utm_medium=feed&utm_campaign=autumn-25
                </code>
              </div>
            </UI.CardBody>
          </UI.Card>
        </div>
      </div>
    </React.Fragment>
  );
}

function ConsultKpi({ label, value, sub, tone }) {
  const c = tone === 'danger'  ? 'var(--status-danger)'  :
            tone === 'warning' ? 'var(--status-warning)' :
            tone === 'success' ? 'var(--status-success)' : 'var(--accent-default)';
  return (
    <div style={{
      background: 'var(--bg-surface)', border: '1px solid var(--border-default)',
      borderRadius: 'var(--radius-lg)', padding: 18,
      position: 'relative', overflow: 'hidden',
    }}>
      <div style={{ position: 'absolute', top: 0, left: 0, width: 3, height: '100%', background: c }}/>
      <div className="t-micro" style={{ marginLeft: 6 }}>{label}</div>
      <div className="t-mono num" style={{ fontSize: 28, fontWeight: 700, marginLeft: 6, marginTop: 2, color: c }}>{value}</div>
      <div className="t-caption" style={{ marginLeft: 6, fontSize: 12 }}>{sub}</div>
    </div>
  );
}

window.ConsultsPro = ConsultsPro;
})();
