Solart.Arca.Client
1.55.1.14
Prefix Reserved
dotnet add package Solart.Arca.Client --version 1.55.1.14
NuGet\Install-Package Solart.Arca.Client -Version 1.55.1.14
<PackageReference Include="Solart.Arca.Client" Version="1.55.1.14" />
<PackageVersion Include="Solart.Arca.Client" Version="1.55.1.14" />
<PackageReference Include="Solart.Arca.Client" />
paket add Solart.Arca.Client --version 1.55.1.14
#r "nuget: Solart.Arca.Client, 1.55.1.14"
#:package Solart.Arca.Client@1.55.1.14
#addin nuget:?package=Solart.Arca.Client&version=1.55.1.14
#tool nuget:?package=Solart.Arca.Client&version=1.55.1.14
Solart.Arca.Client
ARCA (BPC Ipay) virtual POS REST client for ASP.NET Core. Use it to register orders, complete payments on your site or via redirect, run two-stage (pre-auth + capture) flows, manage card bindings, and work with 3DS enrollment — all over the same /payment/rest/ API as the official merchant manual.
Requirements
- .NET 10 or later (targets
net10.0) - Nullable reference types are enabled: response models use
?where the gateway may omit JSON fields; request types userequiredfor parameters you must send for a valid call.
Installation
dotnet add package Solart.Arca.Client
Configuration
Register the client once at startup with your credentials and the gateway base URL:
// Program.cs / Startup.cs
builder.Services.AddArcaClient("default", new ArcaCredentials
{
Username = "your_merchant_username",
Password = "your_merchant_password"
}).ConfigureHttpClient(c =>
c.BaseAddress = new Uri("https://ipay.arca.am/payment/rest/"));
Credentials are stored once and injected automatically into every request — you never need to include them in individual API calls.
The method returns IHttpClientBuilder, so you can chain additional configuration:
builder.Services.AddArcaClient("default", new ArcaCredentials
{
Username = "your_merchant_username",
Password = "your_merchant_password"
})
.ConfigureHttpClient(c =>
c.BaseAddress = new Uri("https://ipay.arca.am/payment/rest/"))
.AddHttpMessageHandler<MyLoggingHandler>()
.AddPolicyHandler(retryPolicy);
Multiple terminals or base URLs
If you need more than one merchant terminal or a different base URL (for example separate payment and binding endpoints), register named clients and resolve them with keyed DI:
builder.Services.AddArcaClient("payments", paymentCreds)
.ConfigureHttpClient(c =>
c.BaseAddress = new Uri("https://ipay.arca.am/payment/rest/"));
builder.Services.AddArcaClient("bindings", bindingCreds)
.ConfigureHttpClient(c =>
c.BaseAddress = new Uri("https://ipay.arca.am/payment/rest/"));
// Elsewhere — resolve by name:
public class Checkout(
[FromKeyedServices("payments")] IArcaClient pay,
[FromKeyedServices("bindings")] IArcaClient bind)
{
}
Without pre-set credentials
If you prefer to set credentials at runtime (e.g. multi-tenant scenarios where credentials vary per request), register without ArcaCredentials and call WithSettings before the first API call:
builder.Services.AddArcaClient()
.ConfigureHttpClient(c =>
c.BaseAddress = new Uri("https://ipay.arca.am/payment/rest/"));
This overload uses the typed HttpClient pattern, so IArcaClient can be injected directly:
public class PaymentService(IArcaClient arca)
{
public async Task Pay(ArcaCredentials creds)
{
var result = await arca.WithSettings(creds).RegisterAsync(new RegisterOrderRequest { ... });
}
}
Usage
Inject IArcaClient via keyed services (when registered with credentials) or directly (when registered without):
// Keyed — matches AddArcaClient("default", creds)
public class PaymentService([FromKeyedServices("default")] IArcaClient arca)
{
}
// Direct — matches AddArcaClient() (no credentials overload)
public class PaymentService(IArcaClient arca)
{
}
Available operations
| Method | Description |
|---|---|
RegisterAsync |
Register a new payment order and get a redirect URL |
PreRegisterAsync |
Pre-authorize (hold) funds without capturing |
DepositAsync |
Capture pre-authorized funds |
GetOrderStatusAsync |
Full order status (getOrderStatusExtended) |
ReverseOrderAsync |
Cancel/reverse a payment |
RefundOrderAsync |
Refund a completed payment |
PaymentOrderAsync |
Direct card payment (card data on your side) |
PaymentOrderBindingAsync |
Pay with a saved card binding |
BindCardAsync |
Activate a saved card binding |
UnBindCardAsync |
Deactivate a saved card binding |
GetBindingsAsync |
List saved card bindings for a client |
VerifyEnrollmentAsync |
Check if a card is enrolled in 3DS |
Examples
Register a payment order
var response = await _arca.RegisterAsync(new RegisterOrderRequest
{
OrderNumber = "ORD-001",
Amount = 5000, // minor units (e.g. 5000 = 50.00 AMD)
ReturnUrl = "https://yoursite.am/payment/result",
Currency = "051", // ISO 4217 numeric — 051 = AMD
Language = "hy",
Description = "Order #ORD-001",
});
if (response.ErrorCode == 0)
{
// Redirect user to response.FormUrl to complete payment
return Redirect(response.FormUrl);
}
Check order status
var status = await _arca.GetOrderStatusAsync(new OrderStatusRequest
{
OrderNumber = "ORD-001",
Language = "en",
});
Console.WriteLine($"Status: {status.OrderStatus?.ToString() ?? "n/a"}, ActionCode: {status.ActionCode}");
Pay with a saved card binding
var result = await _arca.PaymentOrderBindingAsync(new PaymentOrderBindingRequest
{
OrderId = "server-assigned-order-id",
BindingId = "client-binding-id",
CVC = "123",
Language = "en",
});
// 3DS: when the gateway returns ACS data, redirect the browser using AcsUrl, PaReq, TermUrl
if (!string.IsNullOrEmpty(result.AcsUrl))
{
// POST paReq to result.AcsUrl, termUrl = result.TermUrl (per gateway / manual)
}
Get saved card bindings for a client
var bindings = await _arca.GetBindingsAsync(new BindingRequest
{
ClientId = "client-123",
});
foreach (var card in bindings.Bindings ?? [])
{
Console.WriteLine($"{card.MaskedPan} expires {card.ExpiryDate}");
}
Order status values
GetOrderStatusAsync maps orderStatus to Solart.Arca.Client.Constants.OrderStatus? (null if the gateway omits it):
| Enum value | Meaning |
|---|---|
RegisteredUnpaid |
Order registered, not yet paid |
FundsFrozen |
Funds held (pre-auth) |
Authorized |
Payment authorized |
AuthorizationCancelled |
Authorization cancelled |
Refunded |
Refund performed |
InitializedACS |
3DS ACS challenge initiated |
Unauthorized |
Payment declined |
Constants
Use the built-in constants to interpret response codes without magic numbers:
using Solart.Arca.Client.Constants;
if (status.ActionCode == ActionCodes.APPROVED)
{
// payment approved
}
ActionCodes— action code constants (approvals, declines, 3DS, limits, etc.)ErrorCodes— gateway error code helpers where applicable
3DS support
VerifyEnrollmentAsync— check enrollment before a direct card payment.PaymentOrderAsync/PaymentOrderBindingAsync— on success paths that require authentication, responses can includeAcsUrl,PaReq, andTermUrl. Your app should follow the POST/redirect flow described in the Ipay merchant manual (same field names as the REST API).
var enrollment = await _arca.VerifyEnrollmentAsync(new VerifyEnrollmentRequest
{
CardNumber = "4111111111111111",
});
if (enrollment.IsEnrolled == "Y")
{
// proceed with payment and handle ACS if returned
}
Package version vs. documentation
NuGet normalizes package versions. For example 1.55.1.0 and 1.55.1 are the same package identity; the feed and Visual Studio will show 1.55.1. That is expected. Use 1.55.2, a pre-release label, or another distinct version when you need a new published package.
Error handling
Non-success HTTP responses from the gateway are surfaced as InvalidOperationException with the response body as the message. Business outcomes with errorCode in JSON are returned on normal success responses; always check ErrorCode (and gateway-specific fields) on the response models.
Building this library (repository)
From the solart-libraries repo root, use pack.ps1 to set the version at pack time and emit .nupkg files under ./nuget. By default it packs SolartLibraries.slnx (XML solution format).
.\pack.ps1 1.55.2
.\pack.ps1 -Version 1.55.1.0 -Project Solart.Arca.Client\Solart.Arca.Client.csproj
License
This package requires license acceptance. See LICENSE.md for details.
| Product | Versions Compatible and additional computed target framework versions. |
|---|---|
| .NET | net10.0 is compatible. net10.0-android was computed. net10.0-browser was computed. net10.0-ios was computed. net10.0-maccatalyst was computed. net10.0-macos was computed. net10.0-tvos was computed. net10.0-windows was computed. |
-
net10.0
- No dependencies.
NuGet packages
This package is not used by any NuGet packages.
GitHub repositories
This package is not used by any popular GitHub repositories.