Gateway Interface
Gateway adapters implement methods for:
id
label
isConfigured
createCharge
createSubscription
retrySubscriptionPayment
createRefund
syncCustomer
verifyWebhook
mapEvent
Gateway Skeleton
namespace MyPlugin\AweCommerce;
use AweCommerce\Gateways\GatewayInterface;
use AweCommerce\Gateways\IncomingWebhook;
use AweCommerce\Gateways\Requests\ChargeRequest;
use AweCommerce\Gateways\Requests\RefundRequest;
use AweCommerce\Gateways\Requests\SubscriptionRequest;
use AweCommerce\Gateways\Requests\SubscriptionRetryRequest;
use AweCommerce\Gateways\Requests\CustomerSyncRequest;
use AweCommerce\Gateways\Responses\ChargeResult;
use AweCommerce\Gateways\Responses\RefundResult;
use AweCommerce\Gateways\Responses\SubscriptionResult;
use AweCommerce\Gateways\Responses\CustomerSyncResult;
use AweCommerce\Gateways\Responses\MappedEvent;
final class ExampleGateway implements GatewayInterface
{
public function id(): string
{
return 'example';
}
public function label(): string
{
return 'Example Gateway';
}
public function isConfigured(): bool
{
return get_option('example_gateway_secret', '') !== '';
}
public function createCharge(ChargeRequest $request): ChargeResult
{
throw new \RuntimeException('Implement charge creation.');
}
public function createSubscription(SubscriptionRequest $request): SubscriptionResult
{
throw new \RuntimeException('Subscriptions not supported by this gateway.');
}
public function retrySubscriptionPayment(SubscriptionRetryRequest $request): ChargeResult
{
throw new \RuntimeException('Retries not supported by this gateway.');
}
public function createRefund(RefundRequest $request): RefundResult
{
throw new \RuntimeException('Implement refund creation.');
}
public function syncCustomer(CustomerSyncRequest $request): CustomerSyncResult
{
throw new \RuntimeException('Implement customer sync.');
}
public function verifyWebhook(IncomingWebhook $webhook): bool
{
return true;
}
public function mapEvent(IncomingWebhook $webhook): ?MappedEvent
{
return null;
}
}
Gateway Design Rules
- Keep totals server-authoritative.
- Use idempotency keys for charge and refund calls when provider supports them.
- Verify webhook signatures before mapping events.
- Store ignored provider events for review.
- Do not create subscriptions from one-time payment gateways.
- Do not advance subscription access without provider payment confirmation.
- Never log card data or gateway secrets.
- Keep gateway IDs stable once used in production.
Gateway Availability Filter
add_filter('awecommerce_gateway_available', function (array $gateways, string $context) {
if ($context === 'checkout' && isset($gateways['store'])) {
unset($gateways['store']);
}
return $gateways;
}, 10, 2);
Webhook Hooks
add_action('awecommerce_webhook_received', function ($gateway_id, $incoming_webhook) {
error_log('Webhook received for ' . $gateway_id);
}, 10, 2);
add_action('awecommerce_webhook_processed', function ($gateway_id, $mapped_event) {
error_log('Webhook processed for ' . $gateway_id);
}, 10, 2);