From 10051777b61f29f928e356246b34d9de222a6651 Mon Sep 17 00:00:00 2001
From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com>
Date: Wed, 22 Oct 2025 08:03:33 +0000
Subject: [PATCH 1/3] Initial plan
From b8e2263c18fa9d5abbb86f9cbe13341a95bcff18 Mon Sep 17 00:00:00 2001
From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com>
Date: Wed, 22 Oct 2025 08:18:23 +0000
Subject: [PATCH 2/3] Add missing Alliance SDK methods from PHP SDK
Co-authored-by: dampee <1857460+dampee@users.noreply.github.com>
---
.../AddBankAccount/AddBankAccountResult.cs | 16 +
.../API/Alliance/AddBankAccount/Request.cs | 75 ++++
.../Alliance/AddClearing/AddClearingResult.cs | 13 +
PAYNLSDK/API/Alliance/AddClearing/Request.cs | 65 ++++
.../Alliance/AddDocument/AddDocumentResult.cs | 22 ++
PAYNLSDK/API/Alliance/AddDocument/Request.cs | 88 +++++
.../DisablePaymentOptionResult.cs | 13 +
.../Alliance/DisablePaymentOption/Request.cs | 56 +++
.../EnablePaymentOptionResult.cs | 13 +
.../Alliance/EnablePaymentOption/Request.cs | 70 ++++
.../GetAvailablePaymentOptionsResult.cs | 41 +++
.../GetAvailablePaymentOptions/Request.cs | 41 +++
.../GetCategories/GetCategoriesResult.cs | 41 +++
.../API/Alliance/GetCategories/Request.cs | 39 ++
.../GetMerchants/GetMerchantsResult.cs | 41 +++
PAYNLSDK/API/Alliance/GetMerchants/Request.cs | 39 ++
.../API/Alliance/MarkReady/MarkReadyResult.cs | 13 +
PAYNLSDK/API/Alliance/MarkReady/Request.cs | 41 +++
PAYNLSDK/API/Alliance/SetPackage/Request.cs | 54 +++
.../Alliance/SetPackage/SetPackageResult.cs | 13 +
PAYNLSDK/API/Alliance/Suspend/Request.cs | 41 +++
.../API/Alliance/Suspend/SuspendResult.cs | 13 +
PAYNLSDK/API/Alliance/Unsuspend/Request.cs | 41 +++
.../API/Alliance/Unsuspend/UnsuspendResult.cs | 13 +
PAYNLSDK/Alliance.cs | 84 +++++
PAYNLSDK/IAlliance.cs | 84 +++++
PayNLSdk.Tests/AllianceTests.cs | 346 ++++++++++++++++++
27 files changed, 1416 insertions(+)
create mode 100644 PAYNLSDK/API/Alliance/AddBankAccount/AddBankAccountResult.cs
create mode 100644 PAYNLSDK/API/Alliance/AddBankAccount/Request.cs
create mode 100644 PAYNLSDK/API/Alliance/AddClearing/AddClearingResult.cs
create mode 100644 PAYNLSDK/API/Alliance/AddClearing/Request.cs
create mode 100644 PAYNLSDK/API/Alliance/AddDocument/AddDocumentResult.cs
create mode 100644 PAYNLSDK/API/Alliance/AddDocument/Request.cs
create mode 100644 PAYNLSDK/API/Alliance/DisablePaymentOption/DisablePaymentOptionResult.cs
create mode 100644 PAYNLSDK/API/Alliance/DisablePaymentOption/Request.cs
create mode 100644 PAYNLSDK/API/Alliance/EnablePaymentOption/EnablePaymentOptionResult.cs
create mode 100644 PAYNLSDK/API/Alliance/EnablePaymentOption/Request.cs
create mode 100644 PAYNLSDK/API/Alliance/GetAvailablePaymentOptions/GetAvailablePaymentOptionsResult.cs
create mode 100644 PAYNLSDK/API/Alliance/GetAvailablePaymentOptions/Request.cs
create mode 100644 PAYNLSDK/API/Alliance/GetCategories/GetCategoriesResult.cs
create mode 100644 PAYNLSDK/API/Alliance/GetCategories/Request.cs
create mode 100644 PAYNLSDK/API/Alliance/GetMerchants/GetMerchantsResult.cs
create mode 100644 PAYNLSDK/API/Alliance/GetMerchants/Request.cs
create mode 100644 PAYNLSDK/API/Alliance/MarkReady/MarkReadyResult.cs
create mode 100644 PAYNLSDK/API/Alliance/MarkReady/Request.cs
create mode 100644 PAYNLSDK/API/Alliance/SetPackage/Request.cs
create mode 100644 PAYNLSDK/API/Alliance/SetPackage/SetPackageResult.cs
create mode 100644 PAYNLSDK/API/Alliance/Suspend/Request.cs
create mode 100644 PAYNLSDK/API/Alliance/Suspend/SuspendResult.cs
create mode 100644 PAYNLSDK/API/Alliance/Unsuspend/Request.cs
create mode 100644 PAYNLSDK/API/Alliance/Unsuspend/UnsuspendResult.cs
diff --git a/PAYNLSDK/API/Alliance/AddBankAccount/AddBankAccountResult.cs b/PAYNLSDK/API/Alliance/AddBankAccount/AddBankAccountResult.cs
new file mode 100644
index 0000000..6a83a4e
--- /dev/null
+++ b/PAYNLSDK/API/Alliance/AddBankAccount/AddBankAccountResult.cs
@@ -0,0 +1,16 @@
+using Newtonsoft.Json;
+
+namespace PAYNLSDK.API.Alliance.AddBankAccount
+{
+ ///
+ /// Result class for AddBankAccount call
+ ///
+ public class AddBankAccountResult : ResponseBase
+ {
+ ///
+ /// The URL to redirect the user to for iDEAL verification
+ ///
+ [JsonProperty("issuerUrl")]
+ public string IssuerUrl { get; set; }
+ }
+}
diff --git a/PAYNLSDK/API/Alliance/AddBankAccount/Request.cs b/PAYNLSDK/API/Alliance/AddBankAccount/Request.cs
new file mode 100644
index 0000000..db45591
--- /dev/null
+++ b/PAYNLSDK/API/Alliance/AddBankAccount/Request.cs
@@ -0,0 +1,75 @@
+using System.Collections.Specialized;
+using PAYNLSDK.Exceptions;
+using PAYNLSDK.Utilities;
+
+namespace PAYNLSDK.API.Alliance.AddBankAccount
+{
+ ///
+ /// Request to add a bank account for a merchant with iDEAL verification
+ ///
+ public class Request : RequestBase
+ {
+ ///
+ protected override int Version => 7;
+ ///
+ protected override string Controller => "Alliance";
+ ///
+ protected override string Method => "addBankaccount";
+
+ ///
+ /// The merchant ID
+ ///
+ public string MerchantId { get; set; }
+
+ ///
+ /// The URL to redirect the user to after the iDEAL verification is completed
+ ///
+ public string ReturnUrl { get; set; }
+
+ ///
+ /// Optional: the bank ID, if omitted, the user will be asked for the bank
+ ///
+ public string BankId { get; set; }
+
+ ///
+ /// Optional: the ID of the payment profile (standard iDEAL)
+ ///
+ public string PaymentOptionId { get; set; }
+
+ ///
+ public override NameValueCollection GetParameters()
+ {
+ if (ParameterValidator.IsEmpty(MerchantId))
+ {
+ throw new PayNlException("MerchantId is required");
+ }
+ if (ParameterValidator.IsEmpty(ReturnUrl))
+ {
+ throw new PayNlException("ReturnUrl is required");
+ }
+
+ var retval = new NameValueCollection
+ {
+ { "merchantId", MerchantId },
+ { "returnUrl", ReturnUrl }
+ };
+
+ if (!string.IsNullOrEmpty(BankId))
+ {
+ retval.Add("bankId", BankId);
+ }
+ if (!string.IsNullOrEmpty(PaymentOptionId))
+ {
+ retval.Add("paymentOptionId", PaymentOptionId);
+ }
+
+ return retval;
+ }
+
+ ///
+ protected override void PrepareAndSetResponse()
+ {
+ // do nothing
+ }
+ }
+}
diff --git a/PAYNLSDK/API/Alliance/AddClearing/AddClearingResult.cs b/PAYNLSDK/API/Alliance/AddClearing/AddClearingResult.cs
new file mode 100644
index 0000000..a4e0e9e
--- /dev/null
+++ b/PAYNLSDK/API/Alliance/AddClearing/AddClearingResult.cs
@@ -0,0 +1,13 @@
+namespace PAYNLSDK.API.Alliance.AddClearing
+{
+ ///
+ /// Result class for AddClearing call
+ ///
+ public class AddClearingResult : ResponseBase
+ {
+ ///
+ /// Returns true if clearing was successfully added
+ ///
+ public bool Success => Request?.Result == true;
+ }
+}
diff --git a/PAYNLSDK/API/Alliance/AddClearing/Request.cs b/PAYNLSDK/API/Alliance/AddClearing/Request.cs
new file mode 100644
index 0000000..bf041e7
--- /dev/null
+++ b/PAYNLSDK/API/Alliance/AddClearing/Request.cs
@@ -0,0 +1,65 @@
+using System.Collections.Specialized;
+using PAYNLSDK.Exceptions;
+using PAYNLSDK.Utilities;
+
+namespace PAYNLSDK.API.Alliance.AddClearing
+{
+ ///
+ /// Request to add clearing for a merchant
+ ///
+ public class Request : RequestBase
+ {
+ ///
+ protected override int Version => 4;
+ ///
+ protected override string Controller => "Merchant";
+ ///
+ protected override string Method => "addClearing";
+
+ ///
+ /// The amount in cents
+ ///
+ public int Amount { get; set; }
+
+ ///
+ /// The merchant ID (optional)
+ ///
+ public string MerchantId { get; set; }
+
+ ///
+ /// The content category ID (optional)
+ ///
+ public string ContentCategoryId { get; set; }
+
+ ///
+ public override NameValueCollection GetParameters()
+ {
+ if (Amount <= 0)
+ {
+ throw new PayNlException("Amount is required and must be greater than 0");
+ }
+
+ var retval = new NameValueCollection
+ {
+ { "amount", Amount.ToString() }
+ };
+
+ if (!string.IsNullOrEmpty(MerchantId))
+ {
+ retval.Add("merchantId", MerchantId);
+ }
+ if (!string.IsNullOrEmpty(ContentCategoryId))
+ {
+ retval.Add("contentCategoryId", ContentCategoryId);
+ }
+
+ return retval;
+ }
+
+ ///
+ protected override void PrepareAndSetResponse()
+ {
+ // do nothing
+ }
+ }
+}
diff --git a/PAYNLSDK/API/Alliance/AddDocument/AddDocumentResult.cs b/PAYNLSDK/API/Alliance/AddDocument/AddDocumentResult.cs
new file mode 100644
index 0000000..182d55c
--- /dev/null
+++ b/PAYNLSDK/API/Alliance/AddDocument/AddDocumentResult.cs
@@ -0,0 +1,22 @@
+using Newtonsoft.Json;
+
+namespace PAYNLSDK.API.Alliance.AddDocument
+{
+ ///
+ /// Result class for AddDocument call
+ ///
+ public class AddDocumentResult : ResponseBase
+ {
+ ///
+ /// Returns true if document was successfully uploaded
+ ///
+ [JsonProperty("result")]
+ public bool Result { get; set; }
+
+ ///
+ /// Document ID if successful
+ ///
+ [JsonProperty("documentId")]
+ public string DocumentId { get; set; }
+ }
+}
diff --git a/PAYNLSDK/API/Alliance/AddDocument/Request.cs b/PAYNLSDK/API/Alliance/AddDocument/Request.cs
new file mode 100644
index 0000000..cda12a2
--- /dev/null
+++ b/PAYNLSDK/API/Alliance/AddDocument/Request.cs
@@ -0,0 +1,88 @@
+using System;
+using System.Collections.Generic;
+using System.Collections.Specialized;
+using PAYNLSDK.Exceptions;
+using PAYNLSDK.Utilities;
+
+namespace PAYNLSDK.API.Alliance.AddDocument
+{
+ ///
+ /// Request to upload a document
+ ///
+ public class Request : RequestBase
+ {
+ ///
+ protected override int Version => 1;
+ ///
+ protected override string Controller => "Document";
+ ///
+ protected override string Method => "add";
+
+ ///
+ /// The document ID
+ ///
+ public string DocumentId { get; set; }
+
+ ///
+ /// The filename
+ ///
+ public string Filename { get; set; }
+
+ ///
+ /// Base64 encoded document content(s)
+ ///
+ public List Content { get; set; } = new List();
+
+ ///
+ /// Add base64 encoded content
+ ///
+ /// Base64 encoded document content
+ public void AddContent(string base64Content)
+ {
+ Content.Add(base64Content);
+ }
+
+ ///
+ public override NameValueCollection GetParameters()
+ {
+ if (ParameterValidator.IsEmpty(DocumentId))
+ {
+ throw new PayNlException("DocumentId is required");
+ }
+ if (ParameterValidator.IsEmpty(Filename))
+ {
+ throw new PayNlException("Filename is required");
+ }
+ if (Content == null || Content.Count == 0)
+ {
+ throw new PayNlException("Content is required");
+ }
+
+ var retval = new NameValueCollection
+ {
+ { "documentId", DocumentId },
+ { "filename", Filename }
+ };
+
+ if (Content.Count == 1)
+ {
+ retval.Add("documentFile", Content[0]);
+ }
+ else
+ {
+ for (int i = 0; i < Content.Count; i++)
+ {
+ retval.Add($"documentFile[{i}]", Content[i]);
+ }
+ }
+
+ return retval;
+ }
+
+ ///
+ protected override void PrepareAndSetResponse()
+ {
+ // do nothing
+ }
+ }
+}
diff --git a/PAYNLSDK/API/Alliance/DisablePaymentOption/DisablePaymentOptionResult.cs b/PAYNLSDK/API/Alliance/DisablePaymentOption/DisablePaymentOptionResult.cs
new file mode 100644
index 0000000..874b09e
--- /dev/null
+++ b/PAYNLSDK/API/Alliance/DisablePaymentOption/DisablePaymentOptionResult.cs
@@ -0,0 +1,13 @@
+namespace PAYNLSDK.API.Alliance.DisablePaymentOption
+{
+ ///
+ /// Result class for DisablePaymentOption call
+ ///
+ public class DisablePaymentOptionResult : ResponseBase
+ {
+ ///
+ /// Returns true if the payment option was successfully disabled
+ ///
+ public bool Success => Request?.Result == true;
+ }
+}
diff --git a/PAYNLSDK/API/Alliance/DisablePaymentOption/Request.cs b/PAYNLSDK/API/Alliance/DisablePaymentOption/Request.cs
new file mode 100644
index 0000000..3335fe5
--- /dev/null
+++ b/PAYNLSDK/API/Alliance/DisablePaymentOption/Request.cs
@@ -0,0 +1,56 @@
+using System.Collections.Specialized;
+using PAYNLSDK.Exceptions;
+using PAYNLSDK.Utilities;
+
+namespace PAYNLSDK.API.Alliance.DisablePaymentOption
+{
+ ///
+ /// Request to disable a payment option for a service
+ ///
+ public class Request : RequestBase
+ {
+ ///
+ protected override int Version => 4;
+ ///
+ protected override string Controller => "Service";
+ ///
+ protected override string Method => "disablePaymentOption";
+
+ ///
+ /// The service ID
+ ///
+ public string ServiceId { get; set; }
+
+ ///
+ /// The payment profile ID (payment method ID)
+ ///
+ public string PaymentProfileId { get; set; }
+
+ ///
+ public override NameValueCollection GetParameters()
+ {
+ if (ParameterValidator.IsEmpty(ServiceId))
+ {
+ throw new PayNlException("ServiceId is required");
+ }
+ if (ParameterValidator.IsEmpty(PaymentProfileId))
+ {
+ throw new PayNlException("PaymentProfileId is required");
+ }
+
+ var retval = new NameValueCollection
+ {
+ { "serviceId", ServiceId },
+ { "paymentProfileId", PaymentProfileId }
+ };
+
+ return retval;
+ }
+
+ ///
+ protected override void PrepareAndSetResponse()
+ {
+ // do nothing
+ }
+ }
+}
diff --git a/PAYNLSDK/API/Alliance/EnablePaymentOption/EnablePaymentOptionResult.cs b/PAYNLSDK/API/Alliance/EnablePaymentOption/EnablePaymentOptionResult.cs
new file mode 100644
index 0000000..8d35d2a
--- /dev/null
+++ b/PAYNLSDK/API/Alliance/EnablePaymentOption/EnablePaymentOptionResult.cs
@@ -0,0 +1,13 @@
+namespace PAYNLSDK.API.Alliance.EnablePaymentOption
+{
+ ///
+ /// Result class for EnablePaymentOption call
+ ///
+ public class EnablePaymentOptionResult : ResponseBase
+ {
+ ///
+ /// Returns true if the payment option was successfully enabled
+ ///
+ public bool Success => Request?.Result == true;
+ }
+}
diff --git a/PAYNLSDK/API/Alliance/EnablePaymentOption/Request.cs b/PAYNLSDK/API/Alliance/EnablePaymentOption/Request.cs
new file mode 100644
index 0000000..81f473b
--- /dev/null
+++ b/PAYNLSDK/API/Alliance/EnablePaymentOption/Request.cs
@@ -0,0 +1,70 @@
+using System.Collections.Generic;
+using System.Collections.Specialized;
+using PAYNLSDK.Exceptions;
+using PAYNLSDK.Utilities;
+
+namespace PAYNLSDK.API.Alliance.EnablePaymentOption
+{
+ ///
+ /// Request to enable a payment option for a service
+ ///
+ public class Request : RequestBase
+ {
+ ///
+ protected override int Version => 4;
+ ///
+ protected override string Controller => "Service";
+ ///
+ protected override string Method => "enablePaymentOption";
+
+ ///
+ /// The service ID
+ ///
+ public string ServiceId { get; set; }
+
+ ///
+ /// The payment profile ID (payment method ID)
+ ///
+ public string PaymentProfileId { get; set; }
+
+ ///
+ /// Optional: settings for the payment option
+ ///
+ public Dictionary Settings { get; set; }
+
+ ///
+ public override NameValueCollection GetParameters()
+ {
+ if (ParameterValidator.IsEmpty(ServiceId))
+ {
+ throw new PayNlException("ServiceId is required");
+ }
+ if (ParameterValidator.IsEmpty(PaymentProfileId))
+ {
+ throw new PayNlException("PaymentProfileId is required");
+ }
+
+ var retval = new NameValueCollection
+ {
+ { "serviceId", ServiceId },
+ { "paymentProfileId", PaymentProfileId }
+ };
+
+ if (Settings != null && Settings.Count > 0)
+ {
+ foreach (var setting in Settings)
+ {
+ retval.Add($"settings[{setting.Key}]", setting.Value);
+ }
+ }
+
+ return retval;
+ }
+
+ ///
+ protected override void PrepareAndSetResponse()
+ {
+ // do nothing
+ }
+ }
+}
diff --git a/PAYNLSDK/API/Alliance/GetAvailablePaymentOptions/GetAvailablePaymentOptionsResult.cs b/PAYNLSDK/API/Alliance/GetAvailablePaymentOptions/GetAvailablePaymentOptionsResult.cs
new file mode 100644
index 0000000..06ba20c
--- /dev/null
+++ b/PAYNLSDK/API/Alliance/GetAvailablePaymentOptions/GetAvailablePaymentOptionsResult.cs
@@ -0,0 +1,41 @@
+using System.Collections.Generic;
+using Newtonsoft.Json;
+
+namespace PAYNLSDK.API.Alliance.GetAvailablePaymentOptions
+{
+ ///
+ /// Result class for GetAvailablePaymentOptions call
+ ///
+ public class GetAvailablePaymentOptionsResult : ResponseBase
+ {
+ ///
+ /// List of available payment options
+ ///
+ [JsonProperty("paymentOptions")]
+ public List PaymentOptions { get; set; } = new List();
+ }
+
+ ///
+ /// Payment option information
+ ///
+ public class PaymentOption
+ {
+ ///
+ /// Payment option ID
+ ///
+ [JsonProperty("id")]
+ public string Id { get; set; }
+
+ ///
+ /// Payment option name
+ ///
+ [JsonProperty("name")]
+ public string Name { get; set; }
+
+ ///
+ /// Whether the payment option is enabled
+ ///
+ [JsonProperty("enabled")]
+ public bool Enabled { get; set; }
+ }
+}
diff --git a/PAYNLSDK/API/Alliance/GetAvailablePaymentOptions/Request.cs b/PAYNLSDK/API/Alliance/GetAvailablePaymentOptions/Request.cs
new file mode 100644
index 0000000..aa0885c
--- /dev/null
+++ b/PAYNLSDK/API/Alliance/GetAvailablePaymentOptions/Request.cs
@@ -0,0 +1,41 @@
+using System.Collections.Specialized;
+using PAYNLSDK.Exceptions;
+using PAYNLSDK.Utilities;
+
+namespace PAYNLSDK.API.Alliance.GetAvailablePaymentOptions
+{
+ ///
+ /// Request to get available payment options for a service
+ ///
+ public class Request : RequestBase
+ {
+ ///
+ protected override int Version => 4;
+ ///
+ protected override string Controller => "Service";
+ ///
+ protected override string Method => "getAvailablePaymentOptions";
+
+ ///
+ /// The service ID
+ ///
+ public string ServiceId { get; set; }
+
+ ///
+ public override NameValueCollection GetParameters()
+ {
+ if (ParameterValidator.IsEmpty(ServiceId))
+ {
+ throw new PayNlException("ServiceId is required");
+ }
+ var retval = new NameValueCollection { { "serviceId", ServiceId } };
+ return retval;
+ }
+
+ ///
+ protected override void PrepareAndSetResponse()
+ {
+ // do nothing
+ }
+ }
+}
diff --git a/PAYNLSDK/API/Alliance/GetCategories/GetCategoriesResult.cs b/PAYNLSDK/API/Alliance/GetCategories/GetCategoriesResult.cs
new file mode 100644
index 0000000..d8d0a0b
--- /dev/null
+++ b/PAYNLSDK/API/Alliance/GetCategories/GetCategoriesResult.cs
@@ -0,0 +1,41 @@
+using System.Collections.Generic;
+using Newtonsoft.Json;
+
+namespace PAYNLSDK.API.Alliance.GetCategories
+{
+ ///
+ /// Result class for GetCategories call
+ ///
+ public class GetCategoriesResult : ResponseBase
+ {
+ ///
+ /// List of categories
+ ///
+ [JsonProperty("categories")]
+ public List Categories { get; set; } = new List();
+ }
+
+ ///
+ /// Category information
+ ///
+ public class Category
+ {
+ ///
+ /// Category ID
+ ///
+ [JsonProperty("id")]
+ public string Id { get; set; }
+
+ ///
+ /// Category name
+ ///
+ [JsonProperty("name")]
+ public string Name { get; set; }
+
+ ///
+ /// Category description
+ ///
+ [JsonProperty("description")]
+ public string Description { get; set; }
+ }
+}
diff --git a/PAYNLSDK/API/Alliance/GetCategories/Request.cs b/PAYNLSDK/API/Alliance/GetCategories/Request.cs
new file mode 100644
index 0000000..3574ed9
--- /dev/null
+++ b/PAYNLSDK/API/Alliance/GetCategories/Request.cs
@@ -0,0 +1,39 @@
+using System.Collections.Specialized;
+
+namespace PAYNLSDK.API.Alliance.GetCategories
+{
+ ///
+ /// Request to get website categories
+ ///
+ public class Request : RequestBase
+ {
+ ///
+ protected override int Version => 4;
+ ///
+ protected override string Controller => "Service";
+ ///
+ protected override string Method => "getCategories";
+
+ ///
+ /// Optional: filter by payment option ID
+ ///
+ public string PaymentOptionId { get; set; }
+
+ ///
+ public override NameValueCollection GetParameters()
+ {
+ var retval = new NameValueCollection();
+ if (!string.IsNullOrEmpty(PaymentOptionId))
+ {
+ retval.Add("paymentOptionId", PaymentOptionId);
+ }
+ return retval;
+ }
+
+ ///
+ protected override void PrepareAndSetResponse()
+ {
+ // do nothing
+ }
+ }
+}
diff --git a/PAYNLSDK/API/Alliance/GetMerchants/GetMerchantsResult.cs b/PAYNLSDK/API/Alliance/GetMerchants/GetMerchantsResult.cs
new file mode 100644
index 0000000..14788d4
--- /dev/null
+++ b/PAYNLSDK/API/Alliance/GetMerchants/GetMerchantsResult.cs
@@ -0,0 +1,41 @@
+using System.Collections.Generic;
+using Newtonsoft.Json;
+
+namespace PAYNLSDK.API.Alliance.GetMerchants
+{
+ ///
+ /// Result class for GetMerchants call
+ ///
+ public class GetMerchantsResult : ResponseBase
+ {
+ ///
+ /// List of merchants
+ ///
+ [JsonProperty("merchants")]
+ public List Merchants { get; set; } = new List();
+ }
+
+ ///
+ /// Merchant information
+ ///
+ public class MerchantInfo
+ {
+ ///
+ /// Merchant ID
+ ///
+ [JsonProperty("merchantId")]
+ public string MerchantId { get; set; }
+
+ ///
+ /// Merchant name
+ ///
+ [JsonProperty("merchantName")]
+ public string MerchantName { get; set; }
+
+ ///
+ /// Merchant state
+ ///
+ [JsonProperty("state")]
+ public string State { get; set; }
+ }
+}
diff --git a/PAYNLSDK/API/Alliance/GetMerchants/Request.cs b/PAYNLSDK/API/Alliance/GetMerchants/Request.cs
new file mode 100644
index 0000000..6093ac1
--- /dev/null
+++ b/PAYNLSDK/API/Alliance/GetMerchants/Request.cs
@@ -0,0 +1,39 @@
+using System.Collections.Specialized;
+
+namespace PAYNLSDK.API.Alliance.GetMerchants
+{
+ ///
+ /// Request to get a list of merchants
+ ///
+ public class Request : RequestBase
+ {
+ ///
+ protected override int Version => 7;
+ ///
+ protected override string Controller => "Alliance";
+ ///
+ protected override string Method => "getMerchants";
+
+ ///
+ /// Filter by state: new, accepted or deleted
+ ///
+ public string State { get; set; }
+
+ ///
+ public override NameValueCollection GetParameters()
+ {
+ var retval = new NameValueCollection();
+ if (!string.IsNullOrEmpty(State))
+ {
+ retval.Add("state", State);
+ }
+ return retval;
+ }
+
+ ///
+ protected override void PrepareAndSetResponse()
+ {
+ // do nothing
+ }
+ }
+}
diff --git a/PAYNLSDK/API/Alliance/MarkReady/MarkReadyResult.cs b/PAYNLSDK/API/Alliance/MarkReady/MarkReadyResult.cs
new file mode 100644
index 0000000..bf2cb5c
--- /dev/null
+++ b/PAYNLSDK/API/Alliance/MarkReady/MarkReadyResult.cs
@@ -0,0 +1,13 @@
+namespace PAYNLSDK.API.Alliance.MarkReady
+{
+ ///
+ /// Result class for MarkReady call
+ ///
+ public class MarkReadyResult : ResponseBase
+ {
+ ///
+ /// Returns true if the merchant was successfully marked as ready
+ ///
+ public bool Success => Request?.Result == true;
+ }
+}
diff --git a/PAYNLSDK/API/Alliance/MarkReady/Request.cs b/PAYNLSDK/API/Alliance/MarkReady/Request.cs
new file mode 100644
index 0000000..4cfc539
--- /dev/null
+++ b/PAYNLSDK/API/Alliance/MarkReady/Request.cs
@@ -0,0 +1,41 @@
+using System.Collections.Specialized;
+using PAYNLSDK.Exceptions;
+using PAYNLSDK.Utilities;
+
+namespace PAYNLSDK.API.Alliance.MarkReady
+{
+ ///
+ /// Request to mark a merchant as ready
+ ///
+ public class Request : RequestBase
+ {
+ ///
+ protected override int Version => 4;
+ ///
+ protected override string Controller => "Merchant";
+ ///
+ protected override string Method => "markReady";
+
+ ///
+ /// The merchant ID to mark as ready
+ ///
+ public string MerchantId { get; set; }
+
+ ///
+ public override NameValueCollection GetParameters()
+ {
+ if (ParameterValidator.IsEmpty(MerchantId))
+ {
+ throw new PayNlException("MerchantId is required");
+ }
+ var retval = new NameValueCollection { { "merchantId", MerchantId } };
+ return retval;
+ }
+
+ ///
+ protected override void PrepareAndSetResponse()
+ {
+ // do nothing
+ }
+ }
+}
diff --git a/PAYNLSDK/API/Alliance/SetPackage/Request.cs b/PAYNLSDK/API/Alliance/SetPackage/Request.cs
new file mode 100644
index 0000000..fbe9bcb
--- /dev/null
+++ b/PAYNLSDK/API/Alliance/SetPackage/Request.cs
@@ -0,0 +1,54 @@
+using System.Collections.Specialized;
+using PAYNLSDK.Exceptions;
+using PAYNLSDK.Utilities;
+
+namespace PAYNLSDK.API.Alliance.SetPackage
+{
+ ///
+ /// Request to set package for a merchant
+ ///
+ public class Request : RequestBase
+ {
+ ///
+ protected override int Version => 7;
+ ///
+ protected override string Controller => "Alliance";
+ ///
+ protected override string Method => "setPackage";
+
+ ///
+ /// The merchant ID
+ ///
+ public string MerchantId { get; set; }
+
+ ///
+ /// The package name (e.g. "Alliance" or "AlliancePlus")
+ ///
+ public string Package { get; set; }
+
+ ///
+ public override NameValueCollection GetParameters()
+ {
+ if (ParameterValidator.IsEmpty(MerchantId))
+ {
+ throw new PayNlException("MerchantId is required");
+ }
+ if (ParameterValidator.IsEmpty(Package))
+ {
+ throw new PayNlException("Package is required");
+ }
+ var retval = new NameValueCollection
+ {
+ { "merchantId", MerchantId },
+ { "package", Package }
+ };
+ return retval;
+ }
+
+ ///
+ protected override void PrepareAndSetResponse()
+ {
+ // do nothing
+ }
+ }
+}
diff --git a/PAYNLSDK/API/Alliance/SetPackage/SetPackageResult.cs b/PAYNLSDK/API/Alliance/SetPackage/SetPackageResult.cs
new file mode 100644
index 0000000..76a2617
--- /dev/null
+++ b/PAYNLSDK/API/Alliance/SetPackage/SetPackageResult.cs
@@ -0,0 +1,13 @@
+namespace PAYNLSDK.API.Alliance.SetPackage
+{
+ ///
+ /// Result class for SetPackage call
+ ///
+ public class SetPackageResult : ResponseBase
+ {
+ ///
+ /// Returns true if the package was successfully set
+ ///
+ public bool Success => Request?.Result == true;
+ }
+}
diff --git a/PAYNLSDK/API/Alliance/Suspend/Request.cs b/PAYNLSDK/API/Alliance/Suspend/Request.cs
new file mode 100644
index 0000000..18bb7dc
--- /dev/null
+++ b/PAYNLSDK/API/Alliance/Suspend/Request.cs
@@ -0,0 +1,41 @@
+using System.Collections.Specialized;
+using PAYNLSDK.Exceptions;
+using PAYNLSDK.Utilities;
+
+namespace PAYNLSDK.API.Alliance.Suspend
+{
+ ///
+ /// Request to suspend a merchant
+ ///
+ public class Request : RequestBase
+ {
+ ///
+ protected override int Version => 7;
+ ///
+ protected override string Controller => "Alliance";
+ ///
+ protected override string Method => "suspend";
+
+ ///
+ /// The merchant ID to suspend
+ ///
+ public string MerchantId { get; set; }
+
+ ///
+ public override NameValueCollection GetParameters()
+ {
+ if (ParameterValidator.IsEmpty(MerchantId))
+ {
+ throw new PayNlException("MerchantId is required");
+ }
+ var retval = new NameValueCollection { { "merchantId", MerchantId } };
+ return retval;
+ }
+
+ ///
+ protected override void PrepareAndSetResponse()
+ {
+ // do nothing
+ }
+ }
+}
diff --git a/PAYNLSDK/API/Alliance/Suspend/SuspendResult.cs b/PAYNLSDK/API/Alliance/Suspend/SuspendResult.cs
new file mode 100644
index 0000000..77fa2db
--- /dev/null
+++ b/PAYNLSDK/API/Alliance/Suspend/SuspendResult.cs
@@ -0,0 +1,13 @@
+namespace PAYNLSDK.API.Alliance.Suspend
+{
+ ///
+ /// Result class for Suspend call
+ ///
+ public class SuspendResult : ResponseBase
+ {
+ ///
+ /// Returns true if the merchant was successfully suspended
+ ///
+ public bool Success => Request?.Result == true;
+ }
+}
diff --git a/PAYNLSDK/API/Alliance/Unsuspend/Request.cs b/PAYNLSDK/API/Alliance/Unsuspend/Request.cs
new file mode 100644
index 0000000..aef8071
--- /dev/null
+++ b/PAYNLSDK/API/Alliance/Unsuspend/Request.cs
@@ -0,0 +1,41 @@
+using System.Collections.Specialized;
+using PAYNLSDK.Exceptions;
+using PAYNLSDK.Utilities;
+
+namespace PAYNLSDK.API.Alliance.Unsuspend
+{
+ ///
+ /// Request to unsuspend a merchant
+ ///
+ public class Request : RequestBase
+ {
+ ///
+ protected override int Version => 7;
+ ///
+ protected override string Controller => "Alliance";
+ ///
+ protected override string Method => "unsuspend";
+
+ ///
+ /// The merchant ID to unsuspend
+ ///
+ public string MerchantId { get; set; }
+
+ ///
+ public override NameValueCollection GetParameters()
+ {
+ if (ParameterValidator.IsEmpty(MerchantId))
+ {
+ throw new PayNlException("MerchantId is required");
+ }
+ var retval = new NameValueCollection { { "merchantId", MerchantId } };
+ return retval;
+ }
+
+ ///
+ protected override void PrepareAndSetResponse()
+ {
+ // do nothing
+ }
+ }
+}
diff --git a/PAYNLSDK/API/Alliance/Unsuspend/UnsuspendResult.cs b/PAYNLSDK/API/Alliance/Unsuspend/UnsuspendResult.cs
new file mode 100644
index 0000000..d6fc91c
--- /dev/null
+++ b/PAYNLSDK/API/Alliance/Unsuspend/UnsuspendResult.cs
@@ -0,0 +1,13 @@
+namespace PAYNLSDK.API.Alliance.Unsuspend
+{
+ ///
+ /// Result class for Unsuspend call
+ ///
+ public class UnsuspendResult : ResponseBase
+ {
+ ///
+ /// Returns true if the merchant was successfully unsuspended
+ ///
+ public bool Success => Request?.Result == true;
+ }
+}
diff --git a/PAYNLSDK/Alliance.cs b/PAYNLSDK/Alliance.cs
index f986c74..f175db6 100644
--- a/PAYNLSDK/Alliance.cs
+++ b/PAYNLSDK/Alliance.cs
@@ -47,5 +47,89 @@ public API.Alliance.AddInvoice.AddInvoiceResult AddInvoice(API.Alliance.AddInvoi
var response = _webClient.PerformRequest(request);
return Newtonsoft.Json.JsonConvert.DeserializeObject(response);
}
+
+ ///
+ public API.Alliance.GetMerchants.GetMerchantsResult GetMerchants(API.Alliance.GetMerchants.Request request)
+ {
+ var response = _webClient.PerformRequest(request);
+ return Newtonsoft.Json.JsonConvert.DeserializeObject(response);
+ }
+
+ ///
+ public API.Alliance.Suspend.SuspendResult Suspend(API.Alliance.Suspend.Request request)
+ {
+ var response = _webClient.PerformRequest(request);
+ return Newtonsoft.Json.JsonConvert.DeserializeObject(response);
+ }
+
+ ///
+ public API.Alliance.Unsuspend.UnsuspendResult Unsuspend(API.Alliance.Unsuspend.Request request)
+ {
+ var response = _webClient.PerformRequest(request);
+ return Newtonsoft.Json.JsonConvert.DeserializeObject(response);
+ }
+
+ ///
+ public API.Alliance.SetPackage.SetPackageResult SetPackage(API.Alliance.SetPackage.Request request)
+ {
+ var response = _webClient.PerformRequest(request);
+ return Newtonsoft.Json.JsonConvert.DeserializeObject(response);
+ }
+
+ ///
+ public API.Alliance.MarkReady.MarkReadyResult MarkReady(API.Alliance.MarkReady.Request request)
+ {
+ var response = _webClient.PerformRequest(request);
+ return Newtonsoft.Json.JsonConvert.DeserializeObject(response);
+ }
+
+ ///
+ public API.Alliance.AddClearing.AddClearingResult AddClearing(API.Alliance.AddClearing.Request request)
+ {
+ var response = _webClient.PerformRequest(request);
+ return Newtonsoft.Json.JsonConvert.DeserializeObject(response);
+ }
+
+ ///
+ public API.Alliance.AddBankAccount.AddBankAccountResult AddBankAccount(API.Alliance.AddBankAccount.Request request)
+ {
+ var response = _webClient.PerformRequest(request);
+ return Newtonsoft.Json.JsonConvert.DeserializeObject(response);
+ }
+
+ ///
+ public API.Alliance.GetCategories.GetCategoriesResult GetCategories(API.Alliance.GetCategories.Request request)
+ {
+ var response = _webClient.PerformRequest(request);
+ return Newtonsoft.Json.JsonConvert.DeserializeObject(response);
+ }
+
+ ///
+ public API.Alliance.GetAvailablePaymentOptions.GetAvailablePaymentOptionsResult GetAvailablePaymentOptions(API.Alliance.GetAvailablePaymentOptions.Request request)
+ {
+ var response = _webClient.PerformRequest(request);
+ return Newtonsoft.Json.JsonConvert.DeserializeObject(response);
+ }
+
+ ///
+ public API.Alliance.EnablePaymentOption.EnablePaymentOptionResult EnablePaymentOption(API.Alliance.EnablePaymentOption.Request request)
+ {
+ var response = _webClient.PerformRequest(request);
+ return Newtonsoft.Json.JsonConvert.DeserializeObject(response);
+ }
+
+ ///
+ public API.Alliance.DisablePaymentOption.DisablePaymentOptionResult DisablePaymentOption(API.Alliance.DisablePaymentOption.Request request)
+ {
+ var response = _webClient.PerformRequest(request);
+ return Newtonsoft.Json.JsonConvert.DeserializeObject(response);
+ }
+
+ ///
+ public API.Alliance.AddDocument.AddDocumentResult AddDocument(API.Alliance.AddDocument.Request request)
+ {
+ var response = _webClient.PerformRequest(request);
+ return Newtonsoft.Json.JsonConvert.DeserializeObject(response);
+ }
}
}
diff --git a/PAYNLSDK/IAlliance.cs b/PAYNLSDK/IAlliance.cs
index a7131de..03ddabb 100644
--- a/PAYNLSDK/IAlliance.cs
+++ b/PAYNLSDK/IAlliance.cs
@@ -32,5 +32,89 @@ public interface IAlliance
/// The request.
/// API.Alliance.AddInvoice.AddInvoiceResult.
API.Alliance.AddInvoice.AddInvoiceResult AddInvoice(API.Alliance.AddInvoice.Request request);
+
+ ///
+ /// Get a list of merchants
+ ///
+ /// The request.
+ /// API.Alliance.GetMerchants.GetMerchantsResult.
+ API.Alliance.GetMerchants.GetMerchantsResult GetMerchants(API.Alliance.GetMerchants.Request request);
+
+ ///
+ /// Suspend a merchant
+ ///
+ /// The request.
+ /// API.Alliance.Suspend.SuspendResult.
+ API.Alliance.Suspend.SuspendResult Suspend(API.Alliance.Suspend.Request request);
+
+ ///
+ /// Unsuspend a merchant
+ ///
+ /// The request.
+ /// API.Alliance.Unsuspend.UnsuspendResult.
+ API.Alliance.Unsuspend.UnsuspendResult Unsuspend(API.Alliance.Unsuspend.Request request);
+
+ ///
+ /// Set package for a merchant
+ ///
+ /// The request.
+ /// API.Alliance.SetPackage.SetPackageResult.
+ API.Alliance.SetPackage.SetPackageResult SetPackage(API.Alliance.SetPackage.Request request);
+
+ ///
+ /// Mark a merchant as ready
+ ///
+ /// The request.
+ /// API.Alliance.MarkReady.MarkReadyResult.
+ API.Alliance.MarkReady.MarkReadyResult MarkReady(API.Alliance.MarkReady.Request request);
+
+ ///
+ /// Add clearing for a merchant
+ ///
+ /// The request.
+ /// API.Alliance.AddClearing.AddClearingResult.
+ API.Alliance.AddClearing.AddClearingResult AddClearing(API.Alliance.AddClearing.Request request);
+
+ ///
+ /// Add bank account for a merchant with iDEAL verification
+ ///
+ /// The request.
+ /// API.Alliance.AddBankAccount.AddBankAccountResult.
+ API.Alliance.AddBankAccount.AddBankAccountResult AddBankAccount(API.Alliance.AddBankAccount.Request request);
+
+ ///
+ /// Get website categories
+ ///
+ /// The request.
+ /// API.Alliance.GetCategories.GetCategoriesResult.
+ API.Alliance.GetCategories.GetCategoriesResult GetCategories(API.Alliance.GetCategories.Request request);
+
+ ///
+ /// Get available payment options for a service
+ ///
+ /// The request.
+ /// API.Alliance.GetAvailablePaymentOptions.GetAvailablePaymentOptionsResult.
+ API.Alliance.GetAvailablePaymentOptions.GetAvailablePaymentOptionsResult GetAvailablePaymentOptions(API.Alliance.GetAvailablePaymentOptions.Request request);
+
+ ///
+ /// Enable a payment option for a service
+ ///
+ /// The request.
+ /// API.Alliance.EnablePaymentOption.EnablePaymentOptionResult.
+ API.Alliance.EnablePaymentOption.EnablePaymentOptionResult EnablePaymentOption(API.Alliance.EnablePaymentOption.Request request);
+
+ ///
+ /// Disable a payment option for a service
+ ///
+ /// The request.
+ /// API.Alliance.DisablePaymentOption.DisablePaymentOptionResult.
+ API.Alliance.DisablePaymentOption.DisablePaymentOptionResult DisablePaymentOption(API.Alliance.DisablePaymentOption.Request request);
+
+ ///
+ /// Upload a document
+ ///
+ /// The request.
+ /// API.Alliance.AddDocument.AddDocumentResult.
+ API.Alliance.AddDocument.AddDocumentResult AddDocument(API.Alliance.AddDocument.Request request);
}
}
diff --git a/PayNLSdk.Tests/AllianceTests.cs b/PayNLSdk.Tests/AllianceTests.cs
index 18af285..1a0f2c9 100644
--- a/PayNLSdk.Tests/AllianceTests.cs
+++ b/PayNLSdk.Tests/AllianceTests.cs
@@ -123,6 +123,352 @@ public void AddInvoice_ShouldReturnReferenceId()
result.ToString().ShouldContain("INV-1");
}
+ [Fact]
+ public void GetMerchants_ShouldReturnListOfMerchants()
+ {
+ // Arrange
+ var rawResponse = """
+ {
+ "request": {
+ "result": true,
+ "errorId": null,
+ "errorMessage": null
+ },
+ "merchants": [
+ {
+ "merchantId": "M-1",
+ "merchantName": "Merchant One",
+ "state": "accepted"
+ },
+ {
+ "merchantId": "M-2",
+ "merchantName": "Merchant Two",
+ "state": "new"
+ }
+ ]
+ }
+ """;
+ var client = CreateClient(rawResponse);
+ var alliance = new Alliance(client);
+
+ // Act
+ var result = alliance.GetMerchants(new PAYNLSDK.API.Alliance.GetMerchants.Request());
+
+ // Assert
+ result.Merchants.Count.ShouldBe(2);
+ result.Merchants[0].MerchantId.ShouldBe("M-1");
+ result.Merchants[0].MerchantName.ShouldBe("Merchant One");
+ result.Merchants[0].State.ShouldBe("accepted");
+ }
+
+ [Fact]
+ public void Suspend_ShouldReturnSuccess()
+ {
+ // Arrange
+ var rawResponse = """
+ {
+ "request": {
+ "result": true,
+ "errorId": null,
+ "errorMessage": null
+ }
+ }
+ """;
+ var client = CreateClient(rawResponse);
+ var alliance = new Alliance(client);
+
+ // Act
+ var result = alliance.Suspend(new PAYNLSDK.API.Alliance.Suspend.Request { MerchantId = "M-4" });
+
+ // Assert
+ result.Success.ShouldBeTrue();
+ }
+
+ [Fact]
+ public void Unsuspend_ShouldReturnSuccess()
+ {
+ // Arrange
+ var rawResponse = """
+ {
+ "request": {
+ "result": true,
+ "errorId": null,
+ "errorMessage": null
+ }
+ }
+ """;
+ var client = CreateClient(rawResponse);
+ var alliance = new Alliance(client);
+
+ // Act
+ var result = alliance.Unsuspend(new PAYNLSDK.API.Alliance.Unsuspend.Request { MerchantId = "M-4" });
+
+ // Assert
+ result.Success.ShouldBeTrue();
+ }
+
+ [Fact]
+ public void SetPackage_ShouldReturnSuccess()
+ {
+ // Arrange
+ var rawResponse = """
+ {
+ "request": {
+ "result": true,
+ "errorId": null,
+ "errorMessage": null
+ }
+ }
+ """;
+ var client = CreateClient(rawResponse);
+ var alliance = new Alliance(client);
+
+ // Act
+ var result = alliance.SetPackage(new PAYNLSDK.API.Alliance.SetPackage.Request
+ {
+ MerchantId = "M-4",
+ Package = "AlliancePlus"
+ });
+
+ // Assert
+ result.Success.ShouldBeTrue();
+ }
+
+ [Fact]
+ public void MarkReady_ShouldReturnSuccess()
+ {
+ // Arrange
+ var rawResponse = """
+ {
+ "request": {
+ "result": true,
+ "errorId": null,
+ "errorMessage": null
+ }
+ }
+ """;
+ var client = CreateClient(rawResponse);
+ var alliance = new Alliance(client);
+
+ // Act
+ var result = alliance.MarkReady(new PAYNLSDK.API.Alliance.MarkReady.Request { MerchantId = "M-4" });
+
+ // Assert
+ result.Success.ShouldBeTrue();
+ }
+
+ [Fact]
+ public void AddClearing_ShouldReturnSuccess()
+ {
+ // Arrange
+ var rawResponse = """
+ {
+ "request": {
+ "result": true,
+ "errorId": null,
+ "errorMessage": null
+ }
+ }
+ """;
+ var client = CreateClient(rawResponse);
+ var alliance = new Alliance(client);
+
+ // Act
+ var result = alliance.AddClearing(new PAYNLSDK.API.Alliance.AddClearing.Request
+ {
+ Amount = 1000,
+ MerchantId = "M-4"
+ });
+
+ // Assert
+ result.Success.ShouldBeTrue();
+ }
+
+ [Fact]
+ public void AddBankAccount_ShouldReturnIssuerUrl()
+ {
+ // Arrange
+ var rawResponse = """
+ {
+ "request": {
+ "result": true,
+ "errorId": null,
+ "errorMessage": null
+ },
+ "issuerUrl": "https://example.com/ideal"
+ }
+ """;
+ var client = CreateClient(rawResponse);
+ var alliance = new Alliance(client);
+
+ // Act
+ var result = alliance.AddBankAccount(new PAYNLSDK.API.Alliance.AddBankAccount.Request
+ {
+ MerchantId = "M-4",
+ ReturnUrl = "https://example.com/return"
+ });
+
+ // Assert
+ result.IssuerUrl.ShouldBe("https://example.com/ideal");
+ }
+
+ [Fact]
+ public void GetCategories_ShouldReturnListOfCategories()
+ {
+ // Arrange
+ var rawResponse = """
+ {
+ "request": {
+ "result": true,
+ "errorId": null,
+ "errorMessage": null
+ },
+ "categories": [
+ {
+ "id": "1",
+ "name": "Category 1",
+ "description": "Description 1"
+ },
+ {
+ "id": "2",
+ "name": "Category 2",
+ "description": "Description 2"
+ }
+ ]
+ }
+ """;
+ var client = CreateClient(rawResponse);
+ var alliance = new Alliance(client);
+
+ // Act
+ var result = alliance.GetCategories(new PAYNLSDK.API.Alliance.GetCategories.Request());
+
+ // Assert
+ result.Categories.Count.ShouldBe(2);
+ result.Categories[0].Id.ShouldBe("1");
+ result.Categories[0].Name.ShouldBe("Category 1");
+ }
+
+ [Fact]
+ public void GetAvailablePaymentOptions_ShouldReturnListOfOptions()
+ {
+ // Arrange
+ var rawResponse = """
+ {
+ "request": {
+ "result": true,
+ "errorId": null,
+ "errorMessage": null
+ },
+ "paymentOptions": [
+ {
+ "id": "10",
+ "name": "iDEAL",
+ "enabled": true
+ },
+ {
+ "id": "436",
+ "name": "Bancontact",
+ "enabled": false
+ }
+ ]
+ }
+ """;
+ var client = CreateClient(rawResponse);
+ var alliance = new Alliance(client);
+
+ // Act
+ var result = alliance.GetAvailablePaymentOptions(
+ new PAYNLSDK.API.Alliance.GetAvailablePaymentOptions.Request { ServiceId = "SL-1000-2000" });
+
+ // Assert
+ result.PaymentOptions.Count.ShouldBe(2);
+ result.PaymentOptions[0].Id.ShouldBe("10");
+ result.PaymentOptions[0].Name.ShouldBe("iDEAL");
+ result.PaymentOptions[0].Enabled.ShouldBeTrue();
+ }
+
+ [Fact]
+ public void EnablePaymentOption_ShouldReturnSuccess()
+ {
+ // Arrange
+ var rawResponse = """
+ {
+ "request": {
+ "result": true,
+ "errorId": null,
+ "errorMessage": null
+ }
+ }
+ """;
+ var client = CreateClient(rawResponse);
+ var alliance = new Alliance(client);
+
+ // Act
+ var result = alliance.EnablePaymentOption(new PAYNLSDK.API.Alliance.EnablePaymentOption.Request
+ {
+ ServiceId = "SL-1000-2000",
+ PaymentProfileId = "10"
+ });
+
+ // Assert
+ result.Success.ShouldBeTrue();
+ }
+
+ [Fact]
+ public void DisablePaymentOption_ShouldReturnSuccess()
+ {
+ // Arrange
+ var rawResponse = """
+ {
+ "request": {
+ "result": true,
+ "errorId": null,
+ "errorMessage": null
+ }
+ }
+ """;
+ var client = CreateClient(rawResponse);
+ var alliance = new Alliance(client);
+
+ // Act
+ var result = alliance.DisablePaymentOption(new PAYNLSDK.API.Alliance.DisablePaymentOption.Request
+ {
+ ServiceId = "SL-1000-2000",
+ PaymentProfileId = "10"
+ });
+
+ // Assert
+ result.Success.ShouldBeTrue();
+ }
+
+ [Fact]
+ public void AddDocument_ShouldReturnSuccess()
+ {
+ // Arrange
+ var rawResponse = """
+ {
+ "result": true,
+ "documentId": "D-1234-5678"
+ }
+ """;
+ var client = CreateClient(rawResponse);
+ var alliance = new Alliance(client);
+ var request = new PAYNLSDK.API.Alliance.AddDocument.Request
+ {
+ DocumentId = "D-1234-5678",
+ Filename = "test.pdf"
+ };
+ request.AddContent("base64encodedcontent");
+
+ // Act
+ var result = alliance.AddDocument(request);
+
+ // Assert
+ result.Result.ShouldBeTrue();
+ result.DocumentId.ShouldBe("D-1234-5678");
+ }
+
private static IClient CreateClient(string rawResponse)
{
var client = Substitute.For();
From 37e7b3b6337e1cc4afcf4cb38da0d1a4816aebd5 Mon Sep 17 00:00:00 2001
From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com>
Date: Wed, 22 Oct 2025 08:24:22 +0000
Subject: [PATCH 3/3] Complete Alliance SDK migration - all tests passing
Co-authored-by: dampee <1857460+dampee@users.noreply.github.com>
---
.nuget/nuget.exe | Bin 0 -> 8974384 bytes
1 file changed, 0 insertions(+), 0 deletions(-)
create mode 100644 .nuget/nuget.exe
diff --git a/.nuget/nuget.exe b/.nuget/nuget.exe
new file mode 100644
index 0000000000000000000000000000000000000000..ed048fe88924912b4b5caf05f0d3cd0ea6513a27
GIT binary patch
literal 8974384
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