<?php
namespace ConnectionApiSageBundle\Service;
use Symfony\Component\HttpFoundation\Session\SessionInterface;
/**
* Class APIAuthenticationService
* @package ConnectionApiSageBundle\Service
* @author Carlos Gutierrez <carlos.gutierrez@indabasolutions.com>
*
* Handle authentication with Sage API
*/
class APIAuthenticationService
{
private $grantType;
private $clientId;
private $clientSecret;
private $authUrl;
private $tokenUrl;
private $scope;
private $credentials;
private $baseUrl;
private $resourceId;
private static $instances = [];
private $session;
public function __construct(
string $grantType,
string $clientId,
string $clientSecret,
string $authUrl,
string $tokenUrl,
string $scope,
string $baseUrl,
string $resourceId,
SessionInterface $session
)
{
$this->grantType = $grantType;
$this->clientId = $clientId;
$this->clientSecret = $clientSecret;
$this->authUrl = $authUrl;
$this->tokenUrl = $tokenUrl;
$this->scope = $scope;
$this->baseUrl = $baseUrl;
$this->resourceId = $resourceId;
$this->url = $this->baseUrl . DIRECTORY_SEPARATOR . $this->resourceId . DIRECTORY_SEPARATOR;
$this->session = $session;
}
/**
* __clone
*
* @return void
*/
protected function __clone() { }
/**
* __wakeup
*
*/
public function __wakeup()
{
throw new \Exception("Cannot unserialize a singleton.");
}
/**
* getInstance Singleton
*
* @return Singleton
*/
public static function getInstance(): Singleton
{
$cls = static::class;
if (!isset(self::$instances[$cls])) {
self::$instances[$cls] = new static();
}
return self::$instances[$cls];
}
/**
* method Authentication
*
* @return array
*/
public function authentication(): array
{
try {
$params = [
'grant_type' => $this->grantType,
'client_id' => $this->clientId,
'client_secret' => $this->clientSecret,
'auth_url' => $this->authUrl,
'scope' => $this->scope
];
// Request the credentials from the api
$response = $this->curlExec($params);
// Decode json and return
$this->credentials = json_decode($response, true);
// set session
$this->session->set('_token', $this->credentials);
$this->session->set('expire_token', new \DateTime("now"));
// return array
return $this->credentials;
} catch (\Throwable $th) {
$this->session->set('_token', ['access_token' => '']);
$this->session->set('expire_token', (new \DateTime("now"))->modify('-1 day'));
return [];
}
}
/**
* isAuthentication
*
* @return boolean
*/
public function isAuthentication()
{
if($this->session->get('_token') && $this->session->get('_token') !=='' ) {
return true;
}
return false;
}
/**
* getToken
*
* @return string
*/
public function getToken(): string
{
if(!$this->isAuthentication()) {
$this->authentication();
}
$this->getExpireToken();
return $this->session->get('_token')['access_token'];
}
/**
* curlExec
*
* @param [type] $params
* @return string
*/
protected function curlExec($params): string
{
// Init curl
$curlInstance = curl_init();
// Set curl options
curl_setopt($curlInstance, CURLOPT_RETURNTRANSFER, 1);
curl_setopt($curlInstance, CURLOPT_URL, $this->tokenUrl);
curl_setopt($curlInstance, CURLOPT_POST, true);
curl_setopt($curlInstance, CURLOPT_POSTFIELDS, $params);
curl_setopt($curlInstance, CURLOPT_SSL_VERIFYPEER, false);
// Execute curl
$response = curl_exec($curlInstance);
// Close connection
curl_close($curlInstance);
return $response;
}
/**
* getExpireToken
*
* @return void
*/
public function getExpireToken()
{
try {
$now = new \DateTime("now");
$diff = $now->diff($this->session->get('expire_token'));
if($diff->d == 1) {
$this->authentication();
}
} catch (\Throwable $th) {
$this->authentication();
}
}
/**
* getBACCseUrl
*
* @return string
*/
public function getBaseUrl(): string
{
return $this->url;
}
}