2021-10-18 18:24:38 +09:00
|
|
|
<?php
|
|
|
|
|
|
2021-10-21 09:55:32 +09:00
|
|
|
namespace gullevek\AmazonIncentives\AWS;
|
2021-10-18 18:24:38 +09:00
|
|
|
|
2021-10-21 09:55:32 +09:00
|
|
|
use gullevek\AmazonIncentives\Client\Client;
|
|
|
|
|
use gullevek\AmazonIncentives\Config\Config;
|
|
|
|
|
use gullevek\AmazonIncentives\Exceptions\AmazonErrors;
|
|
|
|
|
use gullevek\AmazonIncentives\Debug\AmazonDebug;
|
|
|
|
|
use gullevek\AmazonIncentives\Response\CancelResponse;
|
|
|
|
|
use gullevek\AmazonIncentives\Response\CreateBalanceResponse;
|
|
|
|
|
use gullevek\AmazonIncentives\Response\CreateResponse;
|
2021-10-18 18:24:38 +09:00
|
|
|
|
|
|
|
|
class AWS
|
|
|
|
|
{
|
2022-06-10 14:37:07 +09:00
|
|
|
/** @var string What AWS Service to use: Gift Card on Demand (GCOD) */
|
2021-10-18 18:24:38 +09:00
|
|
|
public const SERVICE_NAME = 'AGCODService';
|
2022-06-10 14:37:07 +09:00
|
|
|
/** @var string */
|
2021-10-18 18:24:38 +09:00
|
|
|
public const ACCEPT_HEADER = 'accept';
|
2022-06-10 14:37:07 +09:00
|
|
|
/** @var string content-type */
|
2021-10-18 18:24:38 +09:00
|
|
|
public const CONTENT_HEADER = 'content-type';
|
2022-06-10 14:37:07 +09:00
|
|
|
/** @var string */
|
2021-10-18 18:24:38 +09:00
|
|
|
public const HOST_HEADER = 'host';
|
2022-06-10 14:37:07 +09:00
|
|
|
/** @var string */
|
2021-10-18 18:24:38 +09:00
|
|
|
public const X_AMZ_DATE_HEADER = 'x-amz-date';
|
2022-06-10 14:37:07 +09:00
|
|
|
/** @var string */
|
2021-10-18 18:24:38 +09:00
|
|
|
public const X_AMZ_TARGET_HEADER = 'x-amz-target';
|
2022-06-10 14:37:07 +09:00
|
|
|
/** @var string */
|
2021-10-18 18:24:38 +09:00
|
|
|
public const AUTHORIZATION_HEADER = 'Authorization';
|
2022-06-10 14:37:07 +09:00
|
|
|
/** @var string type of encryption type */
|
2021-10-18 18:24:38 +09:00
|
|
|
public const AWS_SHA256_ALGORITHM = 'AWS4-HMAC-SHA256';
|
2022-06-10 14:37:07 +09:00
|
|
|
/** @var string key type to use */
|
2021-10-18 18:24:38 +09:00
|
|
|
public const KEY_QUALIFIER = 'AWS4';
|
2022-06-10 14:37:07 +09:00
|
|
|
/** @var string */
|
2021-10-18 18:24:38 +09:00
|
|
|
public const TERMINATION_STRING = 'aws4_request';
|
2022-06-10 14:37:07 +09:00
|
|
|
/** @var string Service to use: Create Gift Card */
|
2021-10-18 18:24:38 +09:00
|
|
|
public const CREATE_GIFT_CARD_SERVICE = 'CreateGiftCard';
|
2022-06-10 14:37:07 +09:00
|
|
|
/** @var string Service to use: Cancle Gift Card */
|
2021-10-18 18:24:38 +09:00
|
|
|
public const CANCEL_GIFT_CARD_SERVICE = 'CancelGiftCard';
|
2022-06-10 14:37:07 +09:00
|
|
|
/** @var string Service to use: Get Available Funds */
|
2021-10-18 18:24:38 +09:00
|
|
|
public const GET_AVAILABLE_FUNDS_SERVICE = 'GetAvailableFunds';
|
|
|
|
|
|
2022-06-10 14:37:07 +09:00
|
|
|
/** @var Config Configuration class with all settings */
|
2021-10-18 18:24:38 +09:00
|
|
|
private $config;
|
|
|
|
|
|
|
|
|
|
/**
|
2022-06-10 14:37:07 +09:00
|
|
|
* Initialize the main AWS class. This class prepares and sends all the actions
|
|
|
|
|
* and returns reponses as defined in in the CreateResponse class
|
|
|
|
|
*
|
2021-10-18 18:24:38 +09:00
|
|
|
* @param Config $config
|
|
|
|
|
*/
|
|
|
|
|
public function __construct(Config $config)
|
|
|
|
|
{
|
|
|
|
|
$this->config = $config;
|
|
|
|
|
AmazonDebug::writeLog([__METHOD__ => date('Y-m-d H:m:s.u')]);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
2022-06-10 14:37:07 +09:00
|
|
|
* Bug a gift card
|
|
|
|
|
*
|
|
|
|
|
* @param float $amount Amount to buy a gifr card in set currencty
|
|
|
|
|
* @param string|null $creation_id Override creation id, if not set will
|
|
|
|
|
* be created automatically. If not valid error
|
|
|
|
|
* will be thrown
|
|
|
|
|
* @return CreateResponse Object with AWS response data
|
2021-10-18 18:24:38 +09:00
|
|
|
*
|
|
|
|
|
* @throws AmazonErrors
|
|
|
|
|
*/
|
|
|
|
|
public function getCode(float $amount, ?string $creation_id = null): CreateResponse
|
|
|
|
|
{
|
|
|
|
|
$service_operation = self::CREATE_GIFT_CARD_SERVICE;
|
|
|
|
|
$payload = $this->getGiftCardPayload($amount, $creation_id);
|
|
|
|
|
$canonical_request = $this->getCanonicalRequest($service_operation, $payload);
|
|
|
|
|
$date_time_string = $this->getTimestamp();
|
|
|
|
|
AmazonDebug::writeLog(['call' => __METHOD__]);
|
|
|
|
|
$result = json_decode($this->makeRequest(
|
|
|
|
|
$payload,
|
|
|
|
|
$canonical_request,
|
|
|
|
|
$service_operation,
|
|
|
|
|
$date_time_string
|
|
|
|
|
), true);
|
|
|
|
|
return new CreateResponse($result);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
2022-06-10 14:37:07 +09:00
|
|
|
* Cancle an ordered gift card, only possible within the the time limit
|
|
|
|
|
*
|
|
|
|
|
* @param string $creation_request_id Previously created creation request id
|
|
|
|
|
* @param string $gift_card_id Previously created gift card id
|
|
|
|
|
* @return CancelResponse Object with AWS response data
|
2021-10-18 18:24:38 +09:00
|
|
|
*
|
|
|
|
|
* @throws AmazonErrors
|
|
|
|
|
*/
|
|
|
|
|
public function cancelCode(string $creation_request_id, string $gift_card_id): CancelResponse
|
|
|
|
|
{
|
|
|
|
|
$service_operation = self::CANCEL_GIFT_CARD_SERVICE;
|
|
|
|
|
$payload = $this->getCancelGiftCardPayload($creation_request_id, $gift_card_id);
|
|
|
|
|
$canonical_request = $this->getCanonicalRequest($service_operation, $payload);
|
|
|
|
|
$date_time_string = $this->getTimestamp();
|
|
|
|
|
AmazonDebug::writeLog(['call' => __METHOD__]);
|
|
|
|
|
$result = json_decode($this->makeRequest(
|
|
|
|
|
$payload,
|
|
|
|
|
$canonical_request,
|
|
|
|
|
$service_operation,
|
|
|
|
|
$date_time_string
|
|
|
|
|
), true);
|
|
|
|
|
return new CancelResponse($result);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
2022-06-10 14:37:07 +09:00
|
|
|
* Get current account funds
|
|
|
|
|
*
|
|
|
|
|
* @return CreateBalanceResponse Object with AWS response data
|
2021-10-18 18:24:38 +09:00
|
|
|
*
|
|
|
|
|
* @throws AmazonErrors
|
|
|
|
|
*/
|
|
|
|
|
public function getBalance(): CreateBalanceResponse
|
|
|
|
|
{
|
|
|
|
|
$service_operation = self::GET_AVAILABLE_FUNDS_SERVICE;
|
|
|
|
|
$payload = $this->getAvailableFundsPayload();
|
|
|
|
|
$canonical_request = $this->getCanonicalRequest($service_operation, $payload);
|
|
|
|
|
$date_time_string = $this->getTimestamp();
|
|
|
|
|
AmazonDebug::writeLog(['call' => __METHOD__]);
|
|
|
|
|
$result = json_decode($this->makeRequest(
|
|
|
|
|
$payload,
|
|
|
|
|
$canonical_request,
|
|
|
|
|
$service_operation,
|
|
|
|
|
$date_time_string
|
|
|
|
|
), true);
|
|
|
|
|
return new CreateBalanceResponse($result);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
2022-06-10 14:37:07 +09:00
|
|
|
* General request method for all actions
|
|
|
|
|
* Calls the Client class that actually runs the json request
|
|
|
|
|
* For service_operation valid data see AWS GCOD documentation
|
|
|
|
|
*
|
|
|
|
|
* @param string $payload The data needed for this request
|
|
|
|
|
* @param string $canonical_request Header data to send for this request
|
|
|
|
|
* @param string $service_operation Service operation. CREATE_GIFT_CARD_SERVICE,
|
|
|
|
|
* CANCEL_GIFT_CARD_SERVICE or
|
|
|
|
|
* GET_AVAILABLE_FUNDS_SERVICE constant values
|
|
|
|
|
* @param string $date_time_string Ymd\THis\Z encoded timestamp, getTimestamp()
|
|
|
|
|
* @return string Request result as string, json data
|
2021-10-18 18:24:38 +09:00
|
|
|
*/
|
|
|
|
|
public function makeRequest(
|
|
|
|
|
string $payload,
|
|
|
|
|
string $canonical_request,
|
|
|
|
|
string $service_operation,
|
|
|
|
|
string $date_time_string
|
|
|
|
|
): string {
|
|
|
|
|
// debug
|
|
|
|
|
AmazonDebug::writeLog([__METHOD__ => [
|
|
|
|
|
'Operation' => $service_operation,
|
|
|
|
|
'Payload' => $payload,
|
|
|
|
|
'Cannonical Request' => $canonical_request,
|
|
|
|
|
'Date Time String' => $date_time_string
|
|
|
|
|
|
|
|
|
|
]]);
|
|
|
|
|
$KEY_QUALIFIER = self::KEY_QUALIFIER;
|
|
|
|
|
$canonical_request_hash = $this->buildHash($canonical_request);
|
|
|
|
|
$string_to_sign = $this->buildStringToSign($canonical_request_hash);
|
|
|
|
|
$authorization_value = $this->buildAuthSignature($string_to_sign);
|
|
|
|
|
|
|
|
|
|
$secret_key = $this->config->getSecret();
|
|
|
|
|
$endpoint = $this->config->getEndpoint();
|
|
|
|
|
$region_name = $this->getRegion();
|
|
|
|
|
|
|
|
|
|
$SERVICE_NAME = 'AGCODService';
|
|
|
|
|
$service_target = 'com.amazonaws.agcod.' . $SERVICE_NAME . '.' . $service_operation;
|
|
|
|
|
$date_string = $this->getDateString();
|
|
|
|
|
|
|
|
|
|
$signature_aws_key = $KEY_QUALIFIER . $secret_key;
|
|
|
|
|
|
|
|
|
|
$k_date = $this->hmac($date_string, $signature_aws_key);
|
|
|
|
|
$k_date_hexis = $this->hmac($date_string, $signature_aws_key, false);
|
|
|
|
|
$k_region = $this->hmac($region_name, $k_date);
|
|
|
|
|
$k_region_hexis = $this->hmac($region_name, $k_date, false);
|
|
|
|
|
$k_service_hexis = $this->hmac($SERVICE_NAME, $k_region, false);
|
|
|
|
|
|
|
|
|
|
AmazonDebug::writeLog([__METHOD__ => [
|
|
|
|
|
'Date' => $k_date_hexis,
|
|
|
|
|
'Region' => $k_region_hexis,
|
|
|
|
|
'Service' => $k_service_hexis,
|
|
|
|
|
]]);
|
|
|
|
|
|
2021-10-21 14:57:29 +09:00
|
|
|
$url = 'https://' . $endpoint . '/' . $service_operation;
|
2022-06-10 14:37:07 +09:00
|
|
|
$headers = $this->buildHeaders(
|
|
|
|
|
$payload,
|
|
|
|
|
$authorization_value,
|
|
|
|
|
$date_time_string,
|
|
|
|
|
$service_target
|
|
|
|
|
);
|
2021-10-18 18:24:38 +09:00
|
|
|
return (new Client())->request($url, $headers, $payload);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
2022-06-10 14:37:07 +09:00
|
|
|
* Build the headers used in the makeRequest method.
|
|
|
|
|
* These are the HTML headers used with curl
|
|
|
|
|
*
|
|
|
|
|
* @param string $payload Paylout to create this header for
|
|
|
|
|
* @param string $authorization_value Auth string
|
|
|
|
|
* @param string $date_time_string Ymd\THis\Z encoded timestamp, getTimestamp()
|
|
|
|
|
* @param string $service_target Target service in the agcod string:
|
|
|
|
|
* Value like com.amazonaws.agcod.<sn>.<so>
|
|
|
|
|
* @return array<mixed> Header data as array for curl request
|
2021-10-18 18:24:38 +09:00
|
|
|
*/
|
|
|
|
|
public function buildHeaders(
|
|
|
|
|
string $payload,
|
|
|
|
|
string $authorization_value,
|
|
|
|
|
string $date_time_string,
|
|
|
|
|
string $service_target
|
|
|
|
|
): array {
|
|
|
|
|
$ACCEPT_HEADER = self::ACCEPT_HEADER;
|
|
|
|
|
$X_AMZ_DATE_HEADER = self::X_AMZ_DATE_HEADER;
|
|
|
|
|
$X_AMZ_TARGET_HEADER = self::X_AMZ_TARGET_HEADER;
|
|
|
|
|
$AUTHORIZATION_HEADER = self::AUTHORIZATION_HEADER;
|
|
|
|
|
return [
|
|
|
|
|
'Content-Type:' . $this->getContentType(),
|
|
|
|
|
'Content-Length: ' . strlen($payload),
|
|
|
|
|
$AUTHORIZATION_HEADER . ':' . $authorization_value,
|
|
|
|
|
$X_AMZ_DATE_HEADER . ':' . $date_time_string,
|
|
|
|
|
$X_AMZ_TARGET_HEADER . ':' . $service_target,
|
|
|
|
|
$ACCEPT_HEADER . ':' . $this->getContentType()
|
|
|
|
|
];
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
2022-06-10 14:37:07 +09:00
|
|
|
* The request string build with the actauly request data created by
|
|
|
|
|
* getCanonicalRequest(). This string is used in the auth signature call
|
|
|
|
|
*
|
|
|
|
|
* @param string $canonical_request_hash sha256 hash to build from
|
|
|
|
|
* @return string String to send to buildAuthSignature()
|
|
|
|
|
*/
|
|
|
|
|
public function buildStringToSign($canonical_request_hash): string
|
|
|
|
|
{
|
|
|
|
|
$AWS_SHA256_ALGORITHM = self::AWS_SHA256_ALGORITHM;
|
|
|
|
|
$TERMINATION_STRING = self::TERMINATION_STRING;
|
|
|
|
|
$SERVICE_NAME = self::SERVICE_NAME;
|
|
|
|
|
$region_name = $this->getRegion();
|
|
|
|
|
$date_time_string = $this->getTimestamp();
|
|
|
|
|
$date_string = $this->getDateString();
|
|
|
|
|
$string_to_sign = "$AWS_SHA256_ALGORITHM\n"
|
|
|
|
|
. "$date_time_string\n"
|
|
|
|
|
. "$date_string/$region_name/$SERVICE_NAME/$TERMINATION_STRING\n"
|
|
|
|
|
. "$canonical_request_hash";
|
|
|
|
|
|
|
|
|
|
return $string_to_sign;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
* Build the authentication signature used in the buildHeaders method
|
|
|
|
|
*
|
|
|
|
|
* @param string $string_to_sign Data to sign, buildStringToSign()
|
|
|
|
|
* @return string Authorized value as string
|
2021-10-18 18:24:38 +09:00
|
|
|
*/
|
|
|
|
|
public function buildAuthSignature(string $string_to_sign): string
|
|
|
|
|
{
|
|
|
|
|
$AWS_SHA256_ALGORITHM = self::AWS_SHA256_ALGORITHM;
|
|
|
|
|
$SERVICE_NAME = self::SERVICE_NAME;
|
|
|
|
|
$TERMINATION_STRING = self::TERMINATION_STRING;
|
|
|
|
|
$ACCEPT_HEADER = self::ACCEPT_HEADER;
|
|
|
|
|
$HOST_HEADER = self::HOST_HEADER;
|
|
|
|
|
$X_AMZ_DATE_HEADER = self::X_AMZ_DATE_HEADER;
|
|
|
|
|
$X_AMZ_TARGET_HEADER = self::X_AMZ_TARGET_HEADER;
|
|
|
|
|
|
|
|
|
|
$aws_key_id = $this->config->getAccessKey();
|
|
|
|
|
$region_name = $this->getRegion();
|
|
|
|
|
|
|
|
|
|
$date_string = $this->getDateString();
|
|
|
|
|
$derived_key = $this->buildDerivedKey();
|
|
|
|
|
// Calculate signature per http://docs.aws.amazon.com/general/latest/gr/sigv4-calculate-signature.html
|
|
|
|
|
$final_signature = $this->hmac($string_to_sign, $derived_key, false);
|
|
|
|
|
|
|
|
|
|
// Assemble Authorization Header with signing information
|
|
|
|
|
// per http://docs.aws.amazon.com/general/latest/gr/sigv4-add-signature-to-request.html
|
|
|
|
|
$authorization_value =
|
|
|
|
|
$AWS_SHA256_ALGORITHM
|
|
|
|
|
. ' Credential=' . $aws_key_id
|
|
|
|
|
. '/' . $date_string . '/' . $region_name . '/' . $SERVICE_NAME . '/' . $TERMINATION_STRING . ','
|
|
|
|
|
. ' SignedHeaders='
|
|
|
|
|
. $ACCEPT_HEADER . ';' . $HOST_HEADER . ';' . $X_AMZ_DATE_HEADER . ';' . $X_AMZ_TARGET_HEADER . ','
|
|
|
|
|
. ' Signature='
|
|
|
|
|
. $final_signature;
|
|
|
|
|
|
|
|
|
|
return $authorization_value;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
2022-06-10 14:37:07 +09:00
|
|
|
* Build the derived key to build the final hmac signature string
|
|
|
|
|
*
|
|
|
|
|
* @param bool $rawOutput Set to true to create the hash based message
|
|
|
|
|
* authenticator string as normal text string or
|
|
|
|
|
* lowercase hexbits
|
|
|
|
|
* @return string Derived key (hmac type)
|
2021-10-18 18:24:38 +09:00
|
|
|
*/
|
|
|
|
|
public function buildDerivedKey(bool $rawOutput = true): string
|
|
|
|
|
{
|
|
|
|
|
$KEY_QUALIFIER = self::KEY_QUALIFIER;
|
|
|
|
|
$TERMINATION_STRING = self::TERMINATION_STRING;
|
|
|
|
|
$SERVICE_NAME = self::SERVICE_NAME;
|
|
|
|
|
|
|
|
|
|
$aws_secret_key = $this->config->getSecret();
|
|
|
|
|
// Append Key Qualifier, "AWS4", to secret key per
|
|
|
|
|
// shttp://docs.aws.amazon.com/general/latest/gr/signature-v4-examples.html
|
|
|
|
|
$signature_aws_key = $KEY_QUALIFIER . $aws_secret_key;
|
|
|
|
|
$region_name = $this->getRegion();
|
|
|
|
|
$date_string = $this->getDateString();
|
|
|
|
|
|
|
|
|
|
$k_date = $this->hmac($date_string, $signature_aws_key);
|
|
|
|
|
$k_region = $this->hmac($region_name, $k_date);
|
|
|
|
|
$k_service = $this->hmac($SERVICE_NAME, $k_region);
|
|
|
|
|
|
|
|
|
|
// Derived the Signing key (derivedKey aka kSigning)
|
|
|
|
|
return $this->hmac($TERMINATION_STRING, $k_service, $rawOutput);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
2021-10-20 16:18:18 +09:00
|
|
|
* get the region based on endpoint
|
|
|
|
|
* list as of 2021/10/20
|
|
|
|
|
* WHERE URL REGION
|
|
|
|
|
* North America https://agcod-v2-gamma.amazon.com us-east-1
|
|
|
|
|
* https://agcod-v2.amazon.com
|
|
|
|
|
* (US, CA, MX)
|
|
|
|
|
* Europe and Asia https://agcod-v2-eu-gamma.amazon.com eu-west-1
|
|
|
|
|
* https://agcod-v2-eu.amazon.com
|
|
|
|
|
* (IT, ES, DE, FR, UK, TR, UAE, KSA, PL, NL, SE)
|
|
|
|
|
* Far East https://agcod-v2-fe-gamma.amazon.com us-west-2
|
|
|
|
|
* https://agcod-v2-fe.amazon.com
|
|
|
|
|
* (JP, AU, SG)
|
|
|
|
|
*
|
|
|
|
|
* CURRENCY
|
|
|
|
|
* USD for US
|
|
|
|
|
* EUR for EU (IT, ES, DE, FR, PL, NL, SE)
|
|
|
|
|
* JPY for JP
|
|
|
|
|
* CAD for CA
|
|
|
|
|
* AUD for AU
|
|
|
|
|
* TRY for TR
|
|
|
|
|
* AED for UAE
|
|
|
|
|
* MXN for MX
|
|
|
|
|
* GBP for UK
|
|
|
|
|
*
|
2022-06-10 14:37:07 +09:00
|
|
|
* @return string Region string depending on given endpoint url
|
2021-10-18 18:24:38 +09:00
|
|
|
*/
|
|
|
|
|
public function getRegion(): string
|
|
|
|
|
{
|
|
|
|
|
$endpoint = $this->config->getEndpoint();
|
|
|
|
|
// default region
|
|
|
|
|
$region_name = 'us-east-1';
|
|
|
|
|
|
|
|
|
|
switch ($endpoint) {
|
|
|
|
|
case 'agcod-v2.amazon.com':
|
|
|
|
|
case 'agcod-v2-gamma.amazon.com':
|
|
|
|
|
$region_name = 'us-east-1';
|
|
|
|
|
break;
|
|
|
|
|
case 'agcod-v2-eu.amazon.com':
|
|
|
|
|
case 'agcod-v2-eu-gamma.amazon.com':
|
|
|
|
|
$region_name = 'us-west-1';
|
|
|
|
|
break;
|
|
|
|
|
case 'agcod-v2-fe.amazon.com':
|
|
|
|
|
case 'agcod-v2-fe-gamma.amazon.com':
|
|
|
|
|
$region_name = 'us-west-2';
|
|
|
|
|
break;
|
|
|
|
|
}
|
|
|
|
|
return $region_name;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
/**
|
2022-06-10 14:37:07 +09:00
|
|
|
* The actual data to send as json encoded string for creating a gift card.
|
|
|
|
|
* The creation request id must be in the format:
|
|
|
|
|
* <partner_id>_<unique id 13 characters>
|
|
|
|
|
*
|
|
|
|
|
* @param float $amount Amount of currencty to create the gift card
|
|
|
|
|
* request for
|
|
|
|
|
* @param string|null $creation_id The creation id, if not set will be created here
|
|
|
|
|
* @return string JSON encoded array to be used as payload
|
|
|
|
|
* in get gift card call
|
2021-10-18 18:24:38 +09:00
|
|
|
*/
|
|
|
|
|
public function getGiftCardPayload(float $amount, ?string $creation_id = null): string
|
|
|
|
|
{
|
|
|
|
|
$payload = [
|
|
|
|
|
'creationRequestId' => $creation_id ?: uniqid($this->config->getPartner() . '_'),
|
|
|
|
|
'partnerId' => $this->config->getPartner(),
|
|
|
|
|
'value' =>
|
|
|
|
|
[
|
|
|
|
|
'currencyCode' => $this->config->getCurrency(),
|
2021-10-21 14:57:29 +09:00
|
|
|
'amount' => $amount
|
2021-10-18 18:24:38 +09:00
|
|
|
]
|
|
|
|
|
];
|
2021-10-21 13:29:50 +09:00
|
|
|
return (json_encode($payload)) ?: '';
|
2021-10-18 18:24:38 +09:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
2022-06-10 14:37:07 +09:00
|
|
|
* The actual data to send as json encoded string to cancel a created gift card
|
|
|
|
|
*
|
|
|
|
|
* @param string $creation_request_id Creation request id from previous get gift card
|
|
|
|
|
* @param string $gift_card_id Gift card id from previous get gift card
|
|
|
|
|
* @return string JSON encoded array to be used as payload
|
|
|
|
|
* in cancle gift card call
|
2021-10-18 18:24:38 +09:00
|
|
|
*/
|
|
|
|
|
public function getCancelGiftCardPayload(string $creation_request_id, string $gift_card_id): string
|
|
|
|
|
{
|
|
|
|
|
$payload = [
|
|
|
|
|
'creationRequestId' => $creation_request_id,
|
|
|
|
|
'partnerId' => $this->config->getPartner(),
|
2021-10-21 13:29:50 +09:00
|
|
|
'gcId' => $gift_card_id
|
2021-10-18 18:24:38 +09:00
|
|
|
];
|
2021-10-21 13:29:50 +09:00
|
|
|
return (json_encode($payload)) ?: '';
|
2021-10-18 18:24:38 +09:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
2022-06-10 14:37:07 +09:00
|
|
|
* The actualy data to send as json encoded string for getting the current
|
|
|
|
|
* account funds
|
|
|
|
|
*
|
|
|
|
|
* @return string JSON encoded array to be used as payload in funds call
|
2021-10-18 18:24:38 +09:00
|
|
|
*/
|
|
|
|
|
public function getAvailableFundsPayload(): string
|
|
|
|
|
{
|
|
|
|
|
$payload = [
|
|
|
|
|
'partnerId' => $this->config->getPartner(),
|
|
|
|
|
];
|
2021-10-21 13:29:50 +09:00
|
|
|
return (json_encode($payload)) ?: '';
|
2021-10-18 18:24:38 +09:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
2022-06-10 14:37:07 +09:00
|
|
|
* Heeders used in the getCanonicalRequest()
|
|
|
|
|
*
|
|
|
|
|
* @param string $service_operation Service operation code in the service string request
|
|
|
|
|
* Value is: com.amazonaws.agcod.AGCODService.<so>
|
|
|
|
|
* @return string Header string to be used
|
|
|
|
|
*/
|
|
|
|
|
public function buildCanonicalHeaders(string $service_operation): string
|
|
|
|
|
{
|
|
|
|
|
$ACCEPT_HEADER = self::ACCEPT_HEADER;
|
|
|
|
|
$HOST_HEADER = self::HOST_HEADER;
|
|
|
|
|
$X_AMZ_DATE_HEADER = self::X_AMZ_DATE_HEADER;
|
|
|
|
|
$X_AMZ_TARGET_HEADER = self::X_AMZ_TARGET_HEADER;
|
|
|
|
|
$date_time_string = $this->getTimestamp();
|
|
|
|
|
$endpoint = $this->config->getEndpoint();
|
|
|
|
|
$content_type = $this->getContentType();
|
|
|
|
|
return "$ACCEPT_HEADER:$content_type\n"
|
|
|
|
|
. "$HOST_HEADER:$endpoint\n"
|
|
|
|
|
. "$X_AMZ_DATE_HEADER:$date_time_string\n"
|
|
|
|
|
. "$X_AMZ_TARGET_HEADER:com.amazonaws.agcod.AGCODService.$service_operation";
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
|
|
|
|
* Headers used in the get/cancel/funds requests
|
|
|
|
|
*
|
|
|
|
|
* @param string $service_operation Service operation code to be used in header request
|
|
|
|
|
* and main request call
|
|
|
|
|
* @param string $payload Payload from get/cancle Code or funds call
|
|
|
|
|
* @return string Full POST service request code
|
2021-10-18 18:24:38 +09:00
|
|
|
*/
|
|
|
|
|
public function getCanonicalRequest(string $service_operation, string $payload): string
|
|
|
|
|
{
|
|
|
|
|
$HOST_HEADER = self::HOST_HEADER;
|
|
|
|
|
$X_AMZ_DATE_HEADER = self::X_AMZ_DATE_HEADER;
|
|
|
|
|
$X_AMZ_TARGET_HEADER = self::X_AMZ_TARGET_HEADER;
|
|
|
|
|
$ACCEPT_HEADER = self::ACCEPT_HEADER;
|
|
|
|
|
$payload_hash = $this->buildHash($payload);
|
|
|
|
|
$canonical_headers = $this->buildCanonicalHeaders($service_operation);
|
|
|
|
|
$canonical_request = "POST\n"
|
|
|
|
|
. "/$service_operation\n\n"
|
|
|
|
|
. "$canonical_headers\n\n"
|
|
|
|
|
. "$ACCEPT_HEADER;$HOST_HEADER;$X_AMZ_DATE_HEADER;$X_AMZ_TARGET_HEADER\n"
|
|
|
|
|
. "$payload_hash";
|
|
|
|
|
return $canonical_request;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
2022-06-10 14:37:07 +09:00
|
|
|
* Build sha256 hash from given data
|
|
|
|
|
*
|
|
|
|
|
* @param string $data Data to be hashed with sha256
|
|
|
|
|
* @return string sha256 hash
|
2021-10-18 18:24:38 +09:00
|
|
|
*/
|
|
|
|
|
public function buildHash(string $data): string
|
|
|
|
|
{
|
|
|
|
|
return hash('sha256', $data);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
2022-06-10 14:37:07 +09:00
|
|
|
* Create a sha256 based Hash-Based Message Authentication Code
|
|
|
|
|
* with the given key and data
|
|
|
|
|
*
|
|
|
|
|
* @param string $data Data to be hashed with key below
|
|
|
|
|
* @param string $key Key to be used for creating the hash
|
|
|
|
|
* @param bool $raw Returning data as ascii string or hexibits
|
|
|
|
|
* @return string Hash-Based Message Authentication Code
|
2021-10-18 18:24:38 +09:00
|
|
|
*/
|
2022-06-10 14:37:07 +09:00
|
|
|
public function hmac(string $data, string $key, bool $raw = true): string
|
2021-10-18 18:24:38 +09:00
|
|
|
{
|
2022-06-10 14:37:07 +09:00
|
|
|
return hash_hmac('sha256', $data, $key, $raw);
|
2021-10-18 18:24:38 +09:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
2022-06-10 14:37:07 +09:00
|
|
|
* Build timestamp in the format used by AWS services
|
|
|
|
|
* eg 20211009\T102030\Z
|
|
|
|
|
*
|
|
|
|
|
* @return string date string based on current time. Ymd\THis\Z
|
2021-10-18 18:24:38 +09:00
|
|
|
*/
|
2022-06-10 14:37:07 +09:00
|
|
|
public function getTimestamp()
|
2021-10-18 18:24:38 +09:00
|
|
|
{
|
2022-06-10 14:37:07 +09:00
|
|
|
return gmdate('Ymd\THis\Z');
|
2021-10-18 18:24:38 +09:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
2022-06-10 14:37:07 +09:00
|
|
|
* Get only the date string from the getTimestamp
|
|
|
|
|
* eg 20211009
|
|
|
|
|
*
|
|
|
|
|
* @return string Date string YYYYmmdd extracted from getTimestamp()
|
2021-10-18 18:24:38 +09:00
|
|
|
*/
|
|
|
|
|
public function getDateString()
|
|
|
|
|
{
|
|
|
|
|
return substr($this->getTimestamp(), 0, 8);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/**
|
2022-06-10 14:37:07 +09:00
|
|
|
* Fixed content type for submission, is json
|
|
|
|
|
*
|
|
|
|
|
* @return string 'application/json' string
|
2021-10-18 18:24:38 +09:00
|
|
|
*/
|
|
|
|
|
public function getContentType(): string
|
|
|
|
|
{
|
|
|
|
|
return 'application/json';
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// __END__
|