/* global React, PD, OverviewView, OperationsView, ViewerView, HistoryView, IncidentsView, ConfigView, JsonView, PD_SAMPLE_DEAL */
const { useState, useEffect, useRef, useCallback } = React;

function PipedriveScreen() {
  const [sub, setSub] = useState('overview');
  const [runState, setRunState] = useState('idle');
  const [logLines, setLogLines] = useState([]);
  const [summary, setSummary] = useState(null);
  const [jsonOpen, setJsonOpen] = useState(null);
  const [status, setStatus] = useState(null);
  const [viewerEntity, setViewerEntity] = useState(null);
  const pollRef = useRef(null);
  const toast = useToast();

  const loadStatus = useCallback(async () => {
    try {
      const s = await PD.getStatus();
      setStatus(s);
    } catch {}
  }, []);

  useEffect(() => { loadStatus(); }, [loadStatus]);

  // Parse plain-text log into structured lines
  function parseLog(text) {
    return text.split('\n').filter(Boolean).map((line, i) => {
      const ts = (line.match(/\[(\d{2}:\d{2}:\d{2})/) || line.match(/T(\d{2}:\d{2}:\d{2})/)||['',''])[1] || '';
      const lower = line.toLowerCase();
      const lvl = /error|err|exception|econnreset/.test(lower) ? 'err'
        : /warn|skip|warning/.test(lower) ? 'warn'
        : /ok|done|complete|success|uploaded|synced/.test(lower) ? 'ok'
        : 'info';
      const msg = line
        .replace(/\[\d{4}-\d{2}-\d{2}T\d{2}:\d{2}:\d{2}[^\]]*\]\s*/g, '')
        .replace(/\[Server\]\s*/g, '')
        .replace(/(\d+)/g, '<num>$1</num>')
        .replace(/'([^']+)'/g, '<str>$1</str>');
      return { ts, lvl, msg };
    });
  }

  const startSync = async () => {
    try {
      await PD.startSync();
      setRunState('running');
      setLogLines([]);
      setSummary(null);
      toast('Sync started', 'success');
      startLogPolling();
    } catch (e) { toast('Failed to start sync: ' + e.message, 'danger'); }
  };

  const stopSync = async () => {
    try {
      await PD.stopSync();
      setRunState('idle');
      stopLogPolling();
      toast('Sync stopped', 'success');
    } catch (e) { toast('Failed to stop sync', 'danger'); }
  };

  const startLogPolling = () => {
    if (pollRef.current) return;
    pollRef.current = setInterval(async () => {
      try {
        const [logText, statusData] = await Promise.all([PD.getLog(), PD.getSyncStatus()]);
        setLogLines(parseLog(logText));
        if (!statusData.isRunning) {
          setRunState('idle');
          stopLogPolling();
          loadStatus();
          // try to build summary from last log
          try {
            const summaryText = await PD.getSummary();
            if (summaryText && summaryText.trim()) {
              setSummary({ raw: summaryText });
            }
          } catch {}
        }
      } catch {}
    }, 1500);
  };

  const stopLogPolling = () => {
    if (pollRef.current) { clearInterval(pollRef.current); pollRef.current = null; }
  };

  useEffect(() => {
    // Check if sync is already running on mount
    PD.getSyncStatus().then(s => {
      if (s.isRunning) { setRunState('running'); startLogPolling(); }
    }).catch(() => {});
    return stopLogPolling;
  }, []);

  const subs = [
    { value: 'overview',   label: 'Overview',      icon: <Icon d={I.home} size={13}/> },
    { value: 'operations', label: 'Operations',    icon: <Icon d={I.zap} size={13}/> },
    { value: 'viewer',     label: 'Data viewer',   icon: <Icon d={I.database} size={13}/> },
    { value: 'history',    label: 'History',       icon: <Icon d={I.clock} size={13}/> },
    { value: 'config',     label: 'Configuration', icon: <Icon d={I.settings} size={13}/> },
  ];

  const onJump = (target, params) => {
    setSub(target);
    if (params?.entity) setViewerEntity(params.entity);
  };

  return (
    <div className="route-in" style={{ display: 'flex', flexDirection: 'column', height: '100%' }}>
      <div style={{ padding: '24px 32px 0', maxWidth: 1280, width: '100%', margin: '0 auto' }}>
        <div style={{ display: 'flex', alignItems: 'flex-end', justifyContent: 'space-between', gap: 24, marginBottom: 18, flexWrap: 'wrap' }}>
          <div>
            <div style={{ display: 'flex', alignItems: 'center', gap: 10, marginBottom: 8 }}>
              <div className="micro">Tool</div>
              {runState === 'running' && <Badge tone="success" dot>Running</Badge>}
            </div>
            <div style={{ display: 'flex', alignItems: 'center', gap: 14 }}>
              <div style={{ width: 36, height: 36, borderRadius: 8, background: 'var(--s-brand-weak)', color: 'var(--s-link)', display: 'flex', alignItems: 'center', justifyContent: 'center' }}>
                <Icon d={I.database} size={18}/>
              </div>
              <h1 style={{ fontFamily: 'var(--s-font-display)', fontWeight: 400, fontSize: 28, letterSpacing: '-0.01em' }}>Pipedrive Sync</h1>
            </div>
          </div>
          <div style={{ display: 'flex', alignItems: 'center', gap: 8 }}>
            {runState === 'running'
              ? <Button variant="secondary" destructive icon={<Icon d={I.stop} size={12}/>} onClick={stopSync}>Stop</Button>
              : <Button variant="primary" icon={<Icon d={I.play} size={12}/>} onClick={startSync}>Run sync</Button>
            }
          </div>
        </div>
        <Tabs value={sub} onChange={setSub} options={subs}/>
      </div>

      <div style={{ flex: 1, overflowY: 'auto' }}>
        <div style={{ padding: '20px 32px 64px', maxWidth: 1280, width: '100%', margin: '0 auto' }}>
          {sub === 'overview'   && <OverviewView status={status} runState={runState} onRun={startSync} onStop={stopSync} onJump={onJump}/>}
          {sub === 'operations' && <OperationsView runState={runState} logLines={logLines} summary={summary} onRun={startSync} onStop={stopSync}
              onClear={async () => { try { await PD.clearDatabase(); toast('Database cleared'); loadStatus(); } catch(e) { toast('Error: ' + e.message, 'danger'); } }}
              onResetFiles={async () => { try { await PD.resetFilesync(); toast('File sync state reset'); } catch(e) { toast('Error: ' + e.message, 'danger'); } }}/>}
          {sub === 'viewer'  && <ViewerView initialEntity={viewerEntity} onJsonOpen={setJsonOpen}/>}
          {sub === 'history' && <HistoryView status={status} onJump={onJump}/>}
          {sub === 'config'  && <ConfigView status={status} onReload={loadStatus}
              onTest={(kind) => toast(kind === 'email' ? 'Test email sent' : 'OneDrive: connection OK')}/>}
        </div>
      </div>

      <Modal open={!!jsonOpen} onClose={() => setJsonOpen(null)} title={jsonOpen ? `${jsonOpen.primary || 'Record'} · ID ${jsonOpen.id}` : 'Record'}>
        <JsonView obj={jsonOpen?.rawData || PD_SAMPLE_DEAL}/>
      </Modal>
    </div>
  );
}

window.PipedriveScreen = PipedriveScreen;
