<?php
/**
 * Weekly newsroom report email (editor-in-chief digest).
 *
 * Hooks into the existing `newsai_weekly_cleanup` cron (after task DB hygiene).
 *
 * @package Newsroom_AI_Assistant
 */

if ( ! defined( 'ABSPATH' ) ) {
	exit;
}

if ( ! function_exists( 'newsai_weekly_report_enabled' ) ) {
	function newsai_weekly_report_enabled() {
		return get_option( 'newsai_weekly_report_enabled', 'no' ) === 'yes';
	}
}

if ( ! function_exists( 'newsai_weekly_report_window_days' ) ) {
	function newsai_weekly_report_window_days() {
		$days = (int) get_option( 'newsai_weekly_report_window_days', 7 );
		return max( 7, min( 30, $days ) );
	}
}

if ( ! function_exists( 'newsai_weekly_report_recipients' ) ) {
	/**
	 * @return list<string> Valid email addresses.
	 */
	function newsai_weekly_report_recipients() {
		$raw = (string) get_option( 'newsai_weekly_report_recipients', '' );
		$lines = preg_split( '/[\s,;]+/', $raw, -1, PREG_SPLIT_NO_EMPTY );
		$out   = [];
		foreach ( (array) $lines as $line ) {
			$email = sanitize_email( $line );
			if ( $email !== '' && is_email( $email ) ) {
				$out[] = $email;
			}
		}
		$out = array_values( array_unique( $out ) );
		if ( $out !== [] ) {
			return $out;
		}
		$admins = get_users(
			[
				'capability' => 'manage_options',
				'fields'     => [ 'user_email' ],
			]
		);
		foreach ( (array) $admins as $user ) {
			if ( ! empty( $user->user_email ) && is_email( $user->user_email ) ) {
				$out[] = $user->user_email;
			}
		}
		return array_values( array_unique( $out ) );
	}
}

if ( ! function_exists( 'newsai_weekly_sparkline' ) ) {
	/**
	 * ASCII sparkline from numeric series (8 levels).
	 *
	 * @param list<int|float> $values
	 */
	function newsai_weekly_sparkline( array $values ) {
		$chars = [ '▁', '▂', '▃', '▄', '▅', '▆', '▇', '█' ];
		if ( $values === [] ) {
			return '—';
		}
		$max = max( $values );
		$min = min( $values );
		if ( $max <= 0 ) {
			return str_repeat( $chars[0], count( $values ) );
		}
		$span = $max - $min;
		$out  = '';
		foreach ( $values as $v ) {
			$v = (float) $v;
			if ( $span <= 0 ) {
				$idx = 7;
			} else {
				$idx = (int) round( ( ( $v - $min ) / $span ) * 7 );
			}
			$idx = max( 0, min( 7, $idx ) );
			$out .= $chars[ $idx ];
		}
		return $out;
	}
}

if ( ! function_exists( 'newsai_weekly_report_score_stats' ) ) {
	/**
	 * Average focus / discover scores for published posts in window.
	 *
	 * @return array{avg_focus:int,avg_discover:int,sample_focus:int,sample_discover:int,posts:int}
	 */
	function newsai_weekly_report_score_stats( $days ) {
		global $wpdb;
		$days         = max( 7, min( 30, (int) $days ) );
		$since        = function_exists( 'newsai_sql_datetime_days_ago' ) ? newsai_sql_datetime_days_ago( $days, true ) : gmdate( 'Y-m-d H:i:s', strtotime( '-' . $days . ' days' ) );
		$discover_key = function_exists( 'newsai_discover_score_meta_key' ) ? newsai_discover_score_meta_key() : '_newsai_discover_score';
		$focus_live   = function_exists( 'newsai_focus_score_meta_key' ) ? newsai_focus_score_meta_key() : '_newsai_focus_score';
		$focus_pin    = function_exists( 'newsai_focus_score_history_meta_key' ) ? newsai_focus_score_history_meta_key() : '_newsai_focus_score_at_publish';

		$post_ids = $wpdb->get_col(
			$wpdb->prepare(
				"SELECT ID FROM {$wpdb->posts}
				WHERE post_type = 'post' AND post_status = 'publish' AND post_date_gmt >= %s",
				$since
			)
		);
		$focus_sum = 0;
		$focus_n   = 0;
		$disc_sum  = 0;
		$disc_n    = 0;
		foreach ( (array) $post_ids as $pid ) {
			$pid = (int) $pid;
			$focus = max( (int) get_post_meta( $pid, $focus_pin, true ), (int) get_post_meta( $pid, $focus_live, true ) );
			if ( $focus > 0 ) {
				$focus_sum += $focus;
				$focus_n++;
			}
			$disc = (int) get_post_meta( $pid, $discover_key, true );
			if ( $disc > 0 ) {
				$disc_sum += $disc;
				$disc_n++;
			}
		}
		return [
			'avg_focus'       => $focus_n > 0 ? (int) round( $focus_sum / $focus_n ) : 0,
			'avg_discover'    => $disc_n > 0 ? (int) round( $disc_sum / $disc_n ) : 0,
			'sample_focus'    => $focus_n,
			'sample_discover' => $disc_n,
			'posts'           => count( (array) $post_ids ),
		];
	}
}

if ( ! function_exists( 'newsai_weekly_report_breaking_count' ) ) {
	function newsai_weekly_report_breaking_count() {
		global $wpdb;
		$now = (int) current_time( 'timestamp' );
		// phpcs:ignore WordPress.DB.DirectDatabaseQuery.DirectQuery, WordPress.DB.DirectDatabaseQuery.NoCaching
		return (int) $wpdb->get_var(
			$wpdb->prepare(
				"SELECT COUNT(DISTINCT post_id) FROM {$wpdb->postmeta}
				WHERE meta_key = %s AND meta_value = %s
				AND EXISTS (
					SELECT 1 FROM {$wpdb->postmeta} e
					WHERE e.post_id = {$wpdb->postmeta}.post_id
					AND e.meta_key = %s AND CAST(e.meta_value AS UNSIGNED) > %d
				)",
				'_newsai_breaking_active',
				'yes',
				'_newsai_breaking_expires',
				$now
			)
		);
	}
}

if ( ! function_exists( 'newsai_weekly_report_gsc_summary' ) ) {
	/**
	 * @return array{ready:bool,channels:array<string,array{clicks:int,impressions:int,delta:int,spark:string}>,top:list<array>}
	 */
	function newsai_weekly_report_gsc_summary( $days ) {
		$empty = [
			'ready'    => false,
			'channels' => [],
			'top'      => [],
		];
		if ( ! function_exists( 'newsai_gsc_data_available' ) || ! newsai_gsc_data_available() ) {
			return $empty;
		}
		global $wpdb;
		$days   = max( 7, min( 30, (int) $days ) );
		$table  = newsai_gsc_table_name();
		$bounds = newsai_gsc_insights_period_bounds( $days );

		$channels = [ 'web', 'discover', 'googleNews' ];
		$ch_out   = [];
		foreach ( $channels as $type ) {
			// phpcs:ignore WordPress.DB.DirectDatabaseQuery.DirectQuery, WordPress.DB.DirectDatabaseQuery.NoCaching
			$cur = $wpdb->get_row(
				$wpdb->prepare(
					"SELECT SUM(clicks) AS c, SUM(impressions) AS i FROM {$table}
					WHERE search_type = %s AND data_date >= %s AND data_date <= %s",
					$type,
					$bounds['cur_start'],
					$bounds['cur_end']
				),
				ARRAY_A
			);
			// phpcs:ignore WordPress.DB.DirectDatabaseQuery.DirectQuery, WordPress.DB.DirectDatabaseQuery.NoCaching
			$prev = $wpdb->get_row(
				$wpdb->prepare(
					"SELECT SUM(clicks) AS c FROM {$table}
					WHERE search_type = %s AND data_date >= %s AND data_date <= %s",
					$type,
					$bounds['prev_start'],
					$bounds['prev_end']
				),
				ARRAY_A
			);
			$clicks = (int) ( $cur['c'] ?? 0 );
			$prev_c = (int) ( $prev['c'] ?? 0 );
			$daily  = $wpdb->get_col(
				$wpdb->prepare(
					"SELECT SUM(clicks) FROM {$table}
					WHERE search_type = %s AND data_date >= %s AND data_date <= %s
					GROUP BY data_date ORDER BY data_date ASC",
					$type,
					$bounds['cur_start'],
					$bounds['cur_end']
				)
			);
			$ch_out[ $type ] = [
				'clicks'      => $clicks,
				'impressions' => (int) ( $cur['i'] ?? 0 ),
				'delta'       => $clicks - $prev_c,
				'spark'       => newsai_weekly_sparkline( array_map( 'intval', (array) $daily ) ),
			];
		}

		$top = function_exists( 'newsai_gsc_insights_top_posts_with_trends' )
			? newsai_gsc_insights_top_posts_with_trends( $days, 'discover', 5, 1 )
			: [];

		return [
			'ready'    => true,
			'channels' => $ch_out,
			'top'      => $top,
		];
	}
}

if ( ! function_exists( 'newsai_weekly_report_collect' ) ) {
	/**
	 * @return array<string, mixed>
	 */
	function newsai_weekly_report_collect() {
		$days = newsai_weekly_report_window_days();
		$kpis = function_exists( 'newsai_get_dashboard_post_publish_kpis' )
			? newsai_get_dashboard_post_publish_kpis()
			: [ 'posts_this_week' => 0, 'posts_last_week' => 0, 'total_posts_30d' => 0 ];

		$table = '';
		global $wpdb;
		$table = $wpdb->prefix . 'newsai_alerts';
		$due   = function_exists( 'newsai_get_dashboard_due_metrics_cached' )
			? newsai_get_dashboard_due_metrics_cached( $table )
			: [ 'overdue' => 0, 'due_today' => 0 ];

		$leaderboard = function_exists( 'newsai_pro_get_writer_leaderboard' )
			? newsai_pro_get_writer_leaderboard( 5 )
			: [];

		$bounds = function_exists( 'newsai_gsc_insights_period_bounds' )
			? newsai_gsc_insights_period_bounds( $days )
			: [
				'cur_start' => gmdate( 'Y-m-d', strtotime( '-' . $days . ' days' ) ),
				'cur_end'   => gmdate( 'Y-m-d' ),
			];

		return [
			'days'          => $days,
			'period_label'  => $bounds['cur_start'] . ' → ' . $bounds['cur_end'],
			'site_name'     => wp_specialchars_decode( get_bloginfo( 'name' ), ENT_QUOTES ),
			'site_url'      => home_url( '/' ),
			'dashboard_url' => admin_url( 'admin.php?page=newsai-settings&tab=alerts' ),
			'insights_url'  => admin_url( 'admin.php?page=newsai-settings&tab=insights' ),
			'is_pro'        => function_exists( 'newsai_is_pro' ) && newsai_is_pro(),
			'kpis'          => $kpis,
			'due'           => $due,
			'scores'        => newsai_weekly_report_score_stats( $days ),
			'breaking'      => newsai_weekly_report_breaking_count(),
			'leaderboard'   => $leaderboard,
			'traffic_drops' => function_exists( 'newsai_weekly_report_traffic_drop_section' ) ? newsai_weekly_report_traffic_drop_section() : [ 'enabled' => false, 'items' => [] ],
			'gsc'           => newsai_weekly_report_gsc_summary( $days ),
			'seasonal'      => function_exists( 'newsai_weekly_report_seasonal_section' ) ? newsai_weekly_report_seasonal_section() : [ 'enabled' => false, 'items' => [] ],
			'generated_utc' => gmdate( 'Y-m-d H:i' ) . ' UTC',
		];
	}
}

if ( ! function_exists( 'newsai_weekly_report_trend_arrow' ) ) {
	function newsai_weekly_report_trend_arrow( $trend ) {
		if ( $trend === 'up' ) {
			return '↗';
		}
		if ( $trend === 'down' ) {
			return '↘';
		}
		if ( $trend === 'new' ) {
			return '★';
		}
		return '→';
	}
}

if ( ! function_exists( 'newsai_weekly_report_build_html' ) ) {
	/**
	 * @param array<string, mixed> $data From newsai_weekly_report_collect().
	 */
	function newsai_weekly_report_build_html( array $data ) {
		$h   = static function ( $s ) {
			return esc_html( (string) $s );
		};
		$u   = static function ( $url ) {
			return esc_url( (string) $url );
		};

		$kpis    = isset( $data['kpis'] ) && is_array( $data['kpis'] ) ? $data['kpis'] : [];
		$scores  = isset( $data['scores'] ) && is_array( $data['scores'] ) ? $data['scores'] : [];
		$due     = isset( $data['due'] ) && is_array( $data['due'] ) ? $data['due'] : [];
		$gsc     = isset( $data['gsc'] ) && is_array( $data['gsc'] ) ? $data['gsc'] : [];
		$traffic_drops = isset( $data['traffic_drops'] ) && is_array( $data['traffic_drops'] ) ? $data['traffic_drops'] : [];
		$seasonal = isset( $data['seasonal'] ) && is_array( $data['seasonal'] ) ? $data['seasonal'] : [];
		$board   = isset( $data['leaderboard'] ) && is_array( $data['leaderboard'] ) ? $data['leaderboard'] : [];

		$week_posts = (int) ( $kpis['posts_this_week'] ?? 0 );
		$last_week  = (int) ( $kpis['posts_last_week'] ?? 0 );
		$pub_delta  = $week_posts - $last_week;

		ob_start();
		?>
<!DOCTYPE html>
<html>
<head><meta charset="utf-8"><title><?php echo $h( $data['site_name'] ?? '' ); ?></title></head>
<body style="margin:0;padding:0;background:#f3f4f6;font-family:-apple-system,BlinkMacSystemFont,'Segoe UI',Roboto,sans-serif;">
<table role="presentation" width="100%" cellpadding="0" cellspacing="0" style="background:#f3f4f6;padding:24px 12px;">
<tr><td align="center">
<table role="presentation" width="600" cellpadding="0" cellspacing="0" style="max-width:600px;background:#ffffff;border:1px solid #e5e7eb;border-radius:12px;overflow:hidden;">
<tr><td style="background:linear-gradient(135deg,#1e3a8a,#4338ca);color:#fff;padding:22px 24px;">
<div style="font-size:11px;opacity:.85;text-transform:uppercase;letter-spacing:.08em;"><?php echo esc_html__( 'Weekly Newsroom Report', 'newsroom-ai-assistant' ); ?></div>
<div style="font-size:22px;font-weight:700;margin-top:6px;"><?php echo $h( $data['site_name'] ?? '' ); ?></div>
<div style="font-size:13px;margin-top:8px;opacity:.9;"><?php echo $h( $data['period_label'] ?? '' ); ?></div>
</td></tr>
<tr><td style="padding:20px 24px;color:#111827;font-size:14px;line-height:1.5;">
<p style="margin:0 0 16px;"><?php
echo esc_html(
	sprintf(
		/* translators: 1: posts published this week, 2: change vs prior week */
		__( 'Your desk published %1$d articles this week (%2$s vs the prior week).', 'newsroom-ai-assistant' ),
		$week_posts,
		( $pub_delta >= 0 ? '+' : '' ) . $pub_delta
	)
);
?></p>
<table role="presentation" width="100%" cellpadding="8" cellspacing="0" style="margin-bottom:18px;border-collapse:separate;border-spacing:0;">
<tr>
<td style="background:#f9fafb;border:1px solid #e5e7eb;border-radius:8px;width:25%;text-align:center;">
<div style="font-size:11px;color:#6b7280;text-transform:uppercase;"><?php echo esc_html__( 'Focus avg', 'newsroom-ai-assistant' ); ?></div>
<div style="font-size:22px;font-weight:700;color:#111827;"><?php echo $h( (int) ( $scores['avg_focus'] ?? 0 ) ); ?>%</div>
</td>
<td style="background:#f9fafb;border:1px solid #e5e7eb;border-radius:8px;width:25%;text-align:center;">
<div style="font-size:11px;color:#6b7280;text-transform:uppercase;"><?php echo esc_html__( 'Discover avg', 'newsroom-ai-assistant' ); ?></div>
<div style="font-size:22px;font-weight:700;color:#111827;"><?php echo $h( (int) ( $scores['avg_discover'] ?? 0 ) ); ?>%</div>
</td>
<td style="background:#f9fafb;border:1px solid #e5e7eb;border-radius:8px;width:25%;text-align:center;">
<div style="font-size:11px;color:#6b7280;text-transform:uppercase;"><?php echo esc_html__( 'Breaking live', 'newsroom-ai-assistant' ); ?></div>
<div style="font-size:22px;font-weight:700;color:#111827;"><?php echo $h( (int) ( $data['breaking'] ?? 0 ) ); ?></div>
</td>
<td style="background:#fef2f2;border:1px solid #fecaca;border-radius:8px;width:25%;text-align:center;">
<div style="font-size:11px;color:#991b1b;text-transform:uppercase;"><?php echo esc_html__( 'Overdue tasks', 'newsroom-ai-assistant' ); ?></div>
<div style="font-size:22px;font-weight:700;color:#991b1b;"><?php echo $h( (int) ( $due['overdue'] ?? 0 ) ); ?></div>
</td>
</tr>
</table>
<?php if ( ! empty( $board ) ) : ?>
<h3 style="margin:18px 0 8px;font-size:15px;color:#111827;"><?php echo esc_html__( 'Author leaderboard (30 days)', 'newsroom-ai-assistant' ); ?></h3>
<table role="presentation" width="100%" cellpadding="6" cellspacing="0" style="border-collapse:collapse;font-size:13px;">
<?php foreach ( $board as $row ) : ?>
<tr style="border-bottom:1px solid #f0f0f1;">
<td style="padding:8px 4px;"><?php echo $h( $row['name'] ?? '' ); ?></td>
<td style="padding:8px 4px;text-align:right;font-weight:700;"><?php echo $h( (int) ( $row['posts_30d'] ?? 0 ) ); ?></td>
<td style="padding:8px 4px;text-align:right;width:32px;"><?php echo esc_html( newsai_weekly_report_trend_arrow( (string) ( $row['trend'] ?? 'flat' ) ) ); ?></td>
</tr>
<?php endforeach; ?>
</table>
<?php endif; ?>
<?php
$gsc_ready = ! empty( $gsc['ready'] );
if ( $gsc_ready && ! empty( $gsc['channels'] ) ) :
	$labels = [
		'web'        => __( 'Web', 'newsroom-ai-assistant' ),
		'discover'   => __( 'Discover', 'newsroom-ai-assistant' ),
		'googleNews' => __( 'Google News', 'newsroom-ai-assistant' ),
	];
	?>
<h3 style="margin:18px 0 8px;font-size:15px;color:#111827;"><?php echo esc_html__( 'Search Console clicks', 'newsroom-ai-assistant' ); ?></h3>
<table role="presentation" width="100%" cellpadding="6" cellspacing="0" style="border-collapse:collapse;font-size:13px;">
<?php foreach ( $labels as $key => $label ) :
	if ( empty( $gsc['channels'][ $key ] ) ) {
		continue;
	}
	$ch = $gsc['channels'][ $key ];
	$delta = (int) ( $ch['delta'] ?? 0 );
	?>
<tr style="border-bottom:1px solid #f0f0f1;">
<td style="padding:8px 4px;"><?php echo $h( $label ); ?></td>
<td style="padding:8px 4px;font-family:Consolas,Monaco,monospace;"><?php echo $h( $ch['spark'] ?? '' ); ?></td>
<td style="padding:8px 4px;text-align:right;font-weight:700;"><?php echo $h( number_format_i18n( (int) ( $ch['clicks'] ?? 0 ) ) ); ?></td>
<td style="padding:8px 4px;text-align:right;color:<?php echo $delta >= 0 ? '#047857' : '#b91c1c'; ?>;"><?php echo esc_html( ( $delta >= 0 ? '+' : '' ) . $delta ); ?></td>
</tr>
<?php endforeach; ?>
</table>
<?php if ( ! empty( $gsc['top'] ) ) : ?>
<h4 style="margin:14px 0 6px;font-size:13px;color:#374151;"><?php echo esc_html__( 'Top Discover articles', 'newsroom-ai-assistant' ); ?></h4>
<ul style="margin:0;padding:0 0 0 18px;font-size:13px;">
<?php foreach ( $gsc['top'] as $art ) : ?>
<li style="margin-bottom:6px;"><?php echo $h( $art['title'] ?? '' ); ?>
<span style="color:#6b7280;"> — <?php echo $h( number_format_i18n( (int) ( $art['clicks'] ?? 0 ) ) ); ?> <?php echo esc_html__( 'clicks', 'newsroom-ai-assistant' ); ?>
<?php echo esc_html( newsai_weekly_report_trend_arrow( (string) ( $art['trend'] ?? 'flat' ) ) ); ?></span></li>
<?php endforeach; ?>
</ul>
<?php endif; ?>
<?php elseif ( empty( $data['is_pro'] ) ) : ?>
<p style="margin:12px 0;font-size:12px;color:#6b7280;"><?php echo esc_html__( 'GSC traffic sections unlock with Newsroom Pro and a connected Search Console sync.', 'newsroom-ai-assistant' ); ?></p>
<?php else : ?>
<p style="margin:12px 0;font-size:12px;color:#6b7280;"><?php echo esc_html__( 'No Search Console data synced yet for this window.', 'newsroom-ai-assistant' ); ?></p>
<?php endif; ?>
<?php if ( ! empty( $seasonal['enabled'] ) && ! empty( $seasonal['items'] ) ) : ?>
<h3 style="margin:18px 0 8px;font-size:15px;color:#111827;"><?php echo esc_html__( 'Seasonal radar — plan ahead', 'newsroom-ai-assistant' ); ?></h3>
<p style="margin:0 0 8px;font-size:13px;"><?php
echo esc_html(
	sprintf(
		/* translators: %d: lead days */
		__( 'Keywords and tags that drove traffic around this time last year (~%d-day lead):', 'newsroom-ai-assistant' ),
		(int) ( $seasonal['lead'] ?? 30 )
	)
);
?></p>
<ul style="margin:0;padding:0 0 0 18px;font-size:13px;">
<?php foreach ( (array) $seasonal['items'] as $item ) : ?>
<li style="margin-bottom:8px;"><strong><?php echo $h( $item['term'] ?? '' ); ?></strong>
<span style="color:#6b7280;"> — <?php echo $h( number_format_i18n( (int) ( $item['yoy_clicks'] ?? 0 ) ) ); ?> <?php echo esc_html__( 'YoY clicks', 'newsroom-ai-assistant' ); ?>
· <?php echo $h( ( ( $item['source'] ?? '' ) === 'gsc_query' ) ? __( 'GSC query', 'newsroom-ai-assistant' ) : __( 'Tag', 'newsroom-ai-assistant' ) ); ?>
· <?php echo $h( $item['target_window'] ?? '' ); ?></span></li>
<?php endforeach; ?>
</ul>
<?php endif; ?>
<?php if ( ! empty( $traffic_drops['enabled'] ) && ! empty( $traffic_drops['items'] ) ) : ?>
<h3 style="margin:18px 0 8px;font-size:15px;color:#111827;"><?php echo esc_html__( 'GSC traffic drops', 'newsroom-ai-assistant' ); ?></h3>
<p style="margin:0 0 8px;font-size:13px;"><?php
echo esc_html(
	sprintf(
		/* translators: %d: comparison window days */
		__( 'Articles losing meaningful GSC clicks vs the previous %d-day window:', 'newsroom-ai-assistant' ),
		(int) ( $traffic_drops['days'] ?? 28 )
	)
);
?></p>
<ul style="margin:0;padding:0 0 0 18px;font-size:13px;">
<?php foreach ( (array) $traffic_drops['items'] as $drop ) : ?>
<li style="margin-bottom:8px;"><strong><?php echo $h( $drop['title'] ?? '' ); ?></strong>
<span style="color:#6b7280;"> — <?php echo $h( number_format_i18n( (int) ( $drop['prev_clicks'] ?? 0 ) ) ); ?> → <?php echo $h( number_format_i18n( (int) ( $drop['clicks'] ?? 0 ) ) ); ?>
(<?php echo $h( number_format_i18n( (int) ( $drop['delta_clicks'] ?? 0 ) ) ); ?>)</span></li>
<?php endforeach; ?>
</ul>
<?php endif; ?>
<p style="margin:20px 0 0;">
<a href="<?php echo $u( $data['dashboard_url'] ?? '' ); ?>" style="display:inline-block;background:#2563eb;color:#fff;text-decoration:none;padding:10px 16px;border-radius:8px;font-weight:600;font-size:13px;"><?php echo esc_html__( 'Open dashboard', 'newsroom-ai-assistant' ); ?></a>
&nbsp;
<a href="<?php echo $u( $data['insights_url'] ?? '' ); ?>" style="display:inline-block;color:#2563eb;font-size:13px;"><?php echo esc_html__( 'Chief Insights', 'newsroom-ai-assistant' ); ?></a>
</p>
<p style="margin:16px 0 0;font-size:11px;color:#9ca3af;"><?php
echo esc_html(
	sprintf(
		/* translators: %s: UTC timestamp */
		__( 'Generated %s · Newsroom OS', 'newsroom-ai-assistant' ),
		(string) ( $data['generated_utc'] ?? '' )
	)
);
?></p>
</td></tr>
</table>
</td></tr>
</table>
</body>
</html>
		<?php
		return (string) ob_get_clean();
	}
}

if ( ! function_exists( 'newsai_weekly_report_mail_error_message' ) ) {
	/**
	 * Human-readable mail failure for admin UI.
	 *
	 * @param string $code   Internal code.
	 * @param string $detail Optional PHPMailer / wp_mail_failed detail.
	 */
	function newsai_weekly_report_mail_error_message( $code, $detail = '' ) {
		$map = [
			'disabled'            => __( 'Enable “Send weekly digest” and save settings first.', 'newsroom-ai-assistant' ),
			'no_recipients'       => __( 'No valid recipient addresses. Add one email per line or ensure an Administrator has an email.', 'newsroom-ai-assistant' ),
			'invalid_admin_email' => __( 'WordPress admin email is missing or invalid. Set it under Settings → General.', 'newsroom-ai-assistant' ),
			'mail_failed'         => __( 'WordPress could not send mail. Many hosts block PHP mail() — use an SMTP plugin (e.g. WP Mail SMTP, FluentSMTP).', 'newsroom-ai-assistant' ),
		];
		$msg = isset( $map[ $code ] ) ? $map[ $code ] : $code;
		$detail = trim( (string) $detail );
		if ( $detail !== '' ) {
			$msg .= ' (' . $detail . ')';
		}
		return $msg;
	}
}

if ( ! function_exists( 'newsai_weekly_report_send_html_mail' ) ) {
	/**
	 * Send HTML report via wp_mail with safe From + UTF-8 + error capture.
	 *
	 * @param string $to      Recipient.
	 * @param string $subject Subject line.
	 * @param string $html    HTML body.
	 * @return bool
	 */
	function newsai_weekly_report_send_html_mail( $to, $subject, $html ) {
		global $newsai_weekly_report_last_mail_error;
		$newsai_weekly_report_last_mail_error = '';

		$to = sanitize_email( $to );
		if ( $to === '' || ! is_email( $to ) ) {
			$newsai_weekly_report_last_mail_error = 'invalid_recipient';
			return false;
		}

		$admin_email = sanitize_email( (string) get_option( 'admin_email' ) );
		if ( $admin_email === '' || ! is_email( $admin_email ) ) {
			$newsai_weekly_report_last_mail_error = 'invalid_admin_email';
			return false;
		}

		$from_name = wp_specialchars_decode( (string) get_bloginfo( 'name' ), ENT_QUOTES );
		if ( $from_name === '' ) {
			$from_name = 'Newsroom OS';
		}

		$from_cb = static function () use ( $admin_email ) {
			return $admin_email;
		};
		$name_cb = static function () use ( $from_name ) {
			return $from_name;
		};
		$type_cb = static function () {
			return 'text/html';
		};
		$fail_cb = static function ( $wp_error ) {
			global $newsai_weekly_report_last_mail_error;
			if ( is_wp_error( $wp_error ) ) {
				$newsai_weekly_report_last_mail_error = $wp_error->get_error_message();
			}
		};
		$mailer_cb = static function ( $phpmailer ) use ( $html ) {
			$phpmailer->isHTML( true );
			$phpmailer->CharSet = 'UTF-8';
			$phpmailer->Encoding = 'base64';
			$phpmailer->AltBody = wp_trim_words( wp_strip_all_tags( $html ), 120, '…' );
		};

		add_filter( 'wp_mail_from', $from_cb, 999 );
		add_filter( 'wp_mail_from_name', $name_cb, 999 );
		add_filter( 'wp_mail_content_type', $type_cb, 999 );
		add_action( 'wp_mail_failed', $fail_cb, 10, 1 );
		add_action( 'phpmailer_init', $mailer_cb, 10, 1 );

		$sent = wp_mail( $to, $subject, $html );

		remove_filter( 'wp_mail_from', $from_cb, 999 );
		remove_filter( 'wp_mail_from_name', $name_cb, 999 );
		remove_filter( 'wp_mail_content_type', $type_cb, 999 );
		remove_action( 'wp_mail_failed', $fail_cb, 10 );
		remove_action( 'phpmailer_init', $mailer_cb, 10 );

		if ( ! $sent && $newsai_weekly_report_last_mail_error === '' ) {
			$newsai_weekly_report_last_mail_error = 'wp_mail returned false';
		}
		return (bool) $sent;
	}
}

if ( ! function_exists( 'newsai_weekly_report_send' ) ) {
	/**
	 * @param bool $force Skip same-week dedupe (test sends).
	 * @return array{ok:bool,sent:int,message:string,detail?:string}
	 */
	function newsai_weekly_report_send( $force = false ) {
		if ( ! $force && ! newsai_weekly_report_enabled() ) {
			return [
				'ok'      => false,
				'sent'    => 0,
				'message' => 'disabled',
			];
		}
		$recipients = newsai_weekly_report_recipients();
		if ( $recipients === [] ) {
			return [
				'ok'      => false,
				'sent'    => 0,
				'message' => 'no_recipients',
			];
		}
		$week_key = gmdate( 'o-\WW' );
		if ( ! $force ) {
			$last = (string) get_option( 'newsai_weekly_report_last_week', '' );
			if ( $last === $week_key ) {
				return [
					'ok'      => true,
					'sent'    => 0,
					'message' => 'already_sent',
				];
			}
		}
		$data    = newsai_weekly_report_collect();
		$html    = newsai_weekly_report_build_html( $data );
		$subject = sprintf(
			/* translators: 1: site name, 2: week label */
			__( '[%1$s] Weekly newsroom report — %2$s', 'newsroom-ai-assistant' ),
			$data['site_name'],
			$data['period_label']
		);
		if ( $force ) {
			$subject = sprintf(
				/* translators: %s: original subject */
				__( '[TEST] %s', 'newsroom-ai-assistant' ),
				$subject
			);
		}

		$sent   = 0;
		$detail = '';
		foreach ( $recipients as $email ) {
			if ( newsai_weekly_report_send_html_mail( $email, $subject, $html ) ) {
				$sent++;
				continue;
			}
			global $newsai_weekly_report_last_mail_error;
			if ( ! empty( $newsai_weekly_report_last_mail_error ) ) {
				$detail = (string) $newsai_weekly_report_last_mail_error;
			}
		}
		if ( $sent > 0 && ! $force ) {
			update_option( 'newsai_weekly_report_last_week', $week_key, false );
		}
		if ( $sent > 0 || $force ) {
			update_option( 'newsai_weekly_report_last_sent', time(), false );
			update_option( 'newsai_weekly_report_last_count', $sent, false );
		}

		$code = $sent > 0 ? 'sent' : ( $detail === 'invalid_admin_email' ? 'invalid_admin_email' : 'mail_failed' );

		return [
			'ok'      => $sent > 0,
			'sent'    => $sent,
			'message' => $code,
			'detail'  => $detail,
		];
	}
}

if ( ! function_exists( 'newsai_weekly_report_cron_send' ) ) {
	function newsai_weekly_report_cron_send() {
		newsai_weekly_report_send( false );
	}
}
add_action( 'newsai_weekly_cleanup', 'newsai_weekly_report_cron_send', 20 );

if ( ! function_exists( 'newsai_weekly_report_ajax_test' ) ) {
	function newsai_weekly_report_ajax_test() {
		check_ajax_referer( 'newsai_ajax_nonce', 'nonce' );
		if ( ! current_user_can( 'manage_options' ) ) {
			wp_send_json_error( [ 'message' => 'unauthorized' ], 403 );
		}
		// Allow testing unsaved recipient textarea (same request as Save).
		if ( isset( $_POST['recipients'] ) ) {
			$raw = sanitize_textarea_field( wp_unslash( (string) $_POST['recipients'] ) );
			update_option( 'newsai_weekly_report_recipients', $raw, false );
		}
		if ( isset( $_POST['weekly_report_enabled'] ) && (string) wp_unslash( $_POST['weekly_report_enabled'] ) === 'yes' ) {
			update_option( 'newsai_weekly_report_enabled', 'yes', false );
		}
		$result = newsai_weekly_report_send( true );
		if ( empty( $result['ok'] ) ) {
			$detail = isset( $result['detail'] ) ? (string) $result['detail'] : '';
			$result['message_human'] = newsai_weekly_report_mail_error_message( (string) ( $result['message'] ?? 'mail_failed' ), $detail );
			wp_send_json_error( $result, 400 );
		}
		$result['message_human'] = sprintf(
			/* translators: %d: number of emails sent */
			__( 'Test report sent to %d recipient(s). Check spam if you do not see it within a few minutes.', 'newsroom-ai-assistant' ),
			(int) ( $result['sent'] ?? 0 )
		);
		wp_send_json_success( $result );
	}
}
add_action( 'wp_ajax_newsai_weekly_report_test', 'newsai_weekly_report_ajax_test' );
