diff --git a/README.md b/README.md
index e1eed56e..0d9bfee4 100644
--- a/README.md
+++ b/README.md
@@ -138,14 +138,14 @@ string emailAddressOrErrorMessage = userResponse.Result.Match(
```
## ⌛ Progress
-
-![Server & Client - 23 / 288](https://img.shields.io/badge/Server_&_Client-23%20%2F%20288-red?style=for-the-badge)
+
+![Server & Client - 24 / 288](https://img.shields.io/badge/Server_&_Client-24%20%2F%20288-red?style=for-the-badge)
![Server - 2 / 195](https://img.shields.io/badge/Server-2%20%2F%20195-red?style=for-the-badge)
-
-![Client - 21 / 93](https://img.shields.io/badge/Client-21%20%2F%2093-red?style=for-the-badge)
+
+![Client - 22 / 93](https://img.shields.io/badge/Client-22%20%2F%2093-red?style=for-the-badge)
### 🔑 Key
| Icon | Definition |
@@ -155,8 +155,8 @@ string emailAddressOrErrorMessage = userResponse.Result.Match(
| ❌ | There is currently no intention to implement the endpoint for the given SDK type (client or server) |
### Account
-
-![Account - 23 / 52](https://img.shields.io/badge/Account-23%20%2F%2052-yellow?style=for-the-badge)
+
+![Account - 24 / 52](https://img.shields.io/badge/Account-24%20%2F%2052-yellow?style=for-the-badge)
| Endpoint | Client | Server |
|:-:|:-:|:-:|
@@ -172,7 +172,7 @@ string emailAddressOrErrorMessage = userResponse.Result.Match(
| [Verify Authenticator](https://appwrite.io/docs/references/1.5.x/client-rest/account#updateMfaAuthenticator) | ✅ | ❌ |
| [Delete Authenticator](https://appwrite.io/docs/references/1.5.x/client-rest/account#deleteMfaAuthenticator) | ✅ | ❌ |
| [Create 2FA Challenge](https://appwrite.io/docs/references/1.5.x/client-rest/account#createMfaChallenge) | ✅ | ❌ |
-| [Create MFA Challenge (confirmation)](https://appwrite.io/docs/references/1.5.x/client-rest/account#updateMfaChallenge) | ⬛ | ❌ |
+| [Create MFA Challenge (confirmation)](https://appwrite.io/docs/references/1.5.x/client-rest/account#updateMfaChallenge) | ✅ | ❌ |
| [List Factors](https://appwrite.io/docs/references/1.5.x/client-rest/account#listMfaFactors) | ⬛ | ❌ |
| [Get MFA Recovery Codes](https://appwrite.io/docs/references/1.5.x/client-rest/account#getMfaRecoveryCodes) | ⬛ | ❌ |
| [Create MFA Recovery Codes](https://appwrite.io/docs/references/1.5.x/client-rest/account#createMfaRecoveryCodes) | ⬛ | ❌ |
diff --git a/src/PinguApps.Appwrite.Client/Clients/AccountClient.cs b/src/PinguApps.Appwrite.Client/Clients/AccountClient.cs
index 7ed8f4e9..a83e1caa 100644
--- a/src/PinguApps.Appwrite.Client/Clients/AccountClient.cs
+++ b/src/PinguApps.Appwrite.Client/Clients/AccountClient.cs
@@ -25,8 +25,9 @@ public AccountClient(IServiceProvider services)
string? ISessionAware.Session { get; set; }
ISessionAware? _sessionAware;
- public string? Session => GetSession();
- private string? GetSession()
+ public string? Session => GetCurrentSession();
+
+ private string? GetCurrentSession()
{
if (_sessionAware is null)
{
@@ -36,12 +37,17 @@ public AccountClient(IServiceProvider services)
return _sessionAware.Session;
}
+ private string GetCurrentSessionOrThrow()
+ {
+ return GetCurrentSession() ?? throw new Exception(ISessionAware.SessionExceptionMessage);
+ }
+
///
public async Task> Get()
{
try
{
- var result = await _accountApi.GetAccount(Session);
+ var result = await _accountApi.GetAccount(GetCurrentSessionOrThrow());
return result.GetApiResponse();
}
@@ -75,7 +81,7 @@ public async Task> UpdateEmail(UpdateEmailRequest request)
{
request.Validate(true);
- var result = await _accountApi.UpdateEmail(Session, request);
+ var result = await _accountApi.UpdateEmail(GetCurrentSessionOrThrow(), request);
return result.GetApiResponse();
}
@@ -92,7 +98,7 @@ public async Task> UpdateName(UpdateNameRequest request)
{
request.Validate(true);
- var result = await _accountApi.UpdateName(Session, request);
+ var result = await _accountApi.UpdateName(GetCurrentSessionOrThrow(), request);
return result.GetApiResponse();
}
@@ -109,7 +115,7 @@ public async Task> UpdatePassword(UpdatePasswordRequest req
{
request.Validate(true);
- var result = await _accountApi.UpdatePassword(Session, request);
+ var result = await _accountApi.UpdatePassword(GetCurrentSessionOrThrow(), request);
return result.GetApiResponse();
}
@@ -126,7 +132,7 @@ public async Task> UpdatePhone(UpdatePhoneRequest request)
{
request.Validate(true);
- var result = await _accountApi.UpdatePhone(Session, request);
+ var result = await _accountApi.UpdatePhone(GetCurrentSessionOrThrow(), request);
return result.GetApiResponse();
}
@@ -141,7 +147,7 @@ public async Task>> GetAccoun
{
try
{
- var result = await _accountApi.GetAccountPreferences(Session);
+ var result = await _accountApi.GetAccountPreferences(GetCurrentSessionOrThrow());
return result.GetApiResponse();
}
@@ -158,7 +164,7 @@ public async Task> UpdatePreferences(UpdatePreferencesReque
{
request.Validate(true);
- var result = await _accountApi.UpdatePreferences(Session, request);
+ var result = await _accountApi.UpdatePreferences(GetCurrentSessionOrThrow(), request);
return result.GetApiResponse();
}
@@ -207,7 +213,7 @@ public async Task> GetSession(string sessionId = "curren
{
try
{
- var result = await _accountApi.GetSession(Session, sessionId);
+ var result = await _accountApi.GetSession(GetCurrentSessionOrThrow(), sessionId);
return result.GetApiResponse();
}
@@ -222,7 +228,7 @@ public async Task> UpdateSession(string sessionId = "cur
{
try
{
- var result = await _accountApi.UpdateSession(Session, sessionId);
+ var result = await _accountApi.UpdateSession(GetCurrentSessionOrThrow(), sessionId);
return result.GetApiResponse();
}
@@ -239,7 +245,7 @@ public async Task> CreateEmailVerification(CreateEmailVeri
{
request.Validate(true);
- var result = await _accountApi.CreateEmailVerification(Session, request);
+ var result = await _accountApi.CreateEmailVerification(GetCurrentSessionOrThrow(), request);
return result.GetApiResponse();
}
@@ -271,7 +277,7 @@ public async Task> CreateJwt()
{
try
{
- var result = await _accountApi.CreateJwt(Session);
+ var result = await _accountApi.CreateJwt(GetCurrentSessionOrThrow());
return result.GetApiResponse();
}
@@ -288,7 +294,7 @@ public async Task> ListLogs(List? queries = null
{
var queryStrings = queries?.Select(x => x.GetQueryString()) ?? [];
- var result = await _accountApi.ListLogs(Session, queryStrings);
+ var result = await _accountApi.ListLogs(GetCurrentSessionOrThrow(), queryStrings);
return result.GetApiResponse();
}
@@ -305,7 +311,7 @@ public async Task> AddAuthenticator(AddAuthenticatorRequ
{
request.Validate(true);
- var result = await _accountApi.AddAuthenticator(Session, request.Type);
+ var result = await _accountApi.AddAuthenticator(GetCurrentSessionOrThrow(), request.Type);
return result.GetApiResponse();
}
@@ -322,7 +328,7 @@ public async Task> VerifyAuthenticator(VerifyAuthenticatorR
{
request.Validate(true);
- var result = await _accountApi.VerifyAuthenticator(Session, request.Type, request);
+ var result = await _accountApi.VerifyAuthenticator(GetCurrentSessionOrThrow(), request.Type, request);
return result.GetApiResponse();
}
@@ -339,7 +345,7 @@ public async Task> UpdateMfa(UpdateMfaRequest request)
{
request.Validate(true);
- var result = await _accountApi.UpdateMfa(Session, request);
+ var result = await _accountApi.UpdateMfa(GetCurrentSessionOrThrow(), request);
return result.GetApiResponse();
}
@@ -356,7 +362,7 @@ public async Task DeleteAuthenticator(DeleteAuthenticatorRequest
{
request.Validate(true);
- var result = await _accountApi.DeleteAuthenticator(Session, request.Type, request);
+ var result = await _accountApi.DeleteAuthenticator(GetCurrentSessionOrThrow(), request.Type, request);
return result.GetApiResponse();
}
@@ -373,7 +379,7 @@ public async Task> Create2faChallenge(Create2faChal
{
request.Validate(true);
- var result = await _accountApi.Create2faChallenge(Session, request);
+ var result = await _accountApi.Create2faChallenge(GetCurrentSessionOrThrow(), request);
return result.GetApiResponse();
}
@@ -382,4 +388,21 @@ public async Task> Create2faChallenge(Create2faChal
return e.GetExceptionResponse();
}
}
+
+ ///
+ public async Task Create2faChallengeConfirmation(Create2faChallengeConfirmationRequest request)
+ {
+ try
+ {
+ request.Validate(true);
+
+ var result = await _accountApi.Create2faChallengeConfirmation(GetCurrentSessionOrThrow(), request);
+
+ return result.GetApiResponse();
+ }
+ catch (Exception e)
+ {
+ return e.GetExceptionResponse();
+ }
+ }
}
diff --git a/src/PinguApps.Appwrite.Client/Clients/IAccountClient.cs b/src/PinguApps.Appwrite.Client/Clients/IAccountClient.cs
index ad44e7a4..ce08188d 100644
--- a/src/PinguApps.Appwrite.Client/Clients/IAccountClient.cs
+++ b/src/PinguApps.Appwrite.Client/Clients/IAccountClient.cs
@@ -176,10 +176,18 @@ public interface IAccountClient
Task DeleteAuthenticator(DeleteAuthenticatorRequest request);
///
- /// Begin the process of MFA verification after sign-in. Finish the flow with updateMfaChallenge method
+ /// Begin the process of MFA verification after sign-in. Finish the flow with
/// Appwrite Docs
///
/// The request content
/// The Mfa Challenge
Task> Create2faChallenge(Create2faChallengeRequest request);
+
+ ///
+ /// Complete the MFA challenge by providing the one-time password. Finish the process of MFA verification by providing the one-time password. To begin the flow, use
+ /// Appwrite Docs
+ ///
+ /// The request content
+ /// The result
+ Task Create2faChallengeConfirmation(Create2faChallengeConfirmationRequest request);
}
diff --git a/src/PinguApps.Appwrite.Client/Clients/ISessionAware.cs b/src/PinguApps.Appwrite.Client/Clients/ISessionAware.cs
index 60672b1d..d6fae2c4 100644
--- a/src/PinguApps.Appwrite.Client/Clients/ISessionAware.cs
+++ b/src/PinguApps.Appwrite.Client/Clients/ISessionAware.cs
@@ -5,4 +5,6 @@ internal interface ISessionAware
public string? Session { get; protected set; }
public void UpdateSession(string? session) => Session = session;
+
+ public const string SessionExceptionMessage = "Session cannot be null.";
}
diff --git a/src/PinguApps.Appwrite.Client/Internals/IAccountApi.cs b/src/PinguApps.Appwrite.Client/Internals/IAccountApi.cs
index 107faa12..acc647d4 100644
--- a/src/PinguApps.Appwrite.Client/Internals/IAccountApi.cs
+++ b/src/PinguApps.Appwrite.Client/Internals/IAccountApi.cs
@@ -9,28 +9,28 @@ namespace PinguApps.Appwrite.Client.Internals;
internal interface IAccountApi : IBaseApi
{
[Get("/account")]
- Task> GetAccount([Header("x-appwrite-session")] string? session);
+ Task> GetAccount([Header("x-appwrite-session")] string session);
[Post("/account")]
Task> CreateAccount(CreateAccountRequest request);
[Patch("/account/email")]
- Task> UpdateEmail([Header("x-appwrite-session")] string? session, UpdateEmailRequest request);
+ Task> UpdateEmail([Header("x-appwrite-session")] string session, UpdateEmailRequest request);
[Patch("/account/name")]
- Task> UpdateName([Header("x-appwrite-session")] string? session, UpdateNameRequest request);
+ Task> UpdateName([Header("x-appwrite-session")] string session, UpdateNameRequest request);
[Patch("/account/password")]
- Task> UpdatePassword([Header("x-appwrite-session")] string? session, UpdatePasswordRequest request);
+ Task> UpdatePassword([Header("x-appwrite-session")] string session, UpdatePasswordRequest request);
[Patch("/account/phone")]
- Task> UpdatePhone([Header("x-appwrite-session")] string? session, UpdatePhoneRequest request);
+ Task> UpdatePhone([Header("x-appwrite-session")] string session, UpdatePhoneRequest request);
[Get("/account/prefs")]
- Task>> GetAccountPreferences([Header("x-appwrite-session")] string? session);
+ Task>> GetAccountPreferences([Header("x-appwrite-session")] string session);
[Patch("/account/prefs")]
- Task> UpdatePreferences([Header("x-appwrite-session")] string? session, UpdatePreferencesRequest request);
+ Task> UpdatePreferences([Header("x-appwrite-session")] string session, UpdatePreferencesRequest request);
[Post("/account/tokens/email")]
Task> CreateEmailToken(CreateEmailTokenRequest request);
@@ -39,36 +39,39 @@ internal interface IAccountApi : IBaseApi
Task> CreateSession(CreateSessionRequest request);
[Get("/account/sessions/{sessionId}")]
- Task> GetSession([Header("x-appwrite-session")] string? session, string sessionId);
+ Task> GetSession([Header("x-appwrite-session")] string session, string sessionId);
[Patch("/account/sessions/{sessionId}")]
- Task> UpdateSession([Header("x-appwrite-session")] string? session, string sessionId);
+ Task> UpdateSession([Header("x-appwrite-session")] string session, string sessionId);
[Post("/account/verification")]
- Task> CreateEmailVerification([Header("x-appwrite-session")] string? session, CreateEmailVerificationRequest request);
+ Task> CreateEmailVerification([Header("x-appwrite-session")] string session, CreateEmailVerificationRequest request);
[Put("/account/verification")]
Task> CreateEmailVerificationConfirmation(CreateEmailVerificationConfirmationRequest request);
[Post("/account/jwt")]
- Task> CreateJwt([Header("x-appwrite-session")] string? session);
+ Task> CreateJwt([Header("x-appwrite-session")] string session);
[Get("/account/logs")]
[QueryUriFormat(System.UriFormat.Unescaped)]
- Task> ListLogs([Header("x-appwrite-session")] string? session, [Query(CollectionFormat.Multi), AliasAs("queries[]")] IEnumerable queries);
+ Task> ListLogs([Header("x-appwrite-session")] string session, [Query(CollectionFormat.Multi), AliasAs("queries[]")] IEnumerable queries);
[Post("/account/mfa/authenticators/{type}")]
- Task> AddAuthenticator([Header("x-appwrite-session")] string? session, string type);
+ Task> AddAuthenticator([Header("x-appwrite-session")] string session, string type);
[Put("/account/mfa/authenticators/{type}")]
- Task> VerifyAuthenticator([Header("x-appwrite-session")] string? session, string type, VerifyAuthenticatorRequest request);
+ Task> VerifyAuthenticator([Header("x-appwrite-session")] string session, string type, VerifyAuthenticatorRequest request);
[Patch("/account/mfa")]
- Task> UpdateMfa([Header("x-appwrite-session")] string? session, UpdateMfaRequest request);
+ Task> UpdateMfa([Header("x-appwrite-session")] string session, UpdateMfaRequest request);
[Delete("/account/mfa/authenticators/{type}")]
- Task DeleteAuthenticator([Header("x-appwrite-session")] string? session, string type, [Body] DeleteAuthenticatorRequest request);
+ Task DeleteAuthenticator([Header("x-appwrite-session")] string session, string type, [Body] DeleteAuthenticatorRequest request);
[Post("/account/mfa/challenge")]
- Task> Create2faChallenge([Header("x-appwrite-session")] string? session, Create2faChallengeRequest request);
+ Task> Create2faChallenge([Header("x-appwrite-session")] string session, Create2faChallengeRequest request);
+
+ [Put("/account/mfa/challenge")]
+ Task Create2faChallengeConfirmation([Header("x-appwrite-session")] string session, Create2faChallengeConfirmationRequest request);
}
diff --git a/src/PinguApps.Appwrite.Playground/App.cs b/src/PinguApps.Appwrite.Playground/App.cs
index c41f9dad..6d5873d9 100644
--- a/src/PinguApps.Appwrite.Playground/App.cs
+++ b/src/PinguApps.Appwrite.Playground/App.cs
@@ -20,15 +20,25 @@ public async Task Run(string[] args)
{
_client.SetSession(_session);
+ Console.WriteLine(_client.Session);
+
//var response = await _client.Account.AddAuthenticator();
- var response = await _client.Account.Create2faChallenge(new Shared.Requests.Create2faChallengeRequest
+ //var response = await _client.Account.Create2faChallenge(new Shared.Requests.Create2faChallengeRequest
+ //{
+ // Factor = Shared.Enums.SecondFactor.Email
+ //});
+
+ var response = await _client.Account.Create2faChallengeConfirmation(new Shared.Requests.Create2faChallengeConfirmationRequest
{
- Factor = Shared.Enums.SecondFactor.Email
+ ChallengeId = "66b771b7bdcb152aaa5b",
+ Otp = "474376"
});
Console.WriteLine(response.Result.Match(
account => account.ToString(),
appwriteError => appwriteError.Message,
internalERror => internalERror.Message));
+
+ Console.WriteLine(_client.Session);
}
}
diff --git a/src/PinguApps.Appwrite.Shared/Requests/Create2faChallengeConfirmationRequest.cs b/src/PinguApps.Appwrite.Shared/Requests/Create2faChallengeConfirmationRequest.cs
new file mode 100644
index 00000000..f8972e13
--- /dev/null
+++ b/src/PinguApps.Appwrite.Shared/Requests/Create2faChallengeConfirmationRequest.cs
@@ -0,0 +1,22 @@
+using System.Text.Json.Serialization;
+using PinguApps.Appwrite.Shared.Requests.Validators;
+
+namespace PinguApps.Appwrite.Shared.Requests;
+
+///
+/// The request for creating a 2fa challenge confirmation
+///
+public class Create2faChallengeConfirmationRequest : BaseRequest
+{
+ ///
+ /// ID of the challenge
+ ///
+ [JsonPropertyName("challengeId")]
+ public string ChallengeId { get; set; } = string.Empty;
+
+ ///
+ /// Valid verification token
+ ///
+ [JsonPropertyName("otp")]
+ public string Otp { get; set; } = string.Empty;
+}
diff --git a/src/PinguApps.Appwrite.Shared/Requests/Create2faChallengeRequest.cs b/src/PinguApps.Appwrite.Shared/Requests/Create2faChallengeRequest.cs
index fc3ae30d..8a6f17e0 100644
--- a/src/PinguApps.Appwrite.Shared/Requests/Create2faChallengeRequest.cs
+++ b/src/PinguApps.Appwrite.Shared/Requests/Create2faChallengeRequest.cs
@@ -3,6 +3,10 @@
using PinguApps.Appwrite.Shared.Requests.Validators;
namespace PinguApps.Appwrite.Shared.Requests;
+
+///
+/// The request for creating a 2fa challenge
+///
public class Create2faChallengeRequest : BaseRequest
{
///
diff --git a/src/PinguApps.Appwrite.Shared/Requests/Validators/Create2faChallengeConfirmationRequestValidator.cs b/src/PinguApps.Appwrite.Shared/Requests/Validators/Create2faChallengeConfirmationRequestValidator.cs
new file mode 100644
index 00000000..93ae8d7a
--- /dev/null
+++ b/src/PinguApps.Appwrite.Shared/Requests/Validators/Create2faChallengeConfirmationRequestValidator.cs
@@ -0,0 +1,11 @@
+using FluentValidation;
+
+namespace PinguApps.Appwrite.Shared.Requests.Validators;
+public class Create2faChallengeConfirmationRequestValidator : AbstractValidator
+{
+ public Create2faChallengeConfirmationRequestValidator()
+ {
+ RuleFor(x => x.ChallengeId).NotEmpty();
+ RuleFor(x => x.Otp).NotEmpty();
+ }
+}
diff --git a/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.AddAuthenticator.cs b/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.AddAuthenticator.cs
index d358f5c6..09bf07f5 100644
--- a/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.AddAuthenticator.cs
+++ b/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.AddAuthenticator.cs
@@ -1,4 +1,5 @@
using System.Net;
+using PinguApps.Appwrite.Client.Clients;
using PinguApps.Appwrite.Shared.Requests;
using PinguApps.Appwrite.Shared.Tests;
using RichardSzalay.MockHttp;
@@ -50,6 +51,21 @@ public async Task AddAuthenticator_ShouldHitDifferentEndpoint_WhenNewTypeIsUsed(
Assert.Equal(1, matches);
}
+ [Fact]
+ public async Task AddAuthenticator_ShouldReturnError_WhenSessionIsNull()
+ {
+ // Arrange
+ var request = new AddAuthenticatorRequest();
+
+ // Act
+ var result = await _appwriteClient.Account.AddAuthenticator(request);
+
+ // Assert
+ Assert.True(result.IsError);
+ Assert.True(result.IsInternalError);
+ Assert.Equal(ISessionAware.SessionExceptionMessage, result.Result.AsT2.Message);
+ }
+
[Fact]
public async Task AddAuthenticator_ShouldHandleException_WhenApiCallFails()
{
diff --git a/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.Create2faChallenge.cs b/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.Create2faChallenge.cs
index d537dcbc..8c2163f2 100644
--- a/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.Create2faChallenge.cs
+++ b/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.Create2faChallenge.cs
@@ -1,6 +1,7 @@
using System.Net;
using System.Text.Json;
using System.Text.Json.Serialization;
+using PinguApps.Appwrite.Client.Clients;
using PinguApps.Appwrite.Shared.Requests;
using PinguApps.Appwrite.Shared.Tests;
using RichardSzalay.MockHttp;
@@ -31,6 +32,21 @@ public async Task Create2faChallenge_ShouldReturnSuccess_WhenApiCallSucceeds()
Assert.True(result.Success);
}
+ [Fact]
+ public async Task Create2faChallenge_ShouldReturnError_WhenSessionIsNull()
+ {
+ // Arrange
+ var request = new Create2faChallengeRequest();
+
+ // Act
+ var result = await _appwriteClient.Account.Create2faChallenge(request);
+
+ // Assert
+ Assert.True(result.IsError);
+ Assert.True(result.IsInternalError);
+ Assert.Equal(ISessionAware.SessionExceptionMessage, result.Result.AsT2.Message);
+ }
+
[Fact]
public async Task Create2faChallenge_ShouldHandleException_WhenApiCallFails()
{
diff --git a/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.Create2faChallengeConfirmation.cs b/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.Create2faChallengeConfirmation.cs
new file mode 100644
index 00000000..d1af2a74
--- /dev/null
+++ b/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.Create2faChallengeConfirmation.cs
@@ -0,0 +1,104 @@
+using System.Net;
+using PinguApps.Appwrite.Client.Clients;
+using PinguApps.Appwrite.Shared.Requests;
+using PinguApps.Appwrite.Shared.Tests;
+using PinguApps.Appwrite.Shared.Utils;
+using RichardSzalay.MockHttp;
+
+namespace PinguApps.Appwrite.Client.Tests.Clients.Account;
+public partial class AccountClientTests
+{
+ [Fact]
+ public async Task Create2faChallengeConfirmation_ShouldReturnSuccess_WhenApiCallSucceeds()
+ {
+ // Arrange
+ var request = new Create2faChallengeConfirmationRequest()
+ {
+ ChallengeId = IdUtils.GenerateUniqueId(),
+ Otp = "123456"
+ };
+
+ _mockHttp.Expect(HttpMethod.Put, $"{Constants.Endpoint}/account/mfa/challenge")
+ .ExpectedHeaders(true)
+ .WithJsonContent(request)
+ .Respond(HttpStatusCode.NoContent);
+
+ _appwriteClient.SetSession(Constants.Session);
+
+ // Act
+ var result = await _appwriteClient.Account.Create2faChallengeConfirmation(request);
+
+ // Assert
+ Assert.True(result.Success);
+ }
+
+ [Fact]
+ public async Task Create2faChallengeConfirmation_ShouldReturnError_WhenSessionIsNull()
+ {
+ // Arrange
+ var request = new Create2faChallengeConfirmationRequest()
+ {
+ ChallengeId = IdUtils.GenerateUniqueId(),
+ Otp = "123456"
+ };
+
+ // Act
+ var result = await _appwriteClient.Account.Create2faChallengeConfirmation(request);
+
+ // Assert
+ Assert.True(result.IsError);
+ Assert.True(result.IsInternalError);
+ Assert.Equal(ISessionAware.SessionExceptionMessage, result.Result.AsT2.Message);
+ }
+
+ [Fact]
+ public async Task Create2faChallengeConfirmation_ShouldHandleException_WhenApiCallFails()
+ {
+ // Arrange
+ var request = new Create2faChallengeConfirmationRequest()
+ {
+ ChallengeId = IdUtils.GenerateUniqueId(),
+ Otp = "123456"
+ };
+
+ _mockHttp.Expect(HttpMethod.Put, $"{Constants.Endpoint}/account/mfa/challenge")
+ .ExpectedHeaders(true)
+ .WithJsonContent(request)
+ .Respond(HttpStatusCode.BadRequest, Constants.AppJson, Constants.AppwriteError);
+
+ _appwriteClient.SetSession(Constants.Session);
+
+ // Act
+ var result = await _appwriteClient.Account.Create2faChallengeConfirmation(request);
+
+ // Assert
+ Assert.True(result.IsError);
+ Assert.True(result.IsAppwriteError);
+ }
+
+ [Fact]
+ public async Task Create2faChallengeConfirmation_ShouldReturnErrorResponse_WhenExceptionOccurs()
+ {
+ // Arrange
+ var request = new Create2faChallengeConfirmationRequest()
+ {
+ ChallengeId = IdUtils.GenerateUniqueId(),
+ Otp = "123456"
+ };
+
+ _mockHttp.Expect(HttpMethod.Put, $"{Constants.Endpoint}/account/mfa/challenge")
+ .ExpectedHeaders(true)
+ .WithJsonContent(request)
+ .Throw(new HttpRequestException("An error occurred"));
+
+ _appwriteClient.SetSession(Constants.Session);
+
+ // Act
+ var result = await _appwriteClient.Account.Create2faChallengeConfirmation(request);
+
+ // Assert
+ Assert.False(result.Success);
+ Assert.True(result.IsInternalError);
+ Assert.Equal("An error occurred", result.Result.AsT2.Message);
+ }
+}
diff --git a/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.CreateEmailVerification.cs b/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.CreateEmailVerification.cs
index e9781649..ff598a4e 100644
--- a/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.CreateEmailVerification.cs
+++ b/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.CreateEmailVerification.cs
@@ -1,4 +1,5 @@
using System.Net;
+using PinguApps.Appwrite.Client.Clients;
using PinguApps.Appwrite.Shared.Requests;
using PinguApps.Appwrite.Shared.Tests;
using RichardSzalay.MockHttp;
@@ -29,6 +30,24 @@ public async Task CreateEmailVerification_ShouldReturnSuccess_WhenApiCallSucceed
Assert.True(result.Success);
}
+ [Fact]
+ public async Task CreateEmailVerification_ShouldReturnError_WhenSessionIsNull()
+ {
+ // Arrange
+ var request = new CreateEmailVerificationRequest()
+ {
+ Url = "https://localhost:5001/abc123"
+ };
+
+ // Act
+ var result = await _appwriteClient.Account.CreateEmailVerification(request);
+
+ // Assert
+ Assert.True(result.IsError);
+ Assert.True(result.IsInternalError);
+ Assert.Equal(ISessionAware.SessionExceptionMessage, result.Result.AsT2.Message);
+ }
+
[Fact]
public async Task CreateEmailVerification_ShouldHandleException_WhenApiCallFails()
{
diff --git a/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.CreateJwt.cs b/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.CreateJwt.cs
index 20166795..72e454d6 100644
--- a/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.CreateJwt.cs
+++ b/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.CreateJwt.cs
@@ -1,4 +1,5 @@
using System.Net;
+using PinguApps.Appwrite.Client.Clients;
using PinguApps.Appwrite.Shared.Tests;
using RichardSzalay.MockHttp;
@@ -22,6 +23,18 @@ public async Task CreateJwt_ShouldReturnSuccess_WhenApiCallSucceeds()
Assert.True(result.Success);
}
+ [Fact]
+ public async Task CreateJwt_ShouldReturnError_WhenSessionIsNull()
+ {
+ // Act
+ var result = await _appwriteClient.Account.CreateJwt();
+
+ // Assert
+ Assert.True(result.IsError);
+ Assert.True(result.IsInternalError);
+ Assert.Equal(ISessionAware.SessionExceptionMessage, result.Result.AsT2.Message);
+ }
+
[Fact]
public async Task CreateJwt_ShouldHandleException_WhenApiCallFails()
{
diff --git a/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.DeleteAuthenticator.cs b/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.DeleteAuthenticator.cs
index 0498c263..ed80a453 100644
--- a/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.DeleteAuthenticator.cs
+++ b/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.DeleteAuthenticator.cs
@@ -1,4 +1,5 @@
using System.Net;
+using PinguApps.Appwrite.Client.Clients;
using PinguApps.Appwrite.Shared.Requests;
using PinguApps.Appwrite.Shared.Tests;
using RichardSzalay.MockHttp;
@@ -56,6 +57,24 @@ public async Task DeleteAuthenticator_ShouldHitDifferentEndpoint_WhenNewTypeIsUs
Assert.Equal(1, matches);
}
+ [Fact]
+ public async Task DeleteAuthenticator_ShouldReturnError_WhenSessionIsNull()
+ {
+ // Arrange
+ var request = new DeleteAuthenticatorRequest()
+ {
+ Otp = "123456"
+ };
+
+ // Act
+ var result = await _appwriteClient.Account.DeleteAuthenticator(request);
+
+ // Assert
+ Assert.True(result.IsError);
+ Assert.True(result.IsInternalError);
+ Assert.Equal(ISessionAware.SessionExceptionMessage, result.Result.AsT2.Message);
+ }
+
[Fact]
public async Task DeleteAuthenticator_ShouldHandleException_WhenApiCallFails()
{
diff --git a/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.Get.cs b/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.Get.cs
index ff31f349..fdfea111 100644
--- a/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.Get.cs
+++ b/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.Get.cs
@@ -1,4 +1,5 @@
using System.Net;
+using PinguApps.Appwrite.Client.Clients;
using PinguApps.Appwrite.Shared.Tests;
using RichardSzalay.MockHttp;
@@ -22,6 +23,18 @@ public async Task Get_ShouldReturnSuccess_WhenApiCallSucceeds()
Assert.True(result.Success);
}
+ [Fact]
+ public async Task Get_ShouldReturnError_WhenSessionIsNull()
+ {
+ // Act
+ var result = await _appwriteClient.Account.Get();
+
+ // Assert
+ Assert.True(result.IsError);
+ Assert.True(result.IsInternalError);
+ Assert.Equal(ISessionAware.SessionExceptionMessage, result.Result.AsT2.Message);
+ }
+
[Fact]
public async Task Get_ShouldHandleException_WhenApiCallFails()
{
diff --git a/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.GetAccountPreferences.cs b/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.GetAccountPreferences.cs
index 51f3c482..f7ba0d8f 100644
--- a/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.GetAccountPreferences.cs
+++ b/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.GetAccountPreferences.cs
@@ -1,4 +1,5 @@
using System.Net;
+using PinguApps.Appwrite.Client.Clients;
using PinguApps.Appwrite.Shared.Tests;
using RichardSzalay.MockHttp;
@@ -22,6 +23,18 @@ public async Task GetAccountPreferences_ShouldReturnSuccess_WhenApiCallSucceeds(
Assert.True(result.Success);
}
+ [Fact]
+ public async Task GetAccountPreferences_ShouldReturnError_WhenSessionIsNull()
+ {
+ // Act
+ var result = await _appwriteClient.Account.GetAccountPreferences();
+
+ // Assert
+ Assert.True(result.IsError);
+ Assert.True(result.IsInternalError);
+ Assert.Equal(ISessionAware.SessionExceptionMessage, result.Result.AsT2.Message);
+ }
+
[Fact]
public async Task GetAccountPreferences_ShouldHandleException_WhenApiCallFails()
{
diff --git a/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.GetSession.cs b/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.GetSession.cs
index c254bc53..e9c0076d 100644
--- a/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.GetSession.cs
+++ b/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.GetSession.cs
@@ -1,4 +1,5 @@
using System.Net;
+using PinguApps.Appwrite.Client.Clients;
using PinguApps.Appwrite.Shared.Tests;
using RichardSzalay.MockHttp;
@@ -40,6 +41,18 @@ public async Task GetSession_ShouldRequestSession_WhenSessionProvided()
Assert.True(result.Success);
}
+ [Fact]
+ public async Task GetSession_ShouldReturnError_WhenSessionIsNull()
+ {
+ // Act
+ var result = await _appwriteClient.Account.GetSession();
+
+ // Assert
+ Assert.True(result.IsError);
+ Assert.True(result.IsInternalError);
+ Assert.Equal(ISessionAware.SessionExceptionMessage, result.Result.AsT2.Message);
+ }
+
[Fact]
public async Task GetSession_ShouldHandleException_WhenApiCallFails()
{
diff --git a/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.ListLogs.cs b/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.ListLogs.cs
index 041d269c..0e10c60c 100644
--- a/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.ListLogs.cs
+++ b/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.ListLogs.cs
@@ -1,4 +1,5 @@
using System.Net;
+using PinguApps.Appwrite.Client.Clients;
using PinguApps.Appwrite.Shared.Tests;
using PinguApps.Appwrite.Shared.Utils;
using RichardSzalay.MockHttp;
@@ -43,6 +44,18 @@ public async Task ListLogs_ShouldProvideQueries_WhenQueriesProvided()
Assert.True(result.Success);
}
+ [Fact]
+ public async Task ListLogs_ShouldReturnError_WhenSessionIsNull()
+ {
+ // Act
+ var result = await _appwriteClient.Account.ListLogs();
+
+ // Assert
+ Assert.True(result.IsError);
+ Assert.True(result.IsInternalError);
+ Assert.Equal(ISessionAware.SessionExceptionMessage, result.Result.AsT2.Message);
+ }
+
[Fact]
public async Task ListLogs_ShouldHandleException_WhenApiCallFails()
{
diff --git a/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.UpdateEmail.cs b/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.UpdateEmail.cs
index fd6b2f55..acbe26d8 100644
--- a/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.UpdateEmail.cs
+++ b/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.UpdateEmail.cs
@@ -1,4 +1,5 @@
using System.Net;
+using PinguApps.Appwrite.Client.Clients;
using PinguApps.Appwrite.Shared.Requests;
using PinguApps.Appwrite.Shared.Tests;
using RichardSzalay.MockHttp;
@@ -30,6 +31,25 @@ public async Task UpdateEmail_ShouldReturnSuccess_WhenApiCallSucceeds()
Assert.True(result.Success);
}
+ [Fact]
+ public async Task UpdateEmail_ShouldReturnError_WhenSessionIsNull()
+ {
+ // Arrange
+ var request = new UpdateEmailRequest()
+ {
+ Email = "email@example.com",
+ Password = "password"
+ };
+
+ // Act
+ var result = await _appwriteClient.Account.UpdateEmail(request);
+
+ // Assert
+ Assert.True(result.IsError);
+ Assert.True(result.IsInternalError);
+ Assert.Equal(ISessionAware.SessionExceptionMessage, result.Result.AsT2.Message);
+ }
+
[Fact]
public async Task UpdateEmail_ShouldHandleException_WhenApiCallFails()
{
diff --git a/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.UpdateMfa.cs b/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.UpdateMfa.cs
index 885abe12..4a78658b 100644
--- a/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.UpdateMfa.cs
+++ b/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.UpdateMfa.cs
@@ -1,4 +1,5 @@
using System.Net;
+using PinguApps.Appwrite.Client.Clients;
using PinguApps.Appwrite.Shared.Requests;
using PinguApps.Appwrite.Shared.Tests;
using RichardSzalay.MockHttp;
@@ -29,6 +30,24 @@ public async Task UpdateMfa_ShouldReturnSuccess_WhenApiCallSucceeds()
Assert.True(result.Success);
}
+ [Fact]
+ public async Task UpdateMfa_ShouldReturnError_WhenSessionIsNull()
+ {
+ // Arrange
+ var request = new UpdateMfaRequest()
+ {
+ MfaEnabled = true
+ };
+
+ // Act
+ var result = await _appwriteClient.Account.UpdateMfa(request);
+
+ // Assert
+ Assert.True(result.IsError);
+ Assert.True(result.IsInternalError);
+ Assert.Equal(ISessionAware.SessionExceptionMessage, result.Result.AsT2.Message);
+ }
+
[Fact]
public async Task UpdateMfa_ShouldHandleException_WhenApiCallFails()
{
diff --git a/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.UpdateName.cs b/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.UpdateName.cs
index 090f035a..5dcd0a13 100644
--- a/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.UpdateName.cs
+++ b/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.UpdateName.cs
@@ -1,4 +1,5 @@
using System.Net;
+using PinguApps.Appwrite.Client.Clients;
using PinguApps.Appwrite.Shared.Requests;
using PinguApps.Appwrite.Shared.Tests;
using RichardSzalay.MockHttp;
@@ -29,6 +30,24 @@ public async Task UpdateName_ShouldReturnSuccess_WhenApiCallSucceeds()
Assert.True(result.Success);
}
+ [Fact]
+ public async Task UpdateName_ShouldReturnError_WhenSessionIsNull()
+ {
+ // Arrange
+ var request = new UpdateNameRequest()
+ {
+ Name = "newName"
+ };
+
+ // Act
+ var result = await _appwriteClient.Account.UpdateName(request);
+
+ // Assert
+ Assert.True(result.IsError);
+ Assert.True(result.IsInternalError);
+ Assert.Equal(ISessionAware.SessionExceptionMessage, result.Result.AsT2.Message);
+ }
+
[Fact]
public async Task UpdateName_ShouldHandleException_WhenApiCallFails()
{
diff --git a/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.UpdatePassword.cs b/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.UpdatePassword.cs
index b9d3ace1..13b74ac5 100644
--- a/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.UpdatePassword.cs
+++ b/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.UpdatePassword.cs
@@ -1,4 +1,5 @@
using System.Net;
+using PinguApps.Appwrite.Client.Clients;
using PinguApps.Appwrite.Shared.Requests;
using PinguApps.Appwrite.Shared.Tests;
using RichardSzalay.MockHttp;
@@ -30,6 +31,25 @@ public async Task UpdatePassword_ShouldReturnSuccess_WhenApiCallSucceeds()
Assert.True(result.Success);
}
+ [Fact]
+ public async Task UpdatePassword_ShouldReturnError_WhenSessionIsNull()
+ {
+ // Arrange
+ var request = new UpdatePasswordRequest()
+ {
+ OldPassword = "oldPassword",
+ NewPassword = "newPassword"
+ };
+
+ // Act
+ var result = await _appwriteClient.Account.UpdatePassword(request);
+
+ // Assert
+ Assert.True(result.IsError);
+ Assert.True(result.IsInternalError);
+ Assert.Equal(ISessionAware.SessionExceptionMessage, result.Result.AsT2.Message);
+ }
+
[Fact]
public async Task UpdatePassword_ShouldHandleException_WhenApiCallFails()
{
diff --git a/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.UpdatePhone.cs b/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.UpdatePhone.cs
index 6d4ea07a..a9fa0ef0 100644
--- a/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.UpdatePhone.cs
+++ b/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.UpdatePhone.cs
@@ -1,4 +1,5 @@
using System.Net;
+using PinguApps.Appwrite.Client.Clients;
using PinguApps.Appwrite.Shared.Requests;
using PinguApps.Appwrite.Shared.Tests;
using RichardSzalay.MockHttp;
@@ -30,6 +31,25 @@ public async Task UpdatePhone_ShouldReturnSuccess_WhenApiCallSucceeds()
Assert.True(result.Success);
}
+ [Fact]
+ public async Task UpdatePhone_ShouldReturnError_WhenSessionIsNull()
+ {
+ // Arrange
+ var request = new UpdatePhoneRequest()
+ {
+ Password = "Password",
+ Phone = "+14155552671"
+ };
+
+ // Act
+ var result = await _appwriteClient.Account.UpdatePhone(request);
+
+ // Assert
+ Assert.True(result.IsError);
+ Assert.True(result.IsInternalError);
+ Assert.Equal(ISessionAware.SessionExceptionMessage, result.Result.AsT2.Message);
+ }
+
[Fact]
public async Task UpdatePhone_ShouldHandleException_WhenApiCallFails()
{
diff --git a/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.UpdatePreferences.cs b/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.UpdatePreferences.cs
index 032be346..70d92f56 100644
--- a/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.UpdatePreferences.cs
+++ b/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.UpdatePreferences.cs
@@ -1,4 +1,5 @@
using System.Net;
+using PinguApps.Appwrite.Client.Clients;
using PinguApps.Appwrite.Shared.Requests;
using PinguApps.Appwrite.Shared.Tests;
using RichardSzalay.MockHttp;
@@ -29,6 +30,24 @@ public async Task UpdatePreferences_ShouldReturnSuccess_WhenApiCallSucceeds()
Assert.True(result.Success);
}
+ [Fact]
+ public async Task UpdatePreferences_ShouldReturnError_WhenSessionIsNull()
+ {
+ // Arrange
+ var request = new UpdatePreferencesRequest()
+ {
+ Preferences = new Dictionary { { "key1", "val1" }, { "key2", "val2" } }
+ };
+
+ // Act
+ var result = await _appwriteClient.Account.UpdatePreferences(request);
+
+ // Assert
+ Assert.True(result.IsError);
+ Assert.True(result.IsInternalError);
+ Assert.Equal(ISessionAware.SessionExceptionMessage, result.Result.AsT2.Message);
+ }
+
[Fact]
public async Task UpdatePreferences_ShouldHandleException_WhenApiCallFails()
{
diff --git a/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.UpdateSession.cs b/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.UpdateSession.cs
index 3b364b01..7bd37908 100644
--- a/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.UpdateSession.cs
+++ b/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.UpdateSession.cs
@@ -1,4 +1,5 @@
using System.Net;
+using PinguApps.Appwrite.Client.Clients;
using PinguApps.Appwrite.Shared.Tests;
using PinguApps.Appwrite.Shared.Utils;
using RichardSzalay.MockHttp;
@@ -42,6 +43,18 @@ public async Task UpdateSession_ShouldReturnSuccess_WhenApiCallSucceeds()
Assert.True(result.Success);
}
+ [Fact]
+ public async Task UpdateSession_ShouldReturnError_WhenSessionIsNull()
+ {
+ // Act
+ var result = await _appwriteClient.Account.UpdateSession();
+
+ // Assert
+ Assert.True(result.IsError);
+ Assert.True(result.IsInternalError);
+ Assert.Equal(ISessionAware.SessionExceptionMessage, result.Result.AsT2.Message);
+ }
+
[Fact]
public async Task UpdateSession_ShouldHandleException_WhenApiCallFails()
{
diff --git a/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.VerifyAuthenticator.cs b/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.VerifyAuthenticator.cs
index c10a34cc..4b2bcb8c 100644
--- a/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.VerifyAuthenticator.cs
+++ b/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.VerifyAuthenticator.cs
@@ -1,4 +1,5 @@
using System.Net;
+using PinguApps.Appwrite.Client.Clients;
using PinguApps.Appwrite.Shared.Requests;
using PinguApps.Appwrite.Shared.Tests;
using RichardSzalay.MockHttp;
@@ -55,6 +56,24 @@ public async Task VerifyAuthenticator_ShouldHitDifferentEndpoint_WhenNewTypeIsUs
Assert.Equal(1, matches);
}
+ [Fact]
+ public async Task VerifyAuthenticator_ShouldReturnError_WhenSessionIsNull()
+ {
+ // Arrange
+ var request = new VerifyAuthenticatorRequest
+ {
+ Otp = "123456"
+ };
+
+ // Act
+ var result = await _appwriteClient.Account.VerifyAuthenticator(request);
+
+ // Assert
+ Assert.True(result.IsError);
+ Assert.True(result.IsInternalError);
+ Assert.Equal(ISessionAware.SessionExceptionMessage, result.Result.AsT2.Message);
+ }
+
[Fact]
public async Task VerifyAuthenticator_ShouldHandleException_WhenApiCallFails()
{
diff --git a/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.cs b/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.cs
index 5b13235b..c42858a7 100644
--- a/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.cs
+++ b/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountClientTests.cs
@@ -1,4 +1,7 @@
using Microsoft.Extensions.DependencyInjection;
+using Moq;
+using PinguApps.Appwrite.Client.Clients;
+using PinguApps.Appwrite.Client.Internals;
using PinguApps.Appwrite.Shared.Tests;
using Refit;
using RichardSzalay.MockHttp;
@@ -23,29 +26,22 @@ public AccountClientTests()
_appwriteClient = serviceProvider.GetRequiredService();
}
-}
-
-public static class AccountTestsExtensions
-{
- public static MockedRequest ExpectedHeaders(this MockedRequest request, bool addSessionHeaders = false)
- {
- var req = request
- .WithHeaders("x-appwrite-project", Constants.ProjectId)
- .WithHeaders("x-sdk-name", Constants.SdkName)
- .WithHeaders("x-sdk-platform", "client")
- .WithHeaders("x-sdk-language", Constants.SdkLanguage)
- .WithHeaders("x-sdk-version", Constants.SdkVersion)
- .WithHeaders("x-appwrite-response-format", Constants.AppwriteResponseFormat);
-
- if (addSessionHeaders)
- return req.ExpectSessionHeaders();
-
- return req;
- }
- public static MockedRequest ExpectSessionHeaders(this MockedRequest request)
+ [Fact]
+ public void SetSession_UpdatesSession()
{
- return request
- .WithHeaders("x-appwrite-session", Constants.Session);
+ // Arrange
+ var sc = new ServiceCollection();
+ var mockAccountApi = new Mock();
+ sc.AddSingleton(mockAccountApi.Object);
+ var sp = sc.BuildServiceProvider();
+ var accountClient = new AccountClient(sp);
+ var sessionAware = accountClient as ISessionAware;
+
+ // Act
+ sessionAware.UpdateSession(Constants.Session);
+
+ // Assert
+ Assert.Equal(Constants.Session, accountClient.Session);
}
}
diff --git a/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountTestsExtensions.cs b/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountTestsExtensions.cs
new file mode 100644
index 00000000..dd6e9a7c
--- /dev/null
+++ b/tests/PinguApps.Appwrite.Client.Tests/Clients/Account/AccountTestsExtensions.cs
@@ -0,0 +1,29 @@
+using PinguApps.Appwrite.Shared.Tests;
+using RichardSzalay.MockHttp;
+
+namespace PinguApps.Appwrite.Client.Tests.Clients.Account;
+
+public static class AccountTestsExtensions
+{
+ public static MockedRequest ExpectedHeaders(this MockedRequest request, bool addSessionHeaders = false)
+ {
+ var req = request
+ .WithHeaders("x-appwrite-project", Constants.ProjectId)
+ .WithHeaders("x-sdk-name", Constants.SdkName)
+ .WithHeaders("x-sdk-platform", "client")
+ .WithHeaders("x-sdk-language", Constants.SdkLanguage)
+ .WithHeaders("x-sdk-version", Constants.SdkVersion)
+ .WithHeaders("x-appwrite-response-format", Constants.AppwriteResponseFormat);
+
+ if (addSessionHeaders)
+ return req.ExpectSessionHeaders();
+
+ return req;
+ }
+
+ public static MockedRequest ExpectSessionHeaders(this MockedRequest request)
+ {
+ return request
+ .WithHeaders("x-appwrite-session", Constants.Session);
+ }
+}
diff --git a/tests/PinguApps.Appwrite.Shared.Tests/Requests/Create2faChallengeConfirmationRequestTests.cs b/tests/PinguApps.Appwrite.Shared.Tests/Requests/Create2faChallengeConfirmationRequestTests.cs
new file mode 100644
index 00000000..0137b81e
--- /dev/null
+++ b/tests/PinguApps.Appwrite.Shared.Tests/Requests/Create2faChallengeConfirmationRequestTests.cs
@@ -0,0 +1,98 @@
+using FluentValidation;
+using PinguApps.Appwrite.Shared.Requests;
+
+namespace PinguApps.Appwrite.Shared.Tests.Requests;
+public class Create2faChallengeConfirmationRequestTests
+{
+ [Fact]
+ public void Constructor_InitializesWithExpectedValues()
+ {
+ // Arrange & Act
+ var request = new Create2faChallengeConfirmationRequest();
+
+ // Assert
+ Assert.Equal(string.Empty, request.ChallengeId);
+ Assert.Equal(string.Empty, request.Otp);
+ }
+
+ [Fact]
+ public void Properties_CanBeSet()
+ {
+ // Arrange
+ var request = new Create2faChallengeConfirmationRequest();
+ var challengeId = "Challenge";
+ var otp = "Otp";
+
+ // Act
+ request.ChallengeId = challengeId;
+ request.Otp = otp;
+
+ // Assert
+ Assert.Equal(challengeId, request.ChallengeId);
+ Assert.Equal(otp, request.Otp);
+ }
+
+ [Theory]
+ [InlineData("A string", "A string")]
+ [InlineData("123456", "123456")]
+ [InlineData("A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. ", "A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. A much longer string. ")]
+ public void IsValid_WithValidInputs_ReturnsTrue(string challenge, string otp)
+ {
+ // Arrange
+ var request = new Create2faChallengeConfirmationRequest
+ {
+ ChallengeId = challenge,
+ Otp = otp
+ };
+
+ // Act
+ var isValid = request.IsValid();
+
+ // Assert
+ Assert.True(isValid);
+ }
+
+ [Theory]
+ [InlineData("", "123456")]
+ [InlineData(null, "123456")]
+ [InlineData("123456", "")]
+ [InlineData("123456", null)]
+ public void IsValid_WithInvalidInputs_ReturnsFalse(string? challenge, string? otp)
+ {
+ // Arrange
+ var request = new Create2faChallengeConfirmationRequest
+ {
+ ChallengeId = challenge!,
+ Otp = otp!
+ };
+
+ // Act
+ var isValid = request.IsValid();
+
+ // Assert
+ Assert.False(isValid);
+ }
+
+ [Fact]
+ public void Validate_WithThrowOnFailuresTrue_ThrowsValidationExceptionOnFailure()
+ {
+ // Arrange
+ var request = new Create2faChallengeConfirmationRequest();
+
+ // Assert
+ Assert.Throws(() => request.Validate(true));
+ }
+
+ [Fact]
+ public void Validate_WithThrowOnFailuresFalse_ReturnsInvalidResultOnFailure()
+ {
+ // Arrange
+ var request = new Create2faChallengeConfirmationRequest();
+
+ // Act
+ var result = request.Validate(false);
+
+ // Assert
+ Assert.False(result.IsValid);
+ }
+}
diff --git a/tests/PinguApps.Appwrite.Shared.Tests/Requests/Create2faChallengeRequestTests.cs b/tests/PinguApps.Appwrite.Shared.Tests/Requests/Create2faChallengeRequestTests.cs
index 2170ccfd..616ae8f6 100644
--- a/tests/PinguApps.Appwrite.Shared.Tests/Requests/Create2faChallengeRequestTests.cs
+++ b/tests/PinguApps.Appwrite.Shared.Tests/Requests/Create2faChallengeRequestTests.cs
@@ -58,8 +58,6 @@ public void IsValid_WithInvalidInputs_ReturnsFalse(SecondFactor factor)
Factor = factor
};
- var ggg = (int)factor;
-
// Act
var isValid = request.IsValid();