Skip to content

VantagePay SDK for .NET

VantagePay.SDK is the official C# client SDK for integrating with VantagePay APIs.

It provides:

  • typed API clients backed by VantagePay.Models
  • automatic token refresh for authenticated calls
  • automatic HTTP retries for transient failures
  • real-time payment and broadcast updates via SignalR

The TypeScript SDK on NPM covers client capabilities only. This .NET SDK includes both client and admin capabilities.


Table of Contents


Installation

shell
dotnet add package VantagePay.SDK

Or with NuGet Package Manager Console:

powershell
Install-Package VantagePay.SDK

Supported Frameworks

VantagePay.SDK currently targets:

  • .NET 8 (net8.0)
  • .NET 9 (net9.0)
  • .NET 10 (net10.0)

Client Types

Use the client that matches your integration model:

ClientIntended useAuthentication model
VantagePayClientClient-facing integrations (web/mobile apps, POS apps, merchant/consumer flows)Access/refresh token session (LoginAsync)
VantagePayAdminClientTrusted server-side admin integrationsAPI key (apiKey)

Basic Usage

VantagePayClient (client-facing)

csharp
using VantagePay.SDK;
using VantagePay.Models.Lookups;

var client = new VantagePayClient("https://sandbox-api.vantagepay.dev");

await client.Authentication.LoginAsync("233548306110", "Password123!");

var currencies = await client.Lookups.GetCurrenciesAsync();

var summary = await client.Reports.GetTransactionSummaryAsync(Currency.GHS);

VantagePayAdminClient (server-side)

csharp
using VantagePay.SDK;

var adminClient = new VantagePayAdminClient(
    "https://sandbox-api.vantagepay.dev",
    apiKey: "your-admin-api-key");

var userReference = await adminClient.Users.CreateUserAsync("partner.user", "StrongPassword123!");

Configuration and Construction

Constructors

VantagePayClient:

  • new VantagePayClient(environmentUrl)
  • new VantagePayClient(environmentUrl, loggerFactory)
  • new VantagePayClient(environmentUrl, accessToken, refreshToken)
  • new VantagePayClient(environmentUrl, accessToken, refreshToken, loggerFactory)

VantagePayAdminClient:

  • new VantagePayAdminClient(environmentUrl, apiKey)
  • new VantagePayAdminClient(environmentUrl, apiKey, loggerFactory)

Logging

Pass an ILoggerFactory to integrate SDK logs into your logging pipeline.

csharp
using Microsoft.Extensions.Logging;
using VantagePay.SDK;

using var loggerFactory = LoggerFactory.Create(builder => builder.AddConsole());

var client = new VantagePayClient(
    "https://sandbox-api.vantagepay.dev",
    accessToken: null,
    refreshToken: null,
    loggerFactory: loggerFactory);

Retry and refresh behavior

  • HTTP retries are automatic for transient failures.
  • access tokens are refreshed automatically when possible using the current refreshToken.
  • SignalR hubs are configured with automatic reconnect.

Authentication and Tokens

Login and token storage

csharp
var token = await client.Authentication.LoginAsync("233548306110", "Password123!");

// Tokens are persisted in-memory on the client instance.
string? accessToken = client.ApiTokens.AccessToken;
string? refreshToken = client.ApiTokens.RefreshToken;

Restore existing tokens

csharp
var client = new VantagePayClient(
    "https://sandbox-api.vantagepay.dev",
    accessToken: storedAccessToken,
    refreshToken: storedRefreshToken);

Session helpers

csharp
bool loggedIn = client.Authentication.IsLoggedIn();
await client.Authentication.RefreshAsync();
await client.Authentication.LogoutAsync();

Token claim helpers

csharp
var userReference = client.Authentication.GetCurrentUserReference();
var merchantReference = client.Authentication.GetCurrentMerchantReference();
var consumerReference = client.Authentication.GetCurrentConsumerReference();
var terminalReference = client.Authentication.GetCurrentTerminalReference();
var emailAddress = client.Authentication.GetCurrentEmailAddress();

Error Handling

SDK operations throw ApiException derivatives for API failures.

Primary exception types:

  • ApiValidationException (400)
  • ApiAuthorizationException (401)
  • ApiForbiddenException (403)
  • ApiNotFoundException (404)
  • ApiException (other status codes)
csharp
using VantagePay.SDK.Exceptions;

try
{
    await client.Authentication.LoginAsync("user", "wrong-password");
}
catch (ApiAuthorizationException ex)
{
    Console.WriteLine($"Unauthorized ({ex.StatusCode}): {ex.Message}");

    if (ex.ErrorResponse?.MustChangePassword == true)
    {
        await client.Authentication.ChangePasswordAsync("OldPassword", "NewPassword123!");
    }

    if (ex.ErrorResponse?.MustValidatePhoneNumber == true ||
        ex.ErrorResponse?.MustValidateEmailAddress == true)
    {
        await client.Authentication.ResendOtpAsync();
        await client.Authentication.ValidateOtpAsync("123456");
    }
}
catch (ApiValidationException ex)
{
    Console.WriteLine($"Validation error ({ex.StatusCode}): {ex.Message}");
}
catch (ApiException ex)
{
    Console.WriteLine($"API error ({ex.StatusCode}): {ex.Message}");
    throw;
}

Note:

  • many Get* methods return null when an entity is not found.
  • CancellationToken is supported across all async methods.

Public API Surface

VantagePayClient modules

ModulePurpose
AuthenticationLogin/logout, refresh, OTP, password, face/liveness checks
LookupsCountries, currencies, languages, banks, wallet operators, categories, product types, address resolution
ConsumersConsumer profile operations, files, limits, debit orders, broadcast listener
MerchantsMerchant profile operations, OTP verify, terminal setup/config, QR code retrieval, telemetry, broadcast listener
ProductsGlobal product catalog browsing and merchant product management, broadcast listener
PaymentsPayment and refund workflows, tokenization, status monitoring, interactive payment signals
NotificationsIn-app message retrieval and lifecycle
QrCodesDynamic QR generation and QR validation
ReportsRecent transactions, summaries, daily and detailed transaction reporting
SystemHealth ping

Example API calls

csharp
// Lookups
var banks = await client.Lookups.GetBanksAsync();

// Consumer profile
var consumer = await client.Consumers.GetConsumerAsync();

// Merchant profile
var merchant = await client.Merchants.GetMerchantAsync();

// Products
var productTypes = await client.Products.GetActiveProductTypesAsync();

// Notifications
var messages = await client.Notifications.GetMessagesAsync();

// Reports
var recent = await client.Reports.GetRecentTransactionsAsync(limit: 10, successfulOnly: true);

// Health
bool isOnline = await client.System.PingAsync();

Payments and Signals

Payments supports both request/response and event-driven processing.

Basic payment submission

csharp
using System.Collections.Generic;
using VantagePay.Models.Lookups;
using VantagePay.Models.Payments;
using VantagePay.Models.Payments.Requests;

var payment = new PaymentRequest
{
    YourReference = "ORDER-1001",
    PaymentSources = new PaymentSources
    {
        MobileWallets = new List<MobileWalletSource>
        {
            new MobileWalletSource
            {
                MobileWalletOperator = MobileWalletOperator.MTN,
                Msisdn = "233555666112",
                AmountInCents = 5000,
                Currency = Currency.GHS,
            }
        }
    },
    PaymentDestinations = new PaymentDestinations
    {
        Merchants = new List<MerchantDestination>
        {
            new MerchantDestination
            {
                MerchantReference = "merchant-reference",
                AmountInCents = 5000,
                Currency = Currency.GHS,
                PaymentType = MerchantPaymentType.BuyingGoods,
            }
        }
    }
};

var initialStatus = await client.Payments.PayAsync(payment);

Subscribing to payment signals

csharp
using VantagePay.Models.Lookups;
using VantagePay.Models.Common;

client.Payments.OnPaymentStatusUpdate = status =>
{
    Console.WriteLine($"{status.PaymentReference}: {status.PercentageComplete}%");
};

client.Payments.OnPaymentComplete = status =>
{
    Console.WriteLine($"Payment complete: {status.PaymentReference}");
};

client.Payments.OnRequiresPin = data =>
{
    var pin = "1234";
    _ = client.Payments.SubmitPinCodeAsync(data.TransactionReference, pin);
};

client.Payments.OnRequiresConfirmation = data =>
{
    _ = client.Payments.SubmitConfirmationAsync(data.TransactionReference, confirm: true);
};

client.Payments.OnRequiresAddress = data =>
{
    var address = new Address
    {
        AddressType = AddressType.Billing,
        AddressLine1 = "10 Main Road",
        City = "Johannesburg",
        CountryIsoCode = Country.ZAF,
        PostalCode = "2196",
    };

    _ = client.Payments.SubmitAddressAsync(data.TransactionReference, address);
};

client.Payments.OnRequires3DSecure = data =>
{
    Console.WriteLine($"Open 3DS URL: {data.ThreeDSecureUrl}");
};

client.Payments.OnComplete3DSecure = () =>
{
    Console.WriteLine("3DS flow completed");
};

Waiting for completion

csharp
var finalStatus = await client.Payments.WaitForPaymentCompleteAsync();

Consumer, merchant, and product broadcast signals

csharp
client.Consumers.OnConsumerUpdate = () =>
{
    Console.WriteLine("Consumer profile updated");
};

client.Merchants.OnMerchantUpdate = () =>
{
    Console.WriteLine("Merchant profile updated");
};

client.Products.OnProductUpdate = () =>
{
    Console.WriteLine("Product catalog updated");
};

await client.Consumers.StartConsumerBroadcastListenerAsync();
await client.Merchants.StartMerchantBroadcastListenerAsync();
await client.Products.StartProductBroadcastListenerAsync();

Manual status-check control

csharp
await client.Payments.StartPaymentStatusCheckingAsync(); // listen for external incoming payment

await client.Payments.StopPaymentStatusCheckingAsync();  // stop all

Tokenization and receipts

csharp
using VantagePay.Models.Lookups;
using VantagePay.Models.Tokens;

var cardToken = await client.Payments.CreateCardTokenAsync(new CardRequest
{
    CardNumber = "4111111111111111",
    NameOnCard = "Jane Doe",
    ExpiryMonth = Month.March,
    ExpiryYear = 2027,
});

if (cardToken?.Token is not null)
{
    await client.Payments.ActivateCardTokenAsync(cardToken.Token);
}
csharp
var receipt = await client.Payments.GetPaymentReceiptAsync(paymentReference);
await client.Payments.SendEmailNotificationAsync(paymentReference.ToString(), "customer@example.com");

Server-side Admin Usage

Use VantagePayAdminClient with API key authorization for administrative workflows.

Admin modules

ModulePurpose
AuthenticationGenerate consumer/merchant tokens, reset passwords, OTP send/validate, lock/unlock/logout user
ConsumersManage consumers, files, and KYC state
MerchantsManage merchants, files, KYB state, business hierarchy, device lookup
NotificationsManage templates and send targeted merchant/consumer in-app messages
ProductsAssignable products, merchant product management, apply product catalogs
PaymentsAdmin payment/refund initiation and status/receipt operations (IPaymentsAdminApi)
UsersCreate and deactivate users

Admin examples

csharp
// Generate a merchant-scoped token pair from the server side.
var merchantToken = await adminClient.Authentication.GenerateMerchantTokenAsync(merchantReference);
csharp
// Reset a user password.
await adminClient.Authentication.ResetPasswordAsync("partner.user", "NewStrongPassword123!");
csharp
// Create a targeted merchant message.
using VantagePay.Models.Notifications;
using VantagePay.Models.Notifications.Requests;

await adminClient.Notifications.CreateMerchantMessageAsync(
    new CreateMessageRequest
    {
        MessageType = MessageType.Information,
        MessageTarget = MessageTarget.Portal,
        MessagePlacement = MessagePlacement.Dashboard,
        Header = "Planned Maintenance",
        Body = "Service window starts at 22:00 UTC.",
        VisibleUntilDate = DateTimeOffset.UtcNow.AddDays(7),
    },
    merchantReference);

Migration Guide

If migrating from ZGA.Core.Web.Api.Client, apply these namespace/package updates:

  • replace ZGA.Core.Web.Api.Client with VantagePay.SDK
  • replace ZGA.Core.Models with VantagePay.Models

Payments for Africa