/* Company Stock Price — News (in-site reading + Finnhub feeds). */
const NEWS_CATS = ['All', 'Markets', 'Global', 'Economy', 'Sector'];

function formatArticleDate(item) {
  if (!item || !item.datetime) return item && item.time ? item.time : '';
  return new Date(item.datetime * 1000).toLocaleString('en-IN', {
    weekday: 'short', day: 'numeric', month: 'short', year: 'numeric',
    hour: '2-digit', minute: '2-digit',
  });
}

function NewsArticleScreen({ articleId, onBack, onOpenArticle }) {
  const L = useLive();
  const [article, setArticle] = useState(() => (window.NewsCache && window.NewsCache.get(articleId)) || null);
  const [body, setBody] = useState(null);
  const [loading, setLoading] = useState(!article);
  const [bodyLoading, setBodyLoading] = useState(false);
  const [err, setErr] = useState('');
  const [bodyErr, setBodyErr] = useState('');

  useEffect(() => {
    if (!L.hasKey) return;
    let cancelled = false;

    async function loadMeta() {
      const cached = window.NewsCache && window.NewsCache.get(articleId);
      if (cached) {
        setArticle(cached);
        setLoading(false);
        return cached;
      }
      setLoading(true);
      setErr('');
      try {
        const a = await L.market.getNewsArticle(articleId);
        if (!cancelled) {
          setArticle(a);
          setLoading(false);
        }
        return a;
      } catch (e) {
        if (!cancelled) {
          setArticle(null);
          setErr(apiErrorMessage(e));
          setLoading(false);
        }
        return null;
      }
    }

    async function loadBody(meta) {
      if (!meta || !meta.url) return;
      setBodyLoading(true);
      setBodyErr('');
      try {
        const full = await L.market.getNewsArticleBody(meta.url);
        if (!cancelled) setBody(full);
      } catch (e) {
        if (!cancelled) setBodyErr(apiErrorMessage(e));
      } finally {
        if (!cancelled) setBodyLoading(false);
      }
    }

    loadMeta().then((meta) => { if (!cancelled && meta) loadBody(meta); });
    return () => { cancelled = true; };
  }, [articleId, L.hasKey]);

  if (!L.hasKey) {
    return (
      <EmptyState icon="news" title="Finnhub API key required" sub="Connect your API key to read articles."
        action={<button className="pill active" onClick={L.openSettings}>Connect API</button>} />
    );
  }

  if (loading && !article) return <SkeletonNews />;
  if (err || !article) {
    return (
      <EmptyState icon="news" title="Article not found" sub={err || 'Could not load this story.'}
        action={<button className="pill" onClick={onBack}>Back to News</button>} />
    );
  }

  const related = window.NewsCache ? window.NewsCache.list(article.id, 5) : [];
  const HT = window.HtmlText;

  function cleanParas(list) {
    return (list || [])
      .map((p) => (HT ? HT.cleanParagraph(p) : String(p || '').replace(/<[^>]+>/g, ' ').trim()))
      .filter((p) => p && p.length > 40);
  }

  let paragraphs = [];
  if (body && body.paragraphs && body.paragraphs.length) {
    paragraphs = cleanParas(body.paragraphs);
  }
  if (!paragraphs.length && article.summaryParagraphs && article.summaryParagraphs.length) {
    paragraphs = article.summaryParagraphs;
  }
  if (!paragraphs.length && article.summary) {
    paragraphs = HT ? HT.htmlToParagraphs(article.summary) : [article.summary];
  }
  if (!paragraphs.length && body && body.excerpt) {
    paragraphs = HT ? HT.htmlToParagraphs(body.excerpt) : [body.excerpt];
  }

  const heroImage = article.image || (body && body.image) || '';
  const leadText = body && body.excerpt
    ? (HT ? HT.stripHtml(body.excerpt) : body.excerpt)
    : '';

  return (
    <div className="news-article-page">
      <button className="link-btn" onClick={onBack} style={{ marginBottom: 14, background: 'none', border: 'none', padding: 0 }}>
        <span style={{ transform: 'scaleX(-1)', display: 'inline-flex' }}><Icon name="chevright" size={14} /></span> Back to News
      </button>

      <article className="card news-article">
        {heroImage && (
          <NewsImg seed={article.id} className="nf-img news-article-hero" h={280} src={heroImage} />
        )}
        <div className="news-article-body">
          <div style={{ display: 'flex', alignItems: 'center', gap: 10, flexWrap: 'wrap', marginBottom: 12 }}>
            <CatPill cat={article.cat} color={article.catColor} />
            <span className="source-badge"><span className="source-dot"></span>{article.source}</span>
            <LiveBadge live={article.live} small />
          </div>
          <h1 className="h1" style={{ fontSize: 28, lineHeight: 1.3, margin: '0 0 12px' }}>{article.headline}</h1>
          <div className="muted" style={{ fontSize: 13, marginBottom: 20 }}>
            {formatArticleDate(article)}{article.read ? ' · ' + article.read + ' read' : ''}
          </div>
          {bodyLoading && (
            <div className="news-article-content" style={{ marginBottom: 16 }}>
              {[0, 1, 2, 3].map((i) => (
                <div key={i} style={{ marginBottom: 14 }}>
                  <Shimmer w="100%" h={14} r={4} style={{ marginBottom: 8 }} />
                  <Shimmer w={i === 3 ? '72%' : '100%'} h={14} r={4} />
                </div>
              ))}
              <p className="muted" style={{ fontSize: 13, marginTop: 8 }}>Loading full article…</p>
            </div>
          )}

          {!bodyLoading && paragraphs.length > 0 && (
            <div className="news-article-content">
              {leadText && (
                <p className="news-article-lead">{leadText}</p>
              )}
              {paragraphs.map((para, i) => (
                <p key={i}>{para}</p>
              ))}
            </div>
          )}

          {!bodyLoading && !paragraphs.length && (
            <p className="muted" style={{ fontSize: 15, lineHeight: 1.6 }}>
              {bodyErr || 'Full article text could not be loaded. Try again later.'}
            </p>
          )}

          <div className="news-article-foot muted" style={{ fontSize: 12, marginTop: 24, paddingTop: 16, borderTop: '1px solid var(--border)' }}>
            Published by {article.source || article.author || 'Newswire'}
            {body && body.wordCount ? ' · ' + body.wordCount.toLocaleString() + ' words' : ''}
            {body && body.partial ? ' · partial extract' : ''}
          </div>
        </div>
      </article>

      {related.length > 0 && onOpenArticle && (
        <div className="section" style={{ marginTop: 20 }}>
          <h2 className="h2" style={{ marginBottom: 12 }}>More headlines</h2>
          <NewsCompact items={related} onOpen={onOpenArticle} />
        </div>
      )}
    </div>
  );
}

function IndicesSidebar() {
  const L = useLive();
  const MD = useMarketData();
  const [region, setRegion] = useState('IN');
  const india = MD.indices || [];
  const global = MD.globalIndices || [];
  const indices = region === 'US' ? global : india;

  useEffect(() => {
    if (region === 'US' && L.hasKey && !global.length && !MD.globalLoading) {
      MD.loadGlobal();
    }
  }, [region, L.hasKey, global.length, MD.globalLoading, MD.loadGlobal]);

  return (
    <div className="card section">
      <div style={{ display: 'flex', alignItems: 'center', justifyContent: 'space-between', gap: 8, marginBottom: 10 }}>
        <h3 className="h3" style={{ margin: 0 }}>Indices</h3>
        <div className="pill-row" style={{ gap: 4 }}>
          <button className={`pill ${region === 'IN' ? 'active' : ''}`} style={{ padding: '4px 10px', fontSize: 11 }} onClick={() => setRegion('IN')}>IN</button>
          <button className={`pill ${region === 'US' ? 'active' : ''}`} style={{ padding: '4px 10px', fontSize: 11 }} onClick={() => setRegion('US')}>US</button>
        </div>
      </div>
      {region === 'US' && !L.hasKey && (
        <p className="muted" style={{ fontSize: 12, margin: '0 0 8px' }}>Connect API key for US indices.</p>
      )}
      {region === 'US' && MD.globalLoading && !indices.length && (
        <p className="muted" style={{ fontSize: 12, margin: 0 }}>Loading US indices…</p>
      )}
      {indices.slice(0, 5).map((ix) => (
        <div key={ix.label} style={{ display: 'flex', justifyContent: 'space-between', padding: '8px 0', borderBottom: '1px solid var(--border)' }}>
          <span style={{ fontSize: 13, fontWeight: 500 }}>{ix.label}</span>
          <span className="mono" style={{ fontSize: 12 }}>{ix.cur === 'INR' ? '₹' : '$'}{fmt.price(ix.value)} <ChangeChip value={ix.chg} sm showArrow={false} /></span>
        </div>
      ))}
    </div>
  );
}

function NewsScreen({ onOpenArticle }) {
  const L = useLive();
  const MD = useMarketData();
  const [cat, setCat] = useState('All');
  const [news, setNews] = useState(MD.news || []);
  const [earnings, setEarnings] = useState([]);
  const [loading, setLoading] = useState(false);
  const [loadingMore, setLoadingMore] = useState(false);
  const [pages, setPages] = useState(2);
  const [err, setErr] = useState('');

  async function loadLive(pageCount = 2) {
    if (!L.hasKey) return;
    setLoading(true); setErr('');
    try {
      const [feed, earn] = await Promise.all([
        L.market.getMarketNewsFeed(cat, { pages: pageCount }),
        L.market.getEarningsCalendar(2, 0).catch(() => []),
      ]);
      setNews(feed);
      if (window.NewsCache) window.NewsCache.putMany(feed);
      setPages(pageCount);
      setEarnings(earn);
      L.refreshRateLimit();
    } catch (e) {
      setErr(apiErrorMessage(e));
    } finally { setLoading(false); }
  }

  async function loadMore() {
    if (!L.hasKey || loadingMore) return;
    setLoadingMore(true); setErr('');
    try {
      const nextPages = pages + 1;
      const feed = await L.market.getMarketNewsFeed(cat, { pages: nextPages });
      setNews(feed);
      if (window.NewsCache) window.NewsCache.putMany(feed);
      setPages(nextPages);
      L.refreshRateLimit();
    } catch (e) {
      setErr(apiErrorMessage(e));
    } finally { setLoadingMore(false); }
  }

  useEffect(() => {
    if (MD.news && MD.news.length) setNews(MD.news);
  }, [MD.news]);

  useEffect(() => {
    if (!L.hasKey) return;
    loadLive(2);
    const id = setInterval(() => loadLive(2), MD.refreshMs || 5 * 60 * 1000);
    return () => clearInterval(id);
  }, [L.hasKey, cat]);

  const trending = news.slice(0, 6).map((n) => ({
    tag: (n.headline || '').split(' ').slice(0, 4).join(' '),
    posts: n.source || 'News',
  }));

  if (!L.hasKey) {
    return (
      <div>
        <h1 className="h1" style={{ marginBottom: 4 }}>News &amp; Insights</h1>
        <EmptyState icon="news" title="Finnhub API key required" sub="Connect your API key in settings to load live market news feeds."
          action={<button className="pill active" onClick={L.openSettings}>Connect API</button>} />
      </div>
    );
  }

  if ((!news.length && loading) || (MD.loading && !MD.ready && !news.length)) {
    return <SkeletonNews />;
  }

  const filtered = cat === 'All' ? news : news.filter((n) => n.cat === cat);
  const featured = filtered[0] || news[0];
  const isFeatured = featured && featured.featured && cat === 'All';
  const rest = isFeatured ? filtered.slice(1) : filtered.slice(1);

  return (
    <div>
      <div style={{ display: 'flex', alignItems: 'flex-end', justifyContent: 'space-between', gap: 12, marginBottom: 14, flexWrap: 'wrap' }}>
        <div>
          <div style={{ display: 'flex', alignItems: 'center', gap: 10 }}>
            <h1 className="h1">News &amp; Insights</h1>
            <LiveBadge live={news.some((n) => n.live)} />
          </div>
          <div className="muted" style={{ marginTop: 2 }}>
            Finnhub feeds: general · forex · crypto · merger
          </div>
        </div>
        {L.hasKey && <button className="pill" onClick={() => loadLive(2)} disabled={loading}>{loading ? 'Loading…' : 'Refresh'}</button>}
      </div>

      {err && <div className="banner err section">{err}</div>}

      <div className="pill-row section" style={{ marginBottom: 14 }}>
        {NEWS_CATS.map((c) => (
          <button key={c} className={`pill ${cat === c ? 'active' : ''}`} onClick={() => setCat(c)}>{c}</button>
        ))}
      </div>

      <div className="news-layout section">
        <div>
          {featured && (
            <div className="card hoverable news-featured" style={{ marginBottom: 14 }} role="button" tabIndex={0}
              onClick={() => onOpenArticle && onOpenArticle(featured)}
              onKeyDown={(e) => { if ((e.key === 'Enter' || e.key === ' ') && onOpenArticle) { e.preventDefault(); onOpenArticle(featured); } }}>
              {featured.image && <div className="nf-img" style={{ backgroundImage: `url(${featured.image})` }}></div>}
              <div className="nf-body">
                <span className="chip" style={{ background: featured.catColor, color: '#fff', marginBottom: 8 }}>{featured.cat}</span>
                <h2 className="h2" style={{ margin: '0 0 8px', lineHeight: 1.35 }}>{featured.headline}</h2>
                {featured.summary && <p className="muted" style={{ margin: '0 0 12px', fontSize: 14, lineHeight: 1.55 }}>{window.HtmlText ? window.HtmlText.stripHtml(featured.summary) : featured.summary}</p>}
                <div className="muted" style={{ fontSize: 12 }}>{featured.source} · {featured.time}{featured.read ? ' · ' + featured.read : ''}</div>
              </div>
            </div>
          )}
          <div className="news-list">
            {rest.map((n) => (
              <div key={n.id} className="card hoverable news-row" role="button" tabIndex={0}
                onClick={() => onOpenArticle && onOpenArticle(n)}
                onKeyDown={(e) => { if ((e.key === 'Enter' || e.key === ' ') && onOpenArticle) { e.preventDefault(); onOpenArticle(n); } }}>
                <span className="chip sm" style={{ background: n.catColor, color: '#fff' }}>{n.cat}</span>
                <h3 className="h3" style={{ margin: '6px 0 4px', lineHeight: 1.35 }}>{n.headline}</h3>
                <div className="muted" style={{ fontSize: 12 }}>{n.source} · {n.time}</div>
              </div>
            ))}
          </div>
          {L.hasKey && rest.length > 0 && (
            <div style={{ marginTop: 14, textAlign: 'center' }}>
              <button className="pill" onClick={loadMore} disabled={loadingMore || loading}>
                {loadingMore ? 'Loading…' : 'Load more headlines'}
              </button>
              <div className="muted" style={{ fontSize: 11, marginTop: 6 }}>{news.length} articles · {pages} API page{pages === 1 ? '' : 's'}</div>
            </div>
          )}
        </div>

        <aside>
          <IndicesSidebar />

          {L.hasKey && earnings.length > 0 && (
            <div className="card section">
              <h3 className="h3" style={{ marginBottom: 10 }}>Upcoming Earnings</h3>
              {earnings.slice(0, 6).map((e) => (
                <div key={e.id} style={{ padding: '8px 0', borderBottom: '1px solid var(--border)' }}>
                  <div style={{ display: 'flex', justifyContent: 'space-between', gap: 8 }}>
                    <span className="mono" style={{ fontWeight: 600, fontSize: 13, color: 'var(--accent)' }}>{e.symbol}</span>
                    <span className="muted" style={{ fontSize: 11 }}>{e.date}</span>
                  </div>
                  {e.epsEstimate != null && <div className="muted" style={{ fontSize: 11, marginTop: 2 }}>EPS est. {e.epsEstimate}</div>}
                </div>
              ))}
            </div>
          )}

          {trending.length > 0 && (
            <div className="card">
              <h3 className="h3" style={{ marginBottom: 10 }}>Trending</h3>
              {trending.map((t, i) => (
                <div key={i} style={{ padding: '8px 0', borderBottom: i < trending.length - 1 ? '1px solid var(--border)' : 'none' }}>
                  <div style={{ fontWeight: 600, fontSize: 13 }}>{t.tag}</div>
                  <div className="muted" style={{ fontSize: 11 }}>{t.posts}</div>
                </div>
              ))}
            </div>
          )}
        </aside>
      </div>
    </div>
  );
}
Object.assign(window, { NewsScreen, NewsArticleScreen });
