/**
 * Leadlotse Inbox (Etappe 4).
 *
 * Schlankes Vanilla-JS ohne Build. Konsumiert die REST-API
 * leadlotse/v1/entries (Liste, Detail, Statuswechsel). Entry-Daten stammen aus
 * oeffentlichen Formulareingaben und sind untrusted: Ausgabe daher ausschliesslich
 * ueber createElement/textContent, nie ueber innerHTML mit Nutzerdaten.
 */
( function () {
	'use strict';

	var cfg = window.leadlotseInbox || {};
	var i18n = cfg.i18n || {};
	var statusLabels = cfg.statusLabels || {};
	var purposeLabels = cfg.purposeLabels || {};

	var state = {
		status: '',
		search: '',
		page: 1,
		totalPages: 1,
		selectedId: 0,
		items: [],
	};

	var listEl;
	var detailEl;
	var searchTimer = null;

	/**
	 * REST-Aufruf mit Nonce.
	 *
	 * @param {string} path   Pfad relativ zu restBase, z.B. "/entries".
	 * @param {Object} [opts] fetch-Optionen.
	 * @return {Promise<Response>}
	 */
	function apiFetch( path, opts ) {
		opts = opts || {};
		opts.headers = opts.headers || {};
		opts.headers[ 'X-WP-Nonce' ] = cfg.nonce;
		opts.credentials = 'same-origin';
		return fetch( cfg.restBase + path, opts );
	}

	/**
	 * Ein sprechendes Label fuer eine Feld-ID (name -> Name, best_time -> Best time).
	 *
	 * @param {string} key Feld-ID.
	 * @return {string}
	 */
	function humanize( key ) {
		var s = String( key ).replace( /_/g, ' ' ).trim();
		return s.charAt( 0 ).toUpperCase() + s.slice( 1 );
	}

	/**
	 * Anzeigename einer Anfrage (Feld "name", sonst E-Mail, sonst Anfrage-Nr.).
	 *
	 * @param {Object} entry Entry.
	 * @return {string}
	 */
	function entryName( entry ) {
		var fv = entry.field_values || {};
		if ( fv.name ) {
			return String( fv.name );
		}
		if ( entry.email ) {
			return String( entry.email );
		}
		return ( i18n.entry || 'Anfrage' ) + ' #' + entry.id;
	}

	/**
	 * Erzeugt ein Element mit optionalem Text und Klasse.
	 *
	 * @param {string} tag  Tagname.
	 * @param {string} [cls] Klasse.
	 * @param {string} [txt] Textinhalt.
	 * @return {HTMLElement}
	 */
	function el( tag, cls, txt ) {
		var node = document.createElement( tag );
		if ( cls ) {
			node.className = cls;
		}
		if ( undefined !== txt && null !== txt ) {
			node.textContent = txt;
		}
		return node;
	}

	/**
	 * Status-Badge.
	 *
	 * @param {string} status Status.
	 * @return {HTMLElement}
	 */
	function statusBadge( status ) {
		return el(
			'span',
			'hs-status hs-status--' + status,
			statusLabels[ status ] || status
		);
	}

	/**
	 * Formatiert ein GMT-Datum in der Site-Sprache (nur Datum, robust).
	 *
	 * @param {string} gmt MySQL-GMT-Datum.
	 * @return {string}
	 */
	function formatDate( gmt ) {
		if ( ! gmt ) {
			return '';
		}
		var d = new Date( String( gmt ).replace( ' ', 'T' ) + 'Z' );
		if ( isNaN( d.getTime() ) ) {
			return String( gmt );
		}
		return d.toLocaleDateString();
	}

	/**
	 * Laedt die Liste anhand des aktuellen Zustands.
	 *
	 * @return {void}
	 */
	function loadList() {
		listEl.setAttribute( 'aria-busy', 'true' );
		var params =
			'?page=' +
			state.page +
			'&per_page=20&status=' +
			encodeURIComponent( state.status ) +
			'&search=' +
			encodeURIComponent( state.search );

		apiFetch( '/entries' + params )
			.then( function ( res ) {
				if ( ! res.ok ) {
					throw new Error( 'http-' + res.status );
				}
				state.totalPages =
					parseInt( res.headers.get( 'X-WP-TotalPages' ), 10 ) || 1;
				return res.json();
			} )
			.then( function ( items ) {
				state.items = Array.isArray( items ) ? items : [];
				renderList();
			} )
			.catch( function () {
				renderListError();
			} )
			.then( function () {
				listEl.setAttribute( 'aria-busy', 'false' );
			} );
	}

	/**
	 * Rendert die Liste.
	 *
	 * @return {void}
	 */
	function renderList() {
		listEl.textContent = '';

		if ( 0 === state.items.length ) {
			listEl.appendChild(
				el(
					'p',
					'hs-inbox-empty',
					i18n.noEntries || 'Noch keine Anfragen.'
				)
			);
			return;
		}

		state.items.forEach( function ( entry ) {
			var row = el( 'button', 'hs-inbox-row' );
			row.type = 'button';
			row.setAttribute( 'role', 'listitem' );
			if ( entry.id === state.selectedId ) {
				row.classList.add( 'is-selected' );
			}
			if ( 'new' === entry.status ) {
				row.classList.add( 'is-unread' );
			}

			var top = el( 'span', 'hs-inbox-row-top' );
			top.appendChild( el( 'span', 'hs-inbox-row-name', entryName( entry ) ) );
			top.appendChild( statusBadge( entry.status ) );
			row.appendChild( top );

			var meta = el( 'span', 'hs-inbox-row-meta' );
			var purpose = purposeLabels[ entry.purpose ] || '';
			meta.textContent =
				formatDate( entry.created_at ) + ( purpose ? ' - ' + purpose : '' );
			row.appendChild( meta );

			row.addEventListener( 'click', function () {
				selectEntry( entry.id );
			} );
			listEl.appendChild( row );
		} );

		renderPagination();
	}

	/**
	 * Einfache Vor/Zurueck-Navigation.
	 *
	 * @return {void}
	 */
	function renderPagination() {
		if ( state.totalPages <= 1 ) {
			return;
		}
		var nav = el( 'div', 'hs-inbox-pagination' );

		var prev = el( 'button', 'button', i18n.prev || 'Zurueck' );
		prev.type = 'button';
		prev.disabled = state.page <= 1;
		prev.addEventListener( 'click', function () {
			if ( state.page > 1 ) {
				state.page--;
				loadList();
			}
		} );

		var info = el(
			'span',
			'hs-inbox-pageinfo',
			state.page + ' / ' + state.totalPages
		);

		var next = el( 'button', 'button', i18n.next || 'Weiter' );
		next.type = 'button';
		next.disabled = state.page >= state.totalPages;
		next.addEventListener( 'click', function () {
			if ( state.page < state.totalPages ) {
				state.page++;
				loadList();
			}
		} );

		nav.appendChild( prev );
		nav.appendChild( info );
		nav.appendChild( next );
		listEl.appendChild( nav );
	}

	/**
	 * Fehlerzustand der Liste.
	 *
	 * @return {void}
	 */
	function renderListError() {
		listEl.textContent = '';
		listEl.appendChild(
			el(
				'p',
				'hs-inbox-error',
				i18n.loadError ||
					'Die Anfragen konnten nicht geladen werden. Bitte laden Sie die Seite neu.'
			)
		);
	}

	/**
	 * Laedt und zeigt eine Anfrage.
	 *
	 * @param {number} id Entry-ID.
	 * @return {void}
	 */
	function selectEntry( id ) {
		state.selectedId = id;
		renderList();
		detailEl.setAttribute( 'aria-busy', 'true' );

		apiFetch( '/entries/' + id )
			.then( function ( res ) {
				if ( ! res.ok ) {
					throw new Error( 'http-' + res.status );
				}
				return res.json();
			} )
			.then( function ( entry ) {
				renderDetail( entry );
			} )
			.catch( function () {
				detailEl.textContent = '';
				detailEl.appendChild(
					el(
						'p',
						'hs-inbox-error',
						i18n.loadError ||
							'Die Anfrage konnte nicht geladen werden.'
					)
				);
			} )
			.then( function () {
				detailEl.setAttribute( 'aria-busy', 'false' );
			} );
	}

	/**
	 * Rendert das Detail-Panel einer Anfrage.
	 *
	 * @param {Object} entry Entry.
	 * @return {void}
	 */
	function renderDetail( entry ) {
		detailEl.textContent = '';

		var header = el( 'div', 'hs-inbox-detail-header' );
		header.appendChild( el( 'h2', null, entryName( entry ) ) );
		header.appendChild( statusBadge( entry.status ) );
		detailEl.appendChild( header );

		var sub = el( 'p', 'hs-inbox-detail-sub' );
		var purpose = purposeLabels[ entry.purpose ] || '';
		sub.textContent =
			formatDate( entry.created_at ) + ( purpose ? ' - ' + purpose : '' );
		detailEl.appendChild( sub );

		// Feldwerte als Definitionsliste (untrusted -> textContent).
		var dl = el( 'dl', 'hs-inbox-fields' );
		var fv = entry.field_values || {};
		var waOptin = false;
		var idProvider = '';
		Object.keys( fv ).forEach( function ( key ) {
			var value = fv[ key ];
			if ( '' === value || null === value || undefined === value ) {
				return;
			}
			// Technische Werte (Unterstrich-Namensraum) nicht als Feld anzeigen.
			if ( 0 === String( key ).indexOf( '_' ) ) {
				if (
					0 === String( key ).indexOf( '_wa_' ) &&
					'1' === String( value )
				) {
					waOptin = true;
				}
				if ( '_identity' === key ) {
					idProvider = String( value );
				}
				return;
			}
			dl.appendChild( el( 'dt', null, humanize( key ) ) );
			dl.appendChild(
				el(
					'dd',
					null,
					Array.isArray( value ) ? value.join( ', ' ) : String( value )
				)
			);
		} );
		detailEl.appendChild( dl );

		if ( waOptin ) {
			detailEl.appendChild(
				el(
					'p',
					'hs-inbox-wa-optin',
					i18n.waOptin || 'WhatsApp-Antwort erlaubt'
				)
			);
		}

		if ( idProvider ) {
			var providerName =
				idProvider.charAt( 0 ).toUpperCase() + idProvider.slice( 1 );
			var idText = ( i18n.idVerified || 'E-Mail bestaetigt ueber %s' ).replace(
				'%s',
				providerName
			);
			detailEl.appendChild( el( 'p', 'hs-inbox-id-verified', idText ) );
		}

		// Quelle / Attribution.
		if ( entry.utm_source || entry.source_url ) {
			var src = el( 'p', 'hs-inbox-source' );
			src.textContent =
				( i18n.source || 'Quelle' ) +
				': ' +
				( entry.utm_source || entry.source_url );
			detailEl.appendChild( src );
		}

		detailEl.appendChild( renderActions( entry ) );
	}

	/**
	 * Aktionsleiste: Statuswechsel und Antworten.
	 *
	 * @param {Object} entry Entry.
	 * @return {HTMLElement}
	 */
	function renderActions( entry ) {
		var actions = el( 'div', 'hs-inbox-actions' );

		var group = el( 'div', 'hs-inbox-status-group' );
		group.setAttribute( 'role', 'group' );
		group.setAttribute(
			'aria-label',
			i18n.statusLabel || 'Status der Anfrage'
		);
		[ 'new', 'in_progress', 'done' ].forEach( function ( status ) {
			var btn = el(
				'button',
				'button hs-inbox-status-btn',
				statusLabels[ status ] || status
			);
			btn.type = 'button';
			if ( entry.status === status ) {
				btn.classList.add( 'button-primary' );
				btn.setAttribute( 'aria-pressed', 'true' );
			} else {
				btn.setAttribute( 'aria-pressed', 'false' );
			}
			btn.addEventListener( 'click', function () {
				updateStatus( entry.id, status );
			} );
			group.appendChild( btn );
		} );
		actions.appendChild( group );

		if ( entry.email ) {
			var reply = el(
				'a',
				'button button-secondary hs-inbox-reply',
				i18n.reply || 'Antworten'
			);
			reply.href = 'mailto:' + encodeURIComponent( entry.email );
			actions.appendChild( reply );
		}

		return actions;
	}

	/**
	 * Setzt den Status einer Anfrage.
	 *
	 * @param {number} id     Entry-ID.
	 * @param {string} status Neuer Status.
	 * @return {void}
	 */
	function updateStatus( id, status ) {
		apiFetch( '/entries/' + id + '/status', {
			method: 'POST',
			headers: { 'Content-Type': 'application/json' },
			body: JSON.stringify( { status: status } ),
		} )
			.then( function ( res ) {
				if ( ! res.ok ) {
					throw new Error( 'http-' + res.status );
				}
				return res.json();
			} )
			.then( function ( entry ) {
				// Liste lokal aktualisieren, dann Detail neu zeichnen.
				state.items = state.items.map( function ( item ) {
					return item.id === entry.id ? entry : item;
				} );
				renderList();
				renderDetail( entry );
			} )
			.catch( function () {
				window.alert(
					i18n.statusError ||
						'Der Status konnte nicht gespeichert werden.'
				);
			} );
	}

	/**
	 * Verdrahtet Filter-Tabs und Suche.
	 *
	 * @return {void}
	 */
	function bindControls() {
		var links = document.querySelectorAll( '.hs-inbox-filter-link' );
		links.forEach( function ( link ) {
			link.addEventListener( 'click', function ( e ) {
				e.preventDefault();
				links.forEach( function ( l ) {
					l.classList.remove( 'current' );
					l.setAttribute( 'aria-selected', 'false' );
				} );
				link.classList.add( 'current' );
				link.setAttribute( 'aria-selected', 'true' );
				state.status = link.getAttribute( 'data-status' ) || '';
				state.page = 1;
				loadList();
			} );
		} );

		var search = document.getElementById( 'hs-inbox-search-input' );
		if ( search ) {
			search.addEventListener( 'input', function () {
				window.clearTimeout( searchTimer );
				searchTimer = window.setTimeout( function () {
					state.search = search.value;
					state.page = 1;
					loadList();
				}, 300 );
			} );
		}
	}

	document.addEventListener( 'DOMContentLoaded', function () {
		listEl = document.getElementById( 'hs-inbox-list' );
		detailEl = document.getElementById( 'hs-inbox-detail' );
		if ( ! listEl || ! detailEl ) {
			return;
		}
		bindControls();
		loadList();
	} );
} )();
