<?php
namespace DM\ApiBundle\Utils\ExternalApi\SmsTideSoftware;
use DM\ApiBundle\Utils\ExternalApi\ExternalApi;
use Symfony\Component\DependencyInjection\Container;
use SimpleXMLElement;
use DM\DashboardBundle\Utils\RandomCodeGenerator;
class SmsTideSoftwareApiAdapter extends ExternalApi {
/**
* max number of attempts
*/
CONST MAX_NUMBER_OF_ATTEMPTS = 30;
/**
* delay check staus in seconds
*/
CONST DELAY_CHECK_STATUS_IN_SECONDS = 1;
/**
* @var Container
*/
private $container;
/**
* @param Container $container
*/
public function __construct(Container $container) {
$this->normalizeInfo = '';
$this->container = $container;
$this->autorization();
parent::__construct();
}
/**
* autorization
*/
private function autorization(): void {
$host = $this->container->hasParameter('api_smsTideSoftwareConfronter_host') ? $this->container->getParameter('api_smsTideSoftwareConfronter_host') : '';
$login = $this->container->hasParameter('api_smsTideSoftwareConfronter_login') ? $this->container->getParameter('api_smsTideSoftwareConfronter_login') : '';
$pass = $this->container->hasParameter('api_smsTideSoftwareConfronter_pass') ? $this->container->getParameter('api_smsTideSoftwareConfronter_pass') : '';
$key = $this->container->hasParameter('api_smsTideSoftwareConfronter_key') ? $this->container->getParameter('api_smsTideSoftwareConfronter_key') : '';
$affiliateId = $this->container->hasParameter('api_smsTideSoftwareConfronter_affiliate_id') ? $this->container->getParameter('api_smsTideSoftwareConfronter_affiliate_id') : '';
$this->setConnectionParameters($host, $login, $pass, $key, $affiliateId);
}
/**
* call method
*
* @param type $method
* @param type $parameters
* @return array
*
* @throws \Exception
*/
public function call($method, $parameters = []): array {
}
/**
* set normalize info
*
* @param array $resposne
*
* @return void
*/
public function setNormalizeInfo($resposne): void {
$arrayResult = json_decode(json_encode((array) $resposne), TRUE);
if (isset($arrayResult['success'])) {
$this->normalizeInfo .= $arrayResult['success'];
}
if (isset($arrayResult['error'])) {
$this->normalizeInfo .= $arrayResult['error'];
}
}
/**
* set normalize status
*
* @param type $resposne
*
* @return void
*/
public function setNormalizeStatus($resposne): void {
$arrayResult = json_decode(json_encode((array) $resposne), TRUE);
if (isset($arrayResult['success']) || isset($arrayResult['TideEnvelopeHeader']['TideCustomersID'])) {
$this->normalizeStatus = self::STATUS_SUCCESS;
}
if (isset($arrayResult['error'])) {
$this->normalizeStatus = self::STATUS_ERROR;
}
}
/**
* get sms report by external id or sms id
*
* @param int|null $externalID
* @param int|null $smsId
*
* @return array
*/
public function getSmsReportByExternalIdOrSmsId(?int $externalID = null, ?int $smsId = null): array {
$host = 'https://tideplatformgate.com/tidexmlreceiver/TideGate.asmx?WSDL';
$content = '<?xml version="1.0" encoding="utf-8"?>
<TideEnvelope:Envelope xmlns:Tide="http://www.tideplatformgate.com/TideProtocol.xsd" xmlns:TideEnvelope="http://www.w3.org/2003/05/soap-envelope">
<TideEnvelope:Header>
<Tide:CustomersID value="' . $this->login . '" />
<Tide:UsersID value="' . $this->key . '" />
<Tide:Password value="' . $this->pass . '" />
<Tide:Generate Date="2019-11-26" Time="15:40:55.160" />
<Tide:Receipt Date="2019-11-26" Time="15:40:55.160" />
</TideEnvelope:Header>
<TideEnvelope:Body>
<Tide:Process id="1" actualnode="1">
<Tide:Node id="1" NodesID="23">
<Tide:Datagroup id="1" />
<Tide:Parameters>
<Tide:Parameter id="1" name="SMSStatusesDataGroup" value="1" />
</Tide:Parameters>
</Tide:Node>
</Tide:Process>
<Tide:Data>
<Tide:Group id="1">
<Tide:Items>';
if ($externalID) {
$content .= '<Tide:Item id="1" name="ExternalID">' . $externalID . '</Tide:Item>';
}
if ($smsId) {
$content .= '<Tide:Item id="1" name="SMSID">' . $smsId . '</Tide:Item>';
}
$content .= '</Tide:Items>
</Tide:Group>
</Tide:Data>
</TideEnvelope:Body>
</TideEnvelope:Envelope>';
try {
$resultXml = $this->callSoap($host, $content);
$body = $resultXml->xpath('//TideEnvelopeEnvelope/TideEnvelopeBody/TideData/TideGroup/TideItems/TideItem/TideAttributes/TideAttribute');
$arrayResult = json_decode(json_encode((array) $body), TRUE);
return $arrayResult;
} catch (\Exception $ex) {
$this->normalizeStatus = self::STATUS_ERROR;
$this->normalizeInfo .= 'error: ' . $ex->getMessage() . ' line: ' . $ex->getLine();
return [];
}
}
/**
* sendSms
*
* @param string $phoneNumber
* @param string $senderName
* @param string $content
*
* @return void
*/
public function sendSms(string $phoneNumber, string $senderName, string $content): void {
$host = $this->affiliateId; //first free parametr from abstract !!! - because we have two hosts for this provider
$randomNumber = time() . RandomCodeGenerator::generate(5);
$content = '<?xml version="1.0" encoding="utf-8" ?>
<TideEnvelope:Envelope xmlns:Tide="http://www.tideplatformgate.com/TideProtocol.xsd" xmlns:TideEnvelope="http://www.w3.org/2003/05/soap-envelope">
<TideEnvelope:Header>
<Tide:CustomersID value="' . $this->login . '" />
<Tide:UsersID value="' . $this->key . '" />
<Tide:Password value="' . $this->pass . '" />
</TideEnvelope:Header>
<TideEnvelope:Body>
<Tide:Process id="1" actualnode="1">
<Tide:Node id="1" NodesID="23">
<Tide:Datagroup id="1" />
<Tide:Parameters>
<Tide:Parameter id="1" name="PhoneNumberAttributeClassID" value="1" />
<Tide:Parameter id="2" name="AuthorizationAttributeClassID" value="2" />
<Tide:Parameter id="3" name="ExternalIDAttributeClassID" value="3" />
<Tide:Parameter id="4" name="SuspensionAttributeClassID" value="4" />
<Tide:Parameter id="5" name="BrandingAttributeClassID" value="5" />
<Tide:Parameter id="6" name="PriorityAttributeClassID" value="6" />
<Tide:Parameter id="7" name="FlashAttributeClassID" value="7" />
<Tide:Parameter id="8" name="WAPAttributeClassID" value="8" />
<Tide:Parameter id="9" name="VoiceAttributeClassID" value="9" />
<Tide:Parameter id="10" name="TTSVoicesIDAttributeClassID" value="10" />
<Tide:Parameter id="11" name="SendDateTimeAttributeClassID" value="11" />
</Tide:Parameters>
</Tide:Node>
</Tide:Process>
<Tide:Data>
<Tide:Group id="1">
<Tide:Items>
<Tide:Item id="1" name="SMSMessage">' . $content . '</Tide:Item>
<Tide:Item id="2" name="SMSAttributes">
<Tide:Attributes save="1">
<Tide:Attribute ExternalID="1" value="' . $phoneNumber . '" />
<Tide:Attribute ExternalID="2" value="0" />
<Tide:Attribute ExternalID="3" value="' . $randomNumber . '" />
<Tide:Attribute ExternalID="5" value="' . $senderName . '"/>
<Tide:Attribute ExternalID="6" value="0" />
<Tide:Attribute ExternalID="7" value="0" />
<Tide:Attribute ExternalID="8" value="0" />
<Tide:Attribute ExternalID="9" value="0" />
</Tide:Attributes>
</Tide:Item>
</Tide:Items>
</Tide:Group>
</Tide:Data>
</TideEnvelope:Body>
</TideEnvelope:Envelope>';
$this->callSoap($host, $content);
if ($this->normalizeStatus === self::STATUS_SUCCESS) {
for ($i = 0; $i < self::MAX_NUMBER_OF_ATTEMPTS; $i++) {
$smsData = $this->getSmsReportByExternalIdOrSmsId($randomNumber);
if ($this->checkSmsStatus($smsData)) {
$this->normalizeStatus = self::STATUS_SUCCESS;
return;
}
sleep(self::DELAY_CHECK_STATUS_IN_SECONDS);
}
}
$this->normalizeStatus = self::STATUS_ERROR;
$this->normalizeInfo .= ' message could be not send';
}
/**
* get report by year month and day
*
* @param int $year
* @param int $month
* @param int|null $day
*
* @return SimpleXMLElement
*/
public function getReportByYearMonthAndDay(int $year, int $month, ?int $day = null): SimpleXMLElement {
$content = '<?xml version="1.0" encoding="utf-8"?>
<TideEnvelope:Envelope xmlns:Tide="http://www.tideplatformgate.com/TideProtocol.xsd" xmlns:TideEnvelope="http://www.w3.org/2003/05/soap-envelope">
<TideEnvelope:Header>
<Tide:CustomersID value="' . $this->login . '" />
<Tide:UsersID value="' . $this->key . '" />
<Tide:Password value="' . $this->pass . '" />
<Tide:Generate Date="2009-11-26" Time="01:40:55.160" />
<Tide:Receipt Date="2009-11-26" Time="01:40:55.160" />
</TideEnvelope:Header>
<TideEnvelope:Body>
<Tide:Process id="1" actualnode="1">
<Tide:Node id="1" NodesID="29">
<Tide:Parameters>
<Tide:Parameter id="2" name="Year" value="' . $year . '" />
<Tide:Parameter id="3" name="Month" value="' . $month . '" />';
if ($day) {
$content .= '<Tide:Parameter id="4" name="Day" value="' . $day . '" />';
}
$content .= '</Tide:Parameters>
</Tide:Node>
</Tide:Process>
</TideEnvelope:Body>
</TideEnvelope:Envelope>';
return $this->callSoap($this->host, $content);
}
/**
* check sms send status
*
* @param array $result
*
* @return bool
*/
public function checkSmsStatus(array $result): bool {
if (
(isset($result[4]['@attributes']['name']) && $result[4]['@attributes']['name'] === 'DeliveryStatus') &&
(isset($result[4]['@attributes']['value']) && $result[4]['@attributes']['value'] === '2')
) {
return true;
}
return false;
}
/**
* connect to web service
*
* @param string $host
* @param string $content - xml
*
* @return SimpleXMLElement
*/
public function callSoap(string $host, string $content): SimpleXMLElement {
$optionsConnect = [
'exceptions' => true,
'trace' => 1,
'cache_wsdl' => WSDL_CACHE_NONE,
'connection_timeout' => 60, // in seconds
'keep_alive' => false,
];
try {
$client = new \SoapClient($host, $optionsConnect);
$contentXml = new SimpleXMLElement($content);
$params = new \stdClass();
$params->xml = $contentXml->asXML();
$result = $client->PostXML($params);
$response = preg_replace("/(<\/?)(\w+):([^>]*>)/", "$1$2$3", $result->PostXMLResult);
if ($result->PostXMLResult === 'Authentication error') {
throw new \Exception('Authentication error');
}
if (mb_strpos($result->PostXMLResult, 'OK ', null, 'utf-8') !== FALSE) {
$response = '<?xml version="1.0" encoding="utf-8"?>
<result>
<success>' . $response . '</success>
</result>';
}
$result = new SimpleXMLElement($response);
$this->setNormalizeInfo($result);
$this->setNormalizeStatus($result);
return $result;
} catch (\Exception $ex) {
$result = new SimpleXMLElement('<?xml version="1.0" encoding="utf-8"?>
<result>
<error>' . $ex->getMessage() . ' line: ' . $ex->getLine() . '</error>
</result>');
$this->setNormalizeInfo($result);
$this->setNormalizeStatus($result);
return $result;
}
}
}