112 lines
3.5 KiB
C#
112 lines
3.5 KiB
C#
using MongoDB.Bson;
|
|
using MongoDB.Bson.Serialization.Attributes;
|
|
|
|
namespace QuestionsApi.Models;
|
|
|
|
public static class CreditEconomy
|
|
{
|
|
public const int RollingEarningLimit = 20;
|
|
public static readonly TimeSpan EarningWindow = TimeSpan.FromHours(24);
|
|
public const string ExamTokenSku = "exam_token_1";
|
|
public const string QBankResetTokenSku = "qbank_reset_1";
|
|
public const int ExamTokenPrice = 100;
|
|
public const int QBankResetTokenPrice = 300;
|
|
|
|
public static readonly IReadOnlyList<RzStoreProduct> Products =
|
|
[
|
|
new()
|
|
{
|
|
Sku = ExamTokenSku,
|
|
Name = "Exam Simulation Token",
|
|
Description = "Starts one new full exam simulation.",
|
|
CoinPrice = ExamTokenPrice,
|
|
Grant = RzStoreGrant.ExamToken
|
|
},
|
|
new()
|
|
{
|
|
Sku = QBankResetTokenSku,
|
|
Name = "QBank Reset Token",
|
|
Description = "Makes every QBank question eligible again without erasing progress.",
|
|
CoinPrice = QBankResetTokenPrice,
|
|
Grant = RzStoreGrant.QBankResetToken
|
|
}
|
|
];
|
|
|
|
public static RzStoreProduct? FindProduct(string sku) =>
|
|
Products.FirstOrDefault(value => value.Sku.Equals(sku, StringComparison.Ordinal));
|
|
}
|
|
|
|
public enum RzStoreGrant { ExamToken, QBankResetToken }
|
|
|
|
public sealed class RzStoreProduct
|
|
{
|
|
public string Sku { get; set; } = "";
|
|
public string Name { get; set; } = "";
|
|
public string Description { get; set; } = "";
|
|
public int CoinPrice { get; set; }
|
|
public RzStoreGrant Grant { get; set; }
|
|
}
|
|
|
|
public sealed class CreditEvent
|
|
{
|
|
public string OperationId { get; set; } = "";
|
|
public DateTime CreatedUtc { get; set; }
|
|
}
|
|
|
|
public sealed class CreditPurchaseEvent
|
|
{
|
|
public string OperationId { get; set; } = "";
|
|
public string Sku { get; set; } = "";
|
|
public int CoinCost { get; set; }
|
|
public DateTime CreatedUtc { get; set; }
|
|
}
|
|
|
|
public sealed class UserCreditAccount
|
|
{
|
|
[BsonId]
|
|
[BsonRepresentation(BsonType.ObjectId)]
|
|
public string? Id { get; set; }
|
|
public string UserId { get; set; } = "";
|
|
public int Credits { get; set; }
|
|
public int ExamTokens { get; set; }
|
|
public int QBankResetTokens { get; set; }
|
|
public int BankCycle { get; set; }
|
|
public bool InitialExamGrantApplied { get; set; }
|
|
public List<CreditEvent> RecentEarnings { get; set; } = [];
|
|
public List<CreditPurchaseEvent> Purchases { get; set; } = [];
|
|
public List<string> AppliedOperations { get; set; } = [];
|
|
public DateTime UpdatedUtc { get; set; } = DateTime.UtcNow;
|
|
}
|
|
|
|
public sealed class CreditStatusResponse
|
|
{
|
|
public int Credits { get; set; }
|
|
public int EarnedInRollingWindow { get; set; }
|
|
public int RemainingEarningCapacity { get; set; }
|
|
public int RollingWindowHours { get; set; } = 24;
|
|
public int ExamTokens { get; set; }
|
|
public int QBankResetTokens { get; set; }
|
|
public int BankCycle { get; set; }
|
|
public IReadOnlyList<RzStoreProduct> Products { get; set; } = CreditEconomy.Products;
|
|
}
|
|
|
|
public sealed class CreditPurchaseRequest
|
|
{
|
|
public string Sku { get; set; } = "";
|
|
public string OperationId { get; set; } = "";
|
|
}
|
|
|
|
public sealed class QBankResetRequest
|
|
{
|
|
public string Confirmation { get; set; } = "";
|
|
public string OperationId { get; set; } = "";
|
|
}
|
|
|
|
public enum CreditOperationResult { Succeeded, InsufficientCredits, InsufficientTokens, OperationConflict }
|
|
|
|
public sealed class CreditOperationResponse
|
|
{
|
|
public CreditOperationResult Result { get; set; }
|
|
public CreditStatusResponse Status { get; set; } = new();
|
|
}
|