<?php
namespace SabaiApps\Directories\Component\Notification\Sender;

use SabaiApps\Directories\Exception\RuntimeException;

class WordPressSmsSender extends AbstractSender {

	protected function _notificationSenderInfo() {
		return array(
			'label'                 => __( 'SMS', 'directories-pro' ),
			'default_settings'      => array(
				'recipients' => array(
					'event'   => null,
					'number'  => null,
					'numbers' => null,
				),
				'body'       => null,
			),
			'event_recipient_types' => array( 'phone' ),
		);
	}

	public function notificationSenderSettingsForm( array $settings, array $messageMeta, array $parents = array() ) {
		$has_user_directory = $this->_application->getComponent( 'User' )->userDirectoryExists();
		return array(
			'recipients' => array(
				'#title'  => __( 'SMS recipients', 'directories-pro' ),
				'number'  => array(
					'#type'          => $has_user_directory ? 'checkbox' : 'hidden',
					'#title'         => __( 'Enter SMS numbers', 'directories-pro' ),
					'#default_value' => ! $has_user_directory || ! empty( $settings['recipients']['number'] ),
					'#weight'        => 5,
					'#switch'        => false,
					'#class'         => DRTS_BS_PREFIX . 'mb-2',
				),
				'numbers' => array(
					'#type'          => 'textfield',
					'#separator'     => ',',
					'#default_value' => $settings['recipients']['numbers'],
					'#weight'        => 6,
					'#class'         => DRTS_BS_PREFIX . 'ms-4',
					'#states'        => array(
						'visible' => array(
							sprintf( '[name="%s[number][]"]', $this->_application->Form_Form_fieldName( array_merge( $parents, array( 'recipients' ) ) ) ) => array(
								'type'  => 'checked',
								'value' => true,
							),
						),
					),
					empty( $settings['recipients']['numbers'] ) ? '#placeholder' : '#description' => __( 'Enter SMS numbers separated with commas.', 'directories-pro' ),
				),
			),
			'body'       => array(
				'#type'                  => 'textarea',
				'#title'                 => __( 'SMS message', 'directories-pro' ),
				'#description'           => $this->_application->System_Util_availableTags( $messageMeta['tags'] ),
				'#description_no_escape' => true,
				'#default_value'         => $settings['body'],
				'#required'              => true,
				'#rows'                  => 10,
			),
		);
	}

	public function notificationSenderSend( array $settings, iterable $messages ) {
		$body = $settings['body'];
		foreach ( $messages as $message ) {
			$body         = $this->_replaceMessageTags( isset( $message['body'] ) ? $message['body'] : $body, $message );
			$numbers_sent = array();
			if ( ! empty( $settings['recipients']['number'] ) ) {
				foreach ( (array) $settings['recipients']['numbers'] as $number ) {
					if ( ! isset( $numbers_sent[ $number ] ) ) {
						$this->_sendSms( $number, $body );
						$numbers_sent[ $number ] = 1;
					}
				}
			}
			if ( ! empty( $settings['recipients']['event'] ) ) {
				foreach ( $settings['recipients']['event'] as $event_recipient ) {
					if ( ! $_recipient = $this->_getEventRecipientByMessage( $event_recipient, $message ) ) {
						continue;
					}

					if ( $_recipient['type'] !== 'phone' ) {
						continue;
					}

					$number = $_recipient['value'];
					if ( ! isset( $numbers_sent[ $number ] ) ) {
						$this->_sendSms( $number, $body );
						$numbers_sent[ $number ] = 1;
					}
				}
			}
		}
	}

	protected function _sendSms( $to, $message ) {
		if ( function_exists( 'twl_send_sms' ) ) {
			$result = twl_send_sms(
				array(
					'number_to' => $to,
					'message'   => $message,
				)
			);
		} elseif ( function_exists( 'wp_sms_send' ) ) {
			$result = wp_sms_send( $to, $message );
		} else {
			throw new RuntimeException( sprintf( 'SMS could not be sent to %s. No SMS function found.', $to ) );
		}
		if ( is_wp_error( $result ) ) {
			throw new RuntimeException( $result->get_error_message() );
		} elseif ( ! $result ) {
			throw new RuntimeException( sprintf( 'SMS could not be sent to %s.', $to ) );
		}
	}

	protected function _getRecipientByEntityField( $entity, $fieldName ) {
		if ( ( $field = $this->_application->Entity_Field( $entity, $fieldName ) )
			&& $field->getFieldType() === 'phone'
		) {
			$this->_application->Entity_Field_load( $entity );
			if ( $field_phone = $entity->getSingleFieldValue( $fieldName ) ) {
				return array(
					'type'  => 'phone',
					'value' => $field_phone,
				);
			}
		}
	}
}
