<?php
/**
 * HTTP-Client zum zentralen KK-AI-Proxy (serv01).
 *
 * Hält Server-URL + Lizenzschlüssel, fragt den Funktionsstatus ab und ruft
 * die Alt-Text-Erzeugung auf. Der API-Schlüssel des KI-Anbieters liegt
 * ausschließlich auf dem Proxy, nie auf der Kundenseite.
 */
if ( ! defined( 'ABSPATH' ) ) {
	exit;
}

class WAVE_AI_Client {

	const OPT = 'wave_ai_options';

	public static function get_options() {
		$defaults = array(
			'server_url'    => 'https://wavetools.io/api/wave-ai/v1',
			'license_key'   => '',
			'auto_upload'   => false,
			'lang'          => '',
			'easy_language' => true, // Website-Schalter (zusätzlich zur Lizenz-Freischaltung)
			'tts'           => true,
		);
		$o = get_option( self::OPT, array() );
		$o = wp_parse_args( is_array( $o ) ? $o : array(), $defaults );
		// Migration: alte Hub-URLs (kk-ai-proxy) auf den Wave-Tools-Dienst umbiegen.
		if ( false !== strpos( (string) $o['server_url'], 'serv01.klopkom.de' ) ) {
			$o['server_url'] = $defaults['server_url'];
			update_option( self::OPT, $o, false );
		}
		// Zentrale Wave-Lizenz hat Vorrang: EIN Schlüssel für alles.
		if ( class_exists( 'Wave_License' ) && Wave_License::key() ) {
			$o['license_key'] = Wave_License::key();
		}
		return $o;
	}

	public static function update_options( $o ) {
		update_option( self::OPT, $o, false );
		delete_transient( 'wave_ai_status' );
	}

	/** Antwort-Sprache (ISO-Kürzel) – konfiguriert oder aus der Site-Locale. */
	public static function lang() {
		$o = self::get_options();
		if ( ! empty( $o['lang'] ) ) {
			return $o['lang'];
		}
		$l = get_bloginfo( 'language' ); // z. B. de-DE
		return $l ? substr( $l, 0, 2 ) : 'de';
	}

	/**
	 * Funktionsstatus der Lizenz (gecacht 1 h).
	 *
	 * @return array { ok, features[], quota, used, message }
	 */
	public static function status( $force = false ) {
		if ( ! $force ) {
			$cached = get_transient( 'wave_ai_status' );
			if ( is_array( $cached ) ) {
				return $cached;
			}
		}
		$o = self::get_options();
		if ( empty( $o['license_key'] ) ) {
			return array( 'ok' => false, 'features' => array(), 'message' => 'Kein Lizenzschlüssel hinterlegt.' );
		}
		$res = self::post( '/status', array( 'license_key' => $o['license_key'] ), 15 );
		if ( is_wp_error( $res ) ) {
			return array( 'ok' => false, 'features' => array(), 'message' => $res->get_error_message() );
		}
		set_transient( 'wave_ai_status', $res, HOUR_IN_SECONDS );
		return $res;
	}

	public static function feature_enabled( $feature ) {
		$s = self::status();
		return ! empty( $s['ok'] ) && ! empty( $s['features'] ) && in_array( $feature, (array) $s['features'], true );
	}

	/**
	 * Alt-Text für eine Bilddatei erzeugen.
	 *
	 * @return array|WP_Error { ok, alt, decorative, used, quota }
	 */
	public static function alt_text( $file_path, $mime, $filename, $context = '' ) {
		$o = self::get_options();
		if ( empty( $o['license_key'] ) ) {
			return new WP_Error( 'license', 'Kein Lizenzschlüssel hinterlegt.' );
		}
		if ( ! file_exists( $file_path ) || ! is_readable( $file_path ) ) {
			return new WP_Error( 'file', 'Bilddatei nicht lesbar.' );
		}
		$data = @file_get_contents( $file_path );
		if ( false === $data || '' === $data ) {
			return new WP_Error( 'file', 'Bild konnte nicht gelesen werden.' );
		}
		return self::post(
			'/alt-text',
			array(
				'license_key' => $o['license_key'],
				'image_b64'   => base64_encode( $data ),
				'media_type'  => $mime,
				'filename'    => $filename,
				'lang'        => self::lang(),
				'context'     => $context,
			),
			60
		);
	}

	/**
	 * Text in Leichte Sprache übersetzen: array mit text oder WP_Error.
	 */
	public static function easy_language( $text ) {
		$o = self::get_options();
		if ( empty( $o['license_key'] ) ) {
			return new WP_Error( 'license', 'Kein Lizenzschlüssel hinterlegt.' );
		}
		return self::post(
			'/easy-language',
			array(
				'license_key' => $o['license_key'],
				'text'        => $text,
				'lang'        => self::lang(),
			),
			120
		);
	}

	/**
	 * Text vorlesen lassen: liefert array mit audio_b64 (MP3) oder WP_Error.
	 */
	public static function tts( $text ) {
		$o = self::get_options();
		if ( empty( $o['license_key'] ) ) {
			return new WP_Error( 'license', 'Kein Lizenzschlüssel hinterlegt.' );
		}
		return self::post(
			'/tts',
			array(
				'license_key' => $o['license_key'],
				'text'        => $text,
			),
			90
		);
	}

	/**
	 * Low-Level-POST → dekodiertes Array oder WP_Error.
	 */
	private static function post( $path, $body, $timeout = 20 ) {
		$o   = self::get_options();
		$url = rtrim( $o['server_url'], '/' ) . $path;

		$resp = wp_remote_post(
			$url,
			array(
				'timeout' => $timeout,
				'headers' => array( 'content-type' => 'application/json' ),
				'body'    => wp_json_encode( $body ),
			)
		);

		if ( is_wp_error( $resp ) ) {
			return $resp;
		}

		$code = (int) wp_remote_retrieve_response_code( $resp );
		$json = json_decode( wp_remote_retrieve_body( $resp ), true );

		if ( ! is_array( $json ) ) {
			return new WP_Error( 'resp', 'Ungültige Antwort vom KI-Proxy (HTTP ' . $code . ').' );
		}
		if ( empty( $json['ok'] ) ) {
			$msg      = isset( $json['message'] ) ? $json['message'] : ( 'HTTP ' . $code );
			// Fehlercode des Proxys erhalten, damit der Aufrufer Einzelbild-Fehler
			// (mime/size/image/upstream) von kontoweiten Fehlern (license/quota/…) unterscheiden kann.
			$err_code = isset( $json['code'] ) ? sanitize_key( $json['code'] ) : 'proxy';
			return new WP_Error( $err_code, $msg );
		}
		return $json;
	}
}
