/**
 * <folk-thread-gallery> — Thread listing grid with cards.
 *
 * Subscribes to Automerge doc and renders all threads sorted by updatedAt.
 * Falls back to static demo previews when offline runtime is unavailable.
 */

import { socialsSchema, socialsDocId } from '../schemas';
import type { SocialsDoc, ThreadData, Campaign, CampaignPost } from '../schemas';
import type { DocumentId } from '../../../shared/local-first/document';
import { DEMO_FEED } from '../lib/types';

interface DraftPostCard {
	id: string;
	campaignId: string;
	campaignTitle: string;
	platform: string;
	content: string;
	scheduledAt: string;
	status: string;
	hashtags: string[];
	threadId?: string;
}

export class FolkThreadGallery extends HTMLElement {
	private _space = 'demo';
	private _threads: ThreadData[] = [];
	private _draftPosts: DraftPostCard[] = [];
	private _offlineUnsub: (() => void) | null = null;
	private _subscribedDocIds: string[] = [];
	private _isDemoFallback = false;

	static get observedAttributes() { return ['space']; }

	connectedCallback() {
		if (!this.shadowRoot) this.attachShadow({ mode: 'open' });
		this._space = this.getAttribute('space') || 'demo';
		this.render();
		this.subscribeOffline();
	}

	disconnectedCallback() {
		this._offlineUnsub?.();
		this._offlineUnsub = null;
		const runtime = (window as any).__rspaceOfflineRuntime;
		if (runtime) {
			for (const id of this._subscribedDocIds) runtime.unsubscribe(id);
		}
		this._subscribedDocIds = [];
	}

	attributeChangedCallback(name: string, _old: string, val: string) {
		if (name === 'space') this._space = val;
	}

	private async subscribeOffline() {
		let runtime = (window as any).__rspaceOfflineRuntime;
		if (!runtime) {
			await new Promise(r => setTimeout(r, 200));
			runtime = (window as any).__rspaceOfflineRuntime;
		}
		if (!runtime) { this.loadDemoFallback(); return; }
		if (!runtime.isInitialized && runtime.init) {
			try { await runtime.init(); } catch { /* already init'd */ }
		}
		if (!runtime.isInitialized) { this.loadDemoFallback(); return; }

		try {
			const docId = socialsDocId(this._space) as DocumentId;
			const doc = await runtime.subscribe(docId, socialsSchema);
			this._subscribedDocIds.push(docId);
			this.renderFromDoc(doc);

			this._offlineUnsub = runtime.onChange(docId, (updated: any) => {
				this.renderFromDoc(updated);
			});
		} catch {
			this.loadDemoFallback();
		}
	}

	private loadDemoFallback() {
		if (this._threads.length > 0) return; // already have data
		// No runtime available — show static demo content (not editable)
		this._threads = DEMO_FEED.slice(0, 3).map((item, i) => ({
			id: `demo-${i}`,
			name: item.username.replace('@', ''),
			handle: item.username,
			title: item.content.substring(0, 60),
			tweets: [item.content],
			createdAt: Date.now() - (i + 1) * 86400000,
			updatedAt: Date.now() - i * 3600000,
		}));
		this._isDemoFallback = true;
		this.render();
	}

	private renderFromDoc(doc: SocialsDoc) {
		if (!doc?.threads) return;
		this._isDemoFallback = false;
		this._threads = Object.values(doc.threads).sort((a, b) => b.updatedAt - a.updatedAt);

		// Extract draft/scheduled posts from campaigns
		this._draftPosts = [];
		if (doc.campaigns) {
			for (const campaign of Object.values(doc.campaigns)) {
				for (const post of campaign.posts || []) {
					if (post.status === 'draft' || post.status === 'scheduled') {
						this._draftPosts.push({
							id: post.id,
							campaignId: campaign.id,
							campaignTitle: campaign.title,
							platform: post.platform,
							content: post.content,
							scheduledAt: post.scheduledAt,
							status: post.status,
							hashtags: post.hashtags || [],
							threadId: post.threadId,
						});
					}
				}
			}
		}

		this.render();
	}

	private get basePath() {
		const host = window.location.hostname;
		if (host.endsWith('.rspace.online') || host.endsWith('.rsocials.online')) {
			return '/rsocials/';
		}
		return `/${this._space}/rsocials/`;
	}

	private esc(s: string): string {
		return s.replace(/&/g, '&amp;').replace(/</g, '&lt;').replace(/>/g, '&gt;').replace(/"/g, '&quot;');
	}

	private platformIcon(platform: string): string {
		const icons: Record<string, string> = {
			x: '𝕏', twitter: '𝕏', linkedin: '💼', instagram: '📷',
			threads: '🧵', bluesky: '🦋', youtube: '📹', newsletter: '📧',
		};
		return icons[platform.toLowerCase()] || '📱';
	}

	private render() {
		if (!this.shadowRoot) return;
		const space = this._space;
		const threads = this._threads;
		const drafts = this._draftPosts;

		const threadCardsHTML = threads.length === 0 && drafts.length === 0
			? `<div class="empty">
				<p>No posts or threads yet. Create your first thread!</p>
				<a href="${this.basePath}thread-editor" class="btn btn--success">Create Thread</a>
			</div>`
			: `<div class="grid">
				${drafts.map(p => {
					const preview = this.esc(p.content.substring(0, 200));
					const schedDate = p.scheduledAt ? new Date(p.scheduledAt).toLocaleDateString('en-US', { month: 'short', day: 'numeric' }) : '';
					const statusBadge = p.status === 'scheduled'
						? '<span class="badge badge--scheduled">Scheduled</span>'
						: '<span class="badge badge--draft">Draft</span>';
					const href = p.threadId
					? `${this.basePath}thread-editor/${this.esc(p.threadId)}/edit`
					: `${this.basePath}campaign`;
				return `<a href="${href}" class="card card--draft">
						<div class="card__badges">
							${statusBadge}
							<span class="badge badge--campaign">${this.esc(p.campaignTitle)}</span>
						</div>
						<h3 class="card__title">${this.platformIcon(p.platform)} ${this.esc(p.platform)} Post</h3>
						<p class="card__preview">${preview}</p>
						<div class="card__meta">
							${p.hashtags.length ? `<span>${p.hashtags.slice(0, 3).join(' ')}</span>` : ''}
							${schedDate ? `<span>${schedDate}</span>` : ''}
						</div>
					</a>`;
				}).join('')}
				${threads.map(t => {
					const initial = (t.name || '?').charAt(0).toUpperCase();
					const preview = this.esc((t.tweets[0] || '').substring(0, 200));
					const dateStr = new Date(t.updatedAt).toLocaleDateString('en-US', { month: 'short', day: 'numeric' });
					const imageTag = t.imageUrl
						? `<div class="card__image"><img src="${this.esc(t.imageUrl)}" alt="" loading="lazy"></div>`
						: '';
					const href = this._isDemoFallback
						? `${this.basePath}thread-editor`
						: `${this.basePath}thread-editor/${this.esc(t.id)}/edit`;
					return `<a href="${href}" class="card" data-collab-id="thread:${this.esc(t.id)}">
						${imageTag}
						<h3 class="card__title">${this.esc(t.title || 'Untitled Thread')}</h3>
						<p class="card__preview">${preview}</p>
						<div class="card__meta">
							<div class="card__author">
								<div class="card__avatar">${this.esc(initial)}</div>
								<span>${this.esc(t.handle || t.name || 'Anonymous')}</span>
							</div>
							<span>${t.tweets.length} tweet${t.tweets.length === 1 ? '' : 's'}</span>
							<span>${dateStr}</span>
						</div>
					</a>`;
				}).join('')}
			</div>`;

		this.shadowRoot.innerHTML = `
			<style>
				:host { display: block; }
				.gallery { max-width: 900px; margin: 0 auto; padding: 2rem 1rem; }
				.header { display: flex; align-items: center; justify-content: space-between; margin-bottom: 1.5rem; flex-wrap: wrap; gap: 0.75rem; }
				.header h1 {
					margin: 0; font-size: 1.5rem;
					background: linear-gradient(135deg, #7dd3fc, #c4b5fd);
					-webkit-background-clip: text; -webkit-text-fill-color: transparent;
				}
				.btn { padding: 0.5rem 1rem; border-radius: 8px; border: none; font-size: 0.85rem; font-weight: 600; cursor: pointer; transition: all 0.15s; text-decoration: none; display: inline-flex; align-items: center; }
				.btn--primary { background: var(--rs-primary); color: white; }
				.btn--primary:hover { background: var(--rs-primary-hover); }
				.btn--success { background: var(--rs-success); color: white; }
				.btn--success:hover { opacity: 0.85; }
				.grid { display: grid; grid-template-columns: repeat(auto-fill, minmax(280px, 1fr)); gap: 1rem; }
				.empty { color: var(--rs-text-muted, #64748b); text-align: center; padding: 3rem 1rem; font-size: 0.9rem; }
				.card {
					background: var(--rs-bg-surface, #1e293b); border: 1px solid var(--rs-input-border, #334155); border-radius: 0.75rem;
					padding: 1.25rem; transition: border-color 0.15s, transform 0.15s;
					display: flex; flex-direction: column; gap: 0.75rem;
					text-decoration: none; color: inherit;
				}
				.card:hover { border-color: var(--rs-primary); transform: translateY(-2px); }
				.card--draft { border-left: 3px solid #f59e0b; }
				.card__badges { display: flex; gap: 0.4rem; flex-wrap: wrap; }
				.badge {
					font-size: 0.65rem; font-weight: 700; text-transform: uppercase; letter-spacing: 0.05em;
					padding: 0.15rem 0.5rem; border-radius: 4px;
				}
				.badge--draft { background: rgba(245,158,11,0.15); color: #f59e0b; }
				.badge--scheduled { background: rgba(59,130,246,0.15); color: #60a5fa; }
				.badge--campaign { background: rgba(99,102,241,0.15); color: #a5b4fc; }
				.card__title { font-size: 1rem; font-weight: 700; color: var(--rs-text-primary, #f1f5f9); margin: 0; line-height: 1.3; }
				.card__preview {
					font-size: 0.85rem; color: var(--rs-text-secondary, #94a3b8); line-height: 1.5;
					display: -webkit-box; -webkit-line-clamp: 3; -webkit-box-orient: vertical; overflow: hidden;
				}
				.card__meta { display: flex; align-items: center; gap: 0.75rem; font-size: 0.75rem; color: var(--rs-text-muted, #64748b); margin-top: auto; }
				.card__author { display: flex; align-items: center; gap: 0.4rem; }
				.card__avatar {
					width: 20px; height: 20px; border-radius: 50%; background: var(--rs-primary);
					display: flex; align-items: center; justify-content: center;
					color: white; font-weight: 700; font-size: 0.55rem; flex-shrink: 0;
				}
				.card__image { border-radius: 8px; overflow: hidden; border: 1px solid var(--rs-input-border, #334155); margin-bottom: 0.25rem; }
				.card__image img { display: block; width: 100%; height: 120px; object-fit: cover; }
			</style>
			<div class="gallery">
				<div class="header">
					<h1>Posts & Threads</h1>
					<a href="${this.basePath}thread-editor" class="btn btn--primary">New Thread</a>
				</div>
				${threadCardsHTML}
			</div>
		`;
	}
}

customElements.define('folk-thread-gallery', FolkThreadGallery);
