<?php
/**
 * SendLayer email API provider.
 *
 * @package EmailSmtp
 * @link https://sendlayer.com/docs/getting-started-with-the-sendlayer-api/
 * @link https://developers.sendlayer.com/quickstart/introduction
 * @link https://developers.sendlayer.com/api-reference/endpoint/email
 */

namespace EmailSmtp\Providers\Sendlayer;

use EmailSmtp\Includes\AbstractApiProvider;
use EmailSmtp\Includes\ApiHttpClient;
use EmailSmtp\Includes\DeliveryResult;
use EmailSmtp\Includes\EmailMessage;

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

final class Provider extends AbstractApiProvider {

	public function get_id(): string {
		return 'sendlayer';
	}

	public function get_name(): string {
		return __( 'SendLayer', 'wp-powersuite' );
	}

	public function get_description(): string {
		return __( 'Send transactional email through the SendLayer REST API.', 'wp-powersuite' );
	}

	public function get_docs_url(): string {
		return 'https://developers.sendlayer.com/guides/send-email';
	}

	public function get_icon(): string {
		return 'dashicons-email-alt';
	}

	public function get_required_fields(): array {
		return [ 'sendlayer_api_key' ];
	}


	public function connect( array $settings ): DeliveryResult {
		$key = $this->secret( $settings, 'sendlayer_api_key', 'WP_POWERSUITE_SENDLAYER_API_KEY' );
		if ( $key === '' ) {
			return DeliveryResult::failure( __( 'SendLayer API key is required.', 'wp-powersuite' ), '', 'authentication' );
		}

		// GET /events validates the Bearer key without sending mail.
		$response = ApiHttpClient::request(
			'GET',
			'https://console.sendlayer.com/api/v1/events?RetrieveCount=1',
			[ 'Authorization' => 'Bearer ' . $key ]
		);

		return ApiHttpClient::to_delivery_result(
			$response,
			static function () {
				return [ 'message' => __( 'SendLayer API key authenticated successfully.', 'wp-powersuite' ) ];
			}
		);
	}

	public function send( EmailMessage $message, array $settings ): DeliveryResult {
		$missing = $this->require_from( $message );
		if ( $missing ) {
			return $missing;
		}

		$key = $this->secret( $settings, 'sendlayer_api_key', 'WP_POWERSUITE_SENDLAYER_API_KEY' );
		if ( $key === '' ) {
			return DeliveryResult::failure( __( 'SendLayer API key is required.', 'wp-powersuite' ), '', 'authentication' );
		}

		$from    = $this->from_parts( $message );
		$payload = [
			'From'    => $this->address_object( $from['email'], $from['name'] ),
			'To'      => array_map( [ $this, 'address_object' ], $message->get_to() ),
			'Subject' => $message->get_subject(),
		];

		if ( $message->is_html() ) {
			$payload['ContentType']  = 'HTML';
			$payload['HTMLContent']  = $message->get_body();
			$payload['PlainContent'] = $message->get_alt_body() !== ''
				? $message->get_alt_body()
				: wp_strip_all_tags( $message->get_body() );
		} else {
			$payload['ContentType']  = 'Text';
			$payload['PlainContent'] = $message->get_body();
		}

		if ( $message->get_cc() !== [] ) {
			$payload['CC'] = array_map( [ $this, 'address_object' ], array_slice( $message->get_cc(), 0, 10 ) );
		}
		if ( $message->get_bcc() !== [] ) {
			$payload['BCC'] = array_map( [ $this, 'address_object' ], array_slice( $message->get_bcc(), 0, 5 ) );
		}
		if ( is_email( $message->get_reply_to_email() ) ) {
			$payload['ReplyTo'] = [
				$this->address_object( $message->get_reply_to_email(), $message->get_reply_to_name() ),
			];
		}

		$attachments = $this->attachments_as_base64( $message );
		if ( $attachments !== [] ) {
			$payload['Attachments'] = array_map(
				static function ( array $a ) {
					$row = [
						'Filename'    => $a['name'],
						'Content'     => $a['content'],
						'Type'        => $a['type'] !== '' ? $a['type'] : 'application/octet-stream',
						'Disposition' => 'attachment',
					];
					return $row;
				},
				$attachments
			);
		}

		$headers = $this->safe_custom_headers( $message );
		if ( $headers !== [] ) {
			$payload['Headers'] = $headers;
		}

		$response = ApiHttpClient::request(
			'POST',
			'https://console.sendlayer.com/api/v1/email',
			[ 'Authorization' => 'Bearer ' . $key ],
			$payload
		);

		return ApiHttpClient::to_delivery_result(
			$response,
			static function ( array $res ) {
				$id = '';
				if ( is_array( $res['json'] ) ) {
					$id = (string) ( $res['json']['MessageID'] ?? $res['json']['messageId'] ?? '' );
				}
				return [
					'message' => __( 'SendLayer accepted the message.', 'wp-powersuite' ),
					'id'      => $id,
				];
			}
		);
	}

	/**
	 * Address object per SendLayer docs: { "email": "...", "name": "..." }.
	 *
	 * @return array{email:string, name?:string}
	 */
	private function address_object( string $email, string $name = '' ): array {
		$row  = [ 'email' => sanitize_email( $email ) ];
		$name = sanitize_text_field( $name );
		if ( $name !== '' ) {
			$row['name'] = $name;
		}
		return $row;
	}
}
