mirror of
https://github.com/DuendeSoftware/products
synced 2026-05-24 09:28:24 +00:00
Merge pull request #2279 from DuendeSoftware/pg/bff-trial-mode
Introduce BFF Trial Mode
This commit is contained in:
commit
7703ed610b
9 changed files with 229 additions and 270 deletions
|
|
@ -97,6 +97,11 @@ public static class BffBuilderExtensions
|
|||
builder.Services
|
||||
.AddSingleton<IPostConfigureOptions<OpenIdConnectOptions>, PostConfigureOidcOptionsForSilentLogin>();
|
||||
|
||||
builder.Services.AddSingleton<TrialModeAuthenticatedSessionTracker>();
|
||||
builder.Services
|
||||
.AddSingleton<IPostConfigureOptions<CookieAuthenticationOptions>,
|
||||
PostConfigureApplicationCookieTrialModeCheck>();
|
||||
|
||||
AddBffMetrics(builder);
|
||||
|
||||
// wrap ASP.NET Core
|
||||
|
|
|
|||
|
|
@ -44,7 +44,10 @@ internal class LicenseAccessor(GetLicenseKey getLicenseKey, ILogger<LicenseAcces
|
|||
}
|
||||
|
||||
var licenseClaims = ValidateKey(key);
|
||||
return new License(new ClaimsPrincipal(new ClaimsIdentity(licenseClaims)));
|
||||
return new License(new ClaimsPrincipal(new ClaimsIdentity(licenseClaims)))
|
||||
{
|
||||
IsConfigured = licenseClaims.Length != 0
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -14,6 +14,7 @@ internal class LicenseValidator(ILogger<LicenseValidator> logger, License licens
|
|||
}
|
||||
|
||||
private bool? _licenseCheckResult;
|
||||
internal const int MaximumAllowedSessionsInTrialMode = 5;
|
||||
|
||||
public bool CheckLicense()
|
||||
{
|
||||
|
|
@ -34,13 +35,19 @@ internal class LicenseValidator(ILogger<LicenseValidator> logger, License licens
|
|||
return false;
|
||||
}
|
||||
|
||||
//An expired license is still considered a valid license.
|
||||
if (license.Expiration <= timeProvider.GetUtcNow())
|
||||
{
|
||||
logger.LicenseHasExpired(LogLevel.Error, license.Expiration, license.ContactInfo ?? "",
|
||||
license.CompanyName ?? "");
|
||||
return false;
|
||||
logger.LicenseHasExpired(LogLevel.Warning, license.Expiration, license.ContactInfo,
|
||||
license.CompanyName);
|
||||
}
|
||||
|
||||
logger.LicenseDetails(
|
||||
LogLevel.Debug,
|
||||
license.Expiration,
|
||||
license.ContactInfo,
|
||||
license.CompanyName);
|
||||
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -9,82 +9,48 @@
|
|||
// {
|
||||
// [LoggerMessage(
|
||||
// Message = """
|
||||
// Duende BFF Security Framework License information:
|
||||
// - Edition: {Edition}
|
||||
// - Expiration: {ExpirationDate}
|
||||
// - LicenseContact: {LicenseContact}
|
||||
// - LicenseCompany: {licenseCompany}
|
||||
// - Number of frontends licensed: {NumberOfFrontends}
|
||||
// """)]
|
||||
// public static partial void LicenseDetails(this ILogger logger, LogLevel level, string? edition, DateTimeOffset? expirationDate, string licenseContact, string licenseCompany, string? numberOfFrontends);
|
||||
// Duende Software License information:
|
||||
// - Expiration: {ExpirationDate}
|
||||
// - LicenseContact: {LicenseContact}
|
||||
// - LicenseCompany: {licenseCompany}
|
||||
// """)]
|
||||
// public static partial void LicenseDetails(this ILogger logger, LogLevel level,
|
||||
// DateTimeOffset? expirationDate, string licenseContact, string licenseCompany);
|
||||
//
|
||||
// [LoggerMessage(
|
||||
// Message = $$"""
|
||||
// Your license for the Duende Software has expired on {ExpirationDate}.
|
||||
// Please contact {licenseContact} from {licenseCompany} to obtain a valid license for Duende software,
|
||||
// or start a conversation with us: https://duende.link/l/bff/contact
|
||||
// Message = """
|
||||
// Your license for the Duende software has expired on {ExpirationDate}.
|
||||
// Please contact {licenseContact} from {licenseCompany} to obtain a valid license for Duende software,
|
||||
// or start a conversation with us: https://duende.link/l/bff/contact
|
||||
//
|
||||
// See https://duende.link/l/bff/expired for more information.
|
||||
// """)]
|
||||
// public static partial void LicenseHasExpired(this ILogger logger, LogLevel level, DateTimeOffset? expirationDate, string licenseContact, string licenseCompany);
|
||||
// See https://duende.link/l/bff/expired for more information.
|
||||
// """)]
|
||||
// public static partial void LicenseHasExpired(this ILogger logger, LogLevel level, DateTimeOffset? expirationDate,
|
||||
// string licenseContact, string licenseCompany);
|
||||
//
|
||||
//
|
||||
// [LoggerMessage(
|
||||
// message: """
|
||||
// You do not have a valid license key for the Duende software.
|
||||
// This is allowed for development and testing scenarios.
|
||||
// If you are running in production you are required to have a licensed version.
|
||||
// Please start a conversation with us: https://duende.link/l/contact"
|
||||
// """)]
|
||||
// Message = """
|
||||
// You do not have a valid license key for the Duende software.
|
||||
// BFF will run in trial mode. This is allowed for development and testing scenarios.
|
||||
//
|
||||
// If you are running in production you are required to have a licensed version.
|
||||
// Please start a conversation with us: https://duende.link/l/bff/contact"
|
||||
// """)]
|
||||
// public static partial void NoValidLicense(this ILogger logger, LogLevel logLevel);
|
||||
//
|
||||
// [LoggerMessage(
|
||||
// message: """
|
||||
// Your license key does not include the BFF feature.
|
||||
// BFF will run in trial mode. It will limit the number of active sessions to 5.
|
||||
// Please contact {LicenseContact} from {LicenseCompany} to obtain a valid license for the Duende software,
|
||||
// or start a conversation with us: https://duende.link/l/bff/contact
|
||||
// Message = """
|
||||
// BFF is running in trial mode. The maximum number of allowed authenticated sessions ({MaximumAllowedSessionsInTrialMode}) has been exceeded.
|
||||
//
|
||||
// See https://duende.link/l/bff/trial for more information.
|
||||
// """)]
|
||||
// public static partial void NotLicensedForBff(this ILogger logger, LogLevel logLevel, string licenseContact, string licenseCompany);
|
||||
// See https://duende.link/l/bff/trial for more information.
|
||||
// """)]
|
||||
// public static partial void TrialModeWarning(this ILogger logger, LogLevel logLevel,
|
||||
// int maximumAllowedSessionsInTrialMode);
|
||||
//
|
||||
// [LoggerMessage(
|
||||
// message: "Error validating the license key." +
|
||||
// "If you are running in production you are required to have a licensed version. " +
|
||||
// "Please start a conversation with us: https://duende.link/l/bff/contact")]
|
||||
// Message = "Error validating the license key." +
|
||||
// "If you are running in production you are required to have a licensed version. " +
|
||||
// "Please start a conversation with us: https://duende.link/l/bff/contact")]
|
||||
// public static partial void ErrorValidatingLicenseKey(this ILogger logger, LogLevel logLevel, Exception ex);
|
||||
//
|
||||
// [LoggerMessage(
|
||||
// message: """
|
||||
// Frontend #{FrontendsUsed} with name {FrontendName} was added. The license allows for unlimited frontends.
|
||||
// """)]
|
||||
// public static partial void UnlimitedFrontends(this ILogger logger, LogLevel logLevel, string frontendName,
|
||||
// int frontendsUsed);
|
||||
// [LoggerMessage(
|
||||
// message: """
|
||||
// Frontend {FrontendName} was added. Currently using {frontendsUsed} of {frontendLimit} in the BFF License.
|
||||
// """)]
|
||||
// public static partial void FrontendAdded(this ILogger logger, LogLevel logLevel, string frontendName,
|
||||
// int frontendsUsed, int frontendLimit);
|
||||
//
|
||||
// [LoggerMessage(
|
||||
// message: """
|
||||
// Frontend {FrontendName} was added. This exceeds the maximum number of frontends allowed by your license.
|
||||
// Currently using {frontendsUsed} of {frontendLimit} in the BFF License.
|
||||
//
|
||||
// See https://duende.link/l/bff/threshold for more information.
|
||||
// """)]
|
||||
// public static partial void FrontendLimitExceeded(this ILogger logger, LogLevel logLevel, string frontendName,
|
||||
// int frontendsUsed, int frontendLimit);
|
||||
//
|
||||
// [LoggerMessage(
|
||||
// message: """
|
||||
// Frontend {FrontendName} was added. However, your current license does not support multiple frontends.
|
||||
// If you are running in production you are required to have a license for each frontend.
|
||||
// Please start a conversation with us: https://duende.link/l/bff/contact
|
||||
//
|
||||
// See https://duende.link/l/bff/threshold for more information.
|
||||
// """)]
|
||||
// public static partial void NotLicensedForMultiFrontend(this ILogger logger, LogLevel logLevel, string frontendName);
|
||||
// }
|
||||
|
|
|
|||
|
|
@ -0,0 +1,21 @@
|
|||
// Copyright (c) Duende Software. All rights reserved.
|
||||
// See LICENSE in the project root for license information.
|
||||
|
||||
using System.Collections.Concurrent;
|
||||
|
||||
namespace Duende.Bff.Licensing;
|
||||
|
||||
internal class TrialModeAuthenticatedSessionTracker
|
||||
{
|
||||
private readonly ConcurrentDictionary<string, byte> _authenticatedSessions = new();
|
||||
|
||||
public int UniqueAuthenticatedSessions => _authenticatedSessions.Count;
|
||||
|
||||
public void RecordAuthenticatedSession(string subjectId)
|
||||
{
|
||||
if (_authenticatedSessions.Count <= LicenseValidator.MaximumAllowedSessionsInTrialMode)
|
||||
{
|
||||
_authenticatedSessions.TryAdd(subjectId, 0);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -90,10 +90,10 @@ namespace Duende.Bff.Licensing
|
|||
internal static class LicensingLogMessages
|
||||
{
|
||||
/// <summary>
|
||||
/// Logs "Duende BFF Security Framework License information:\r\n - Edition: {Edition}\r\n - Expiration: {ExpirationDate}\r\n - LicenseContact: {LicenseContact}\r\n - LicenseCompany: {licenseCompany}\r\n - Number of frontends licensed: {NumberOfFrontends}".
|
||||
/// Logs "Duende Software License information:\r\n - Expiration: {ExpirationDate}\r\n - LicenseContact: {LicenseContact}\r\n - LicenseCompany: {licenseCompany}".
|
||||
/// </summary>
|
||||
[global::System.CodeDom.Compiler.GeneratedCodeAttribute("Microsoft.Gen.Logging", "10.0.0.0")]
|
||||
public static void LicenseDetails(this global::Microsoft.Extensions.Logging.ILogger logger, global::Microsoft.Extensions.Logging.LogLevel level, string? edition, global::System.DateTimeOffset? expirationDate, string licenseContact, string licenseCompany, string? numberOfFrontends)
|
||||
public static void LicenseDetails(this global::Microsoft.Extensions.Logging.ILogger logger, global::Microsoft.Extensions.Logging.LogLevel level, global::System.DateTimeOffset? expirationDate, string licenseContact, string licenseCompany)
|
||||
{
|
||||
if (!logger.IsEnabled(level))
|
||||
{
|
||||
|
|
@ -102,13 +102,11 @@ namespace Duende.Bff.Licensing
|
|||
|
||||
var state = global::Microsoft.Extensions.Logging.LoggerMessageHelper.ThreadLocalState;
|
||||
|
||||
_ = state.ReserveTagSpace(6);
|
||||
state.TagArray[5] = new("{OriginalFormat}", "Duende BFF Security Framework License information:\r\n - Edition: {Edition}\r\n - Expiration: {ExpirationDate}\r\n - LicenseContact: {LicenseContact}\r\n - LicenseCompany: {licenseCompany}\r\n - Number of frontends licensed: {NumberOfFrontends}");
|
||||
state.TagArray[4] = new("Edition", edition);
|
||||
state.TagArray[3] = new("ExpirationDate", expirationDate);
|
||||
state.TagArray[2] = new("LicenseContact", licenseContact);
|
||||
state.TagArray[1] = new("licenseCompany", licenseCompany);
|
||||
state.TagArray[0] = new("NumberOfFrontends", numberOfFrontends);
|
||||
_ = state.ReserveTagSpace(4);
|
||||
state.TagArray[3] = new("{OriginalFormat}", "Duende Software License information:\r\n - Expiration: {ExpirationDate}\r\n - LicenseContact: {LicenseContact}\r\n - LicenseCompany: {licenseCompany}");
|
||||
state.TagArray[2] = new("ExpirationDate", expirationDate);
|
||||
state.TagArray[1] = new("LicenseContact", licenseContact);
|
||||
state.TagArray[0] = new("licenseCompany", licenseCompany);
|
||||
|
||||
logger.Log(
|
||||
level,
|
||||
|
|
@ -117,15 +115,13 @@ namespace Duende.Bff.Licensing
|
|||
null,
|
||||
[global::System.CodeDom.Compiler.GeneratedCodeAttribute("Microsoft.Gen.Logging", "10.0.0.0")] static string (s, _) =>
|
||||
{
|
||||
var edition = s.TagArray[4].Value ?? "(null)";
|
||||
var expirationDate = s.TagArray[3].Value ?? "(null)";
|
||||
var licenseContact = s.TagArray[2].Value ?? "(null)";
|
||||
var licenseCompany = s.TagArray[1].Value ?? "(null)";
|
||||
var numberOfFrontends = s.TagArray[0].Value ?? "(null)";
|
||||
var expirationDate = s.TagArray[2].Value ?? "(null)";
|
||||
var licenseContact = s.TagArray[1].Value ?? "(null)";
|
||||
var licenseCompany = s.TagArray[0].Value ?? "(null)";
|
||||
#if NET
|
||||
return string.Create(global::System.Globalization.CultureInfo.InvariantCulture, $"Duende BFF Security Framework License information:\r\n - Edition: {edition}\r\n - Expiration: {expirationDate}\r\n - LicenseContact: {licenseContact}\r\n - LicenseCompany: {licenseCompany}\r\n - Number of frontends licensed: {numberOfFrontends}");
|
||||
return string.Create(global::System.Globalization.CultureInfo.InvariantCulture, $"Duende Software License information:\r\n - Expiration: {expirationDate}\r\n - LicenseContact: {licenseContact}\r\n - LicenseCompany: {licenseCompany}");
|
||||
#else
|
||||
return global::System.FormattableString.Invariant($"Duende BFF Security Framework License information:\r\n - Edition: {edition}\r\n - Expiration: {expirationDate}\r\n - LicenseContact: {licenseContact}\r\n - LicenseCompany: {licenseCompany}\r\n - Number of frontends licensed: {numberOfFrontends}");
|
||||
return global::System.FormattableString.Invariant($"Duende Software License information:\r\n - Expiration: {expirationDate}\r\n - LicenseContact: {licenseContact}\r\n - LicenseCompany: {licenseCompany}");
|
||||
#endif
|
||||
});
|
||||
|
||||
|
|
@ -133,7 +129,7 @@ namespace Duende.Bff.Licensing
|
|||
}
|
||||
|
||||
/// <summary>
|
||||
/// Logs "Your license for the Duende Software has expired on {ExpirationDate}.\r\nPlease contact {licenseContact} from {licenseCompany} to obtain a valid license for Duende software,\r\nor start a conversation with us: https://duende.link/l/bff/contact\r\n\r\nSee https://duende.link/l/bff/expired for more information.".
|
||||
/// Logs "Your license for the Duende software has expired on {ExpirationDate}.\r\nPlease contact {licenseContact} from {licenseCompany} to obtain a valid license for Duende software,\r\nor start a conversation with us: https://duende.link/l/bff/contact\r\n\r\nSee https://duende.link/l/bff/expired for more information.".
|
||||
/// </summary>
|
||||
[global::System.CodeDom.Compiler.GeneratedCodeAttribute("Microsoft.Gen.Logging", "10.0.0.0")]
|
||||
public static void LicenseHasExpired(this global::Microsoft.Extensions.Logging.ILogger logger, global::Microsoft.Extensions.Logging.LogLevel level, global::System.DateTimeOffset? expirationDate, string licenseContact, string licenseCompany)
|
||||
|
|
@ -146,7 +142,7 @@ namespace Duende.Bff.Licensing
|
|||
var state = global::Microsoft.Extensions.Logging.LoggerMessageHelper.ThreadLocalState;
|
||||
|
||||
_ = state.ReserveTagSpace(4);
|
||||
state.TagArray[3] = new("{OriginalFormat}", "Your license for the Duende Software has expired on {ExpirationDate}.\r\nPlease contact {licenseContact} from {licenseCompany} to obtain a valid license for Duende software,\r\nor start a conversation with us: https://duende.link/l/bff/contact\r\n\r\nSee https://duende.link/l/bff/expired for more information.");
|
||||
state.TagArray[3] = new("{OriginalFormat}", "Your license for the Duende software has expired on {ExpirationDate}.\r\nPlease contact {licenseContact} from {licenseCompany} to obtain a valid license for Duende software,\r\nor start a conversation with us: https://duende.link/l/bff/contact\r\n\r\nSee https://duende.link/l/bff/expired for more information.");
|
||||
state.TagArray[2] = new("ExpirationDate", expirationDate);
|
||||
state.TagArray[1] = new("licenseContact", licenseContact);
|
||||
state.TagArray[0] = new("licenseCompany", licenseCompany);
|
||||
|
|
@ -162,9 +158,9 @@ namespace Duende.Bff.Licensing
|
|||
var licenseContact = s.TagArray[1].Value ?? "(null)";
|
||||
var licenseCompany = s.TagArray[0].Value ?? "(null)";
|
||||
#if NET
|
||||
return string.Create(global::System.Globalization.CultureInfo.InvariantCulture, $"Your license for the Duende Software has expired on {expirationDate}.\r\nPlease contact {licenseContact} from {licenseCompany} to obtain a valid license for Duende software,\r\nor start a conversation with us: https://duende.link/l/bff/contact\r\n\r\nSee https://duende.link/l/bff/expired for more information.");
|
||||
return string.Create(global::System.Globalization.CultureInfo.InvariantCulture, $"Your license for the Duende software has expired on {expirationDate}.\r\nPlease contact {licenseContact} from {licenseCompany} to obtain a valid license for Duende software,\r\nor start a conversation with us: https://duende.link/l/bff/contact\r\n\r\nSee https://duende.link/l/bff/expired for more information.");
|
||||
#else
|
||||
return global::System.FormattableString.Invariant($"Your license for the Duende Software has expired on {expirationDate}.\r\nPlease contact {licenseContact} from {licenseCompany} to obtain a valid license for Duende software,\r\nor start a conversation with us: https://duende.link/l/bff/contact\r\n\r\nSee https://duende.link/l/bff/expired for more information.");
|
||||
return global::System.FormattableString.Invariant($"Your license for the Duende software has expired on {expirationDate}.\r\nPlease contact {licenseContact} from {licenseCompany} to obtain a valid license for Duende software,\r\nor start a conversation with us: https://duende.link/l/bff/contact\r\n\r\nSee https://duende.link/l/bff/expired for more information.");
|
||||
#endif
|
||||
});
|
||||
|
||||
|
|
@ -172,7 +168,7 @@ namespace Duende.Bff.Licensing
|
|||
}
|
||||
|
||||
/// <summary>
|
||||
/// Logs "You do not have a valid license key for the Duende software.\r\nThis is allowed for development and testing scenarios.\r\nIf you are running in production you are required to have a licensed version.\r\nPlease start a conversation with us: https://duende.link/l/contact"".
|
||||
/// Logs "You do not have a valid license key for the Duende software.\r\nBFF will run in trial mode. This is allowed for development and testing scenarios.\r\n\r\nIf you are running in production you are required to have a licensed version.\r\nPlease start a conversation with us: https://duende.link/l/bff/contact"".
|
||||
/// </summary>
|
||||
[global::System.CodeDom.Compiler.GeneratedCodeAttribute("Microsoft.Gen.Logging", "10.0.0.0")]
|
||||
public static void NoValidLicense(this global::Microsoft.Extensions.Logging.ILogger logger, global::Microsoft.Extensions.Logging.LogLevel logLevel)
|
||||
|
|
@ -185,7 +181,7 @@ namespace Duende.Bff.Licensing
|
|||
var state = global::Microsoft.Extensions.Logging.LoggerMessageHelper.ThreadLocalState;
|
||||
|
||||
_ = state.ReserveTagSpace(1);
|
||||
state.TagArray[0] = new("{OriginalFormat}", "You do not have a valid license key for the Duende software.\r\nThis is allowed for development and testing scenarios.\r\nIf you are running in production you are required to have a licensed version.\r\nPlease start a conversation with us: https://duende.link/l/contact\"");
|
||||
state.TagArray[0] = new("{OriginalFormat}", "You do not have a valid license key for the Duende software.\r\nBFF will run in trial mode. This is allowed for development and testing scenarios.\r\n\r\nIf you are running in production you are required to have a licensed version.\r\nPlease start a conversation with us: https://duende.link/l/bff/contact\"");
|
||||
|
||||
logger.Log(
|
||||
logLevel,
|
||||
|
|
@ -194,17 +190,17 @@ namespace Duende.Bff.Licensing
|
|||
null,
|
||||
[global::System.CodeDom.Compiler.GeneratedCodeAttribute("Microsoft.Gen.Logging", "10.0.0.0")] static string (s, _) =>
|
||||
{
|
||||
return "You do not have a valid license key for the Duende software.\r\nThis is allowed for development and testing scenarios.\r\nIf you are running in production you are required to have a licensed version.\r\nPlease start a conversation with us: https://duende.link/l/contact\"";
|
||||
return "You do not have a valid license key for the Duende software.\r\nBFF will run in trial mode. This is allowed for development and testing scenarios.\r\n\r\nIf you are running in production you are required to have a licensed version.\r\nPlease start a conversation with us: https://duende.link/l/bff/contact\"";
|
||||
});
|
||||
|
||||
state.Clear();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Logs "Your license key does not include the BFF feature.\r\nBFF will run in trial mode. It will limit the number of active sessions to 5.\r\nPlease contact {LicenseContact} from {LicenseCompany} to obtain a valid license for the Duende software,\r\nor start a conversation with us: https://duende.link/l/bff/contact\r\n\r\nSee https://duende.link/l/bff/trial for more information.".
|
||||
/// Logs "BFF is running in trial mode. The maximum number of allowed authenticated sessions ({MaximumAllowedSessionsInTrialMode}) has been exceeded.\r\n\r\nSee https://duende.link/l/bff/trial for more information.".
|
||||
/// </summary>
|
||||
[global::System.CodeDom.Compiler.GeneratedCodeAttribute("Microsoft.Gen.Logging", "10.0.0.0")]
|
||||
public static void NotLicensedForBff(this global::Microsoft.Extensions.Logging.ILogger logger, global::Microsoft.Extensions.Logging.LogLevel logLevel, string licenseContact, string licenseCompany)
|
||||
public static void TrialModeWarning(this global::Microsoft.Extensions.Logging.ILogger logger, global::Microsoft.Extensions.Logging.LogLevel logLevel, int maximumAllowedSessionsInTrialMode)
|
||||
{
|
||||
if (!logger.IsEnabled(logLevel))
|
||||
{
|
||||
|
|
@ -213,24 +209,22 @@ namespace Duende.Bff.Licensing
|
|||
|
||||
var state = global::Microsoft.Extensions.Logging.LoggerMessageHelper.ThreadLocalState;
|
||||
|
||||
_ = state.ReserveTagSpace(3);
|
||||
state.TagArray[2] = new("{OriginalFormat}", "Your license key does not include the BFF feature.\r\nBFF will run in trial mode. It will limit the number of active sessions to 5.\r\nPlease contact {LicenseContact} from {LicenseCompany} to obtain a valid license for the Duende software,\r\nor start a conversation with us: https://duende.link/l/bff/contact\r\n\r\nSee https://duende.link/l/bff/trial for more information.");
|
||||
state.TagArray[1] = new("LicenseContact", licenseContact);
|
||||
state.TagArray[0] = new("LicenseCompany", licenseCompany);
|
||||
_ = state.ReserveTagSpace(2);
|
||||
state.TagArray[1] = new("{OriginalFormat}", "BFF is running in trial mode. The maximum number of allowed authenticated sessions ({MaximumAllowedSessionsInTrialMode}) has been exceeded.\r\n\r\nSee https://duende.link/l/bff/trial for more information.");
|
||||
state.TagArray[0] = new("MaximumAllowedSessionsInTrialMode", maximumAllowedSessionsInTrialMode);
|
||||
|
||||
logger.Log(
|
||||
logLevel,
|
||||
new(792057768, nameof(NotLicensedForBff)),
|
||||
new(875645872, nameof(TrialModeWarning)),
|
||||
state,
|
||||
null,
|
||||
[global::System.CodeDom.Compiler.GeneratedCodeAttribute("Microsoft.Gen.Logging", "10.0.0.0")] static string (s, _) =>
|
||||
{
|
||||
var licenseContact = s.TagArray[1].Value ?? "(null)";
|
||||
var licenseCompany = s.TagArray[0].Value ?? "(null)";
|
||||
var maximumAllowedSessionsInTrialMode = s.TagArray[0].Value;
|
||||
#if NET
|
||||
return string.Create(global::System.Globalization.CultureInfo.InvariantCulture, $"Your license key does not include the BFF feature.\r\nBFF will run in trial mode. It will limit the number of active sessions to 5.\r\nPlease contact {licenseContact} from {licenseCompany} to obtain a valid license for the Duende software,\r\nor start a conversation with us: https://duende.link/l/bff/contact\r\n\r\nSee https://duende.link/l/bff/trial for more information.");
|
||||
return string.Create(global::System.Globalization.CultureInfo.InvariantCulture, $"BFF is running in trial mode. The maximum number of allowed authenticated sessions ({maximumAllowedSessionsInTrialMode}) has been exceeded.\r\n\r\nSee https://duende.link/l/bff/trial for more information.");
|
||||
#else
|
||||
return global::System.FormattableString.Invariant($"Your license key does not include the BFF feature.\r\nBFF will run in trial mode. It will limit the number of active sessions to 5.\r\nPlease contact {licenseContact} from {licenseCompany} to obtain a valid license for the Duende software,\r\nor start a conversation with us: https://duende.link/l/bff/contact\r\n\r\nSee https://duende.link/l/bff/trial for more information.");
|
||||
return global::System.FormattableString.Invariant($"BFF is running in trial mode. The maximum number of allowed authenticated sessions ({maximumAllowedSessionsInTrialMode}) has been exceeded.\r\n\r\nSee https://duende.link/l/bff/trial for more information.");
|
||||
#endif
|
||||
});
|
||||
|
||||
|
|
@ -265,156 +259,6 @@ namespace Duende.Bff.Licensing
|
|||
|
||||
state.Clear();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Logs "Frontend #{FrontendsUsed} with name {FrontendName} was added. The license allows for unlimited frontends.".
|
||||
/// </summary>
|
||||
[global::System.CodeDom.Compiler.GeneratedCodeAttribute("Microsoft.Gen.Logging", "10.0.0.0")]
|
||||
public static void UnlimitedFrontends(this global::Microsoft.Extensions.Logging.ILogger logger, global::Microsoft.Extensions.Logging.LogLevel logLevel, string frontendName, int frontendsUsed)
|
||||
{
|
||||
if (!logger.IsEnabled(logLevel))
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
var state = global::Microsoft.Extensions.Logging.LoggerMessageHelper.ThreadLocalState;
|
||||
|
||||
_ = state.ReserveTagSpace(3);
|
||||
state.TagArray[2] = new("{OriginalFormat}", "Frontend #{FrontendsUsed} with name {FrontendName} was added. The license allows for unlimited frontends.");
|
||||
state.TagArray[1] = new("FrontendName", frontendName);
|
||||
state.TagArray[0] = new("FrontendsUsed", frontendsUsed);
|
||||
|
||||
logger.Log(
|
||||
logLevel,
|
||||
new(1958275515, nameof(UnlimitedFrontends)),
|
||||
state,
|
||||
null,
|
||||
[global::System.CodeDom.Compiler.GeneratedCodeAttribute("Microsoft.Gen.Logging", "10.0.0.0")] static string (s, _) =>
|
||||
{
|
||||
var frontendName = s.TagArray[1].Value ?? "(null)";
|
||||
var frontendsUsed = s.TagArray[0].Value;
|
||||
#if NET
|
||||
return string.Create(global::System.Globalization.CultureInfo.InvariantCulture, $"Frontend #{frontendsUsed} with name {frontendName} was added. The license allows for unlimited frontends.");
|
||||
#else
|
||||
return global::System.FormattableString.Invariant($"Frontend #{frontendsUsed} with name {frontendName} was added. The license allows for unlimited frontends.");
|
||||
#endif
|
||||
});
|
||||
|
||||
state.Clear();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Logs "Frontend {FrontendName} was added. Currently using {frontendsUsed} of {frontendLimit} in the BFF License.".
|
||||
/// </summary>
|
||||
[global::System.CodeDom.Compiler.GeneratedCodeAttribute("Microsoft.Gen.Logging", "10.0.0.0")]
|
||||
public static void FrontendAdded(this global::Microsoft.Extensions.Logging.ILogger logger, global::Microsoft.Extensions.Logging.LogLevel logLevel, string frontendName, int frontendsUsed, int frontendLimit)
|
||||
{
|
||||
if (!logger.IsEnabled(logLevel))
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
var state = global::Microsoft.Extensions.Logging.LoggerMessageHelper.ThreadLocalState;
|
||||
|
||||
_ = state.ReserveTagSpace(4);
|
||||
state.TagArray[3] = new("{OriginalFormat}", "Frontend {FrontendName} was added. Currently using {frontendsUsed} of {frontendLimit} in the BFF License.");
|
||||
state.TagArray[2] = new("FrontendName", frontendName);
|
||||
state.TagArray[1] = new("frontendsUsed", frontendsUsed);
|
||||
state.TagArray[0] = new("frontendLimit", frontendLimit);
|
||||
|
||||
logger.Log(
|
||||
logLevel,
|
||||
new(231888333, nameof(FrontendAdded)),
|
||||
state,
|
||||
null,
|
||||
[global::System.CodeDom.Compiler.GeneratedCodeAttribute("Microsoft.Gen.Logging", "10.0.0.0")] static string (s, _) =>
|
||||
{
|
||||
var frontendName = s.TagArray[2].Value ?? "(null)";
|
||||
var frontendsUsed = s.TagArray[1].Value;
|
||||
var frontendLimit = s.TagArray[0].Value;
|
||||
#if NET
|
||||
return string.Create(global::System.Globalization.CultureInfo.InvariantCulture, $"Frontend {frontendName} was added. Currently using {frontendsUsed} of {frontendLimit} in the BFF License.");
|
||||
#else
|
||||
return global::System.FormattableString.Invariant($"Frontend {frontendName} was added. Currently using {frontendsUsed} of {frontendLimit} in the BFF License.");
|
||||
#endif
|
||||
});
|
||||
|
||||
state.Clear();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Logs "Frontend {FrontendName} was added. This exceeds the maximum number of frontends allowed by your license.\r\nCurrently using {frontendsUsed} of {frontendLimit} in the BFF License.\r\n\r\nSee https://duende.link/l/bff/threshold for more information.".
|
||||
/// </summary>
|
||||
[global::System.CodeDom.Compiler.GeneratedCodeAttribute("Microsoft.Gen.Logging", "10.0.0.0")]
|
||||
public static void FrontendLimitExceeded(this global::Microsoft.Extensions.Logging.ILogger logger, global::Microsoft.Extensions.Logging.LogLevel logLevel, string frontendName, int frontendsUsed, int frontendLimit)
|
||||
{
|
||||
if (!logger.IsEnabled(logLevel))
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
var state = global::Microsoft.Extensions.Logging.LoggerMessageHelper.ThreadLocalState;
|
||||
|
||||
_ = state.ReserveTagSpace(4);
|
||||
state.TagArray[3] = new("{OriginalFormat}", "Frontend {FrontendName} was added. This exceeds the maximum number of frontends allowed by your license.\r\nCurrently using {frontendsUsed} of {frontendLimit} in the BFF License.\r\n\r\nSee https://duende.link/l/bff/threshold for more information.");
|
||||
state.TagArray[2] = new("FrontendName", frontendName);
|
||||
state.TagArray[1] = new("frontendsUsed", frontendsUsed);
|
||||
state.TagArray[0] = new("frontendLimit", frontendLimit);
|
||||
|
||||
logger.Log(
|
||||
logLevel,
|
||||
new(438656937, nameof(FrontendLimitExceeded)),
|
||||
state,
|
||||
null,
|
||||
[global::System.CodeDom.Compiler.GeneratedCodeAttribute("Microsoft.Gen.Logging", "10.0.0.0")] static string (s, _) =>
|
||||
{
|
||||
var frontendName = s.TagArray[2].Value ?? "(null)";
|
||||
var frontendsUsed = s.TagArray[1].Value;
|
||||
var frontendLimit = s.TagArray[0].Value;
|
||||
#if NET
|
||||
return string.Create(global::System.Globalization.CultureInfo.InvariantCulture, $"Frontend {frontendName} was added. This exceeds the maximum number of frontends allowed by your license.\r\nCurrently using {frontendsUsed} of {frontendLimit} in the BFF License.\r\n\r\nSee https://duende.link/l/bff/threshold for more information.");
|
||||
#else
|
||||
return global::System.FormattableString.Invariant($"Frontend {frontendName} was added. This exceeds the maximum number of frontends allowed by your license.\r\nCurrently using {frontendsUsed} of {frontendLimit} in the BFF License.\r\n\r\nSee https://duende.link/l/bff/threshold for more information.");
|
||||
#endif
|
||||
});
|
||||
|
||||
state.Clear();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Logs "Frontend {FrontendName} was added. However, your current license does not support multiple frontends.\r\nIf you are running in production you are required to have a license for each frontend.\r\nPlease start a conversation with us: https://duende.link/l/bff/contact\r\n\r\nSee https://duende.link/l/bff/threshold for more information.".
|
||||
/// </summary>
|
||||
[global::System.CodeDom.Compiler.GeneratedCodeAttribute("Microsoft.Gen.Logging", "10.0.0.0")]
|
||||
public static void NotLicensedForMultiFrontend(this global::Microsoft.Extensions.Logging.ILogger logger, global::Microsoft.Extensions.Logging.LogLevel logLevel, string frontendName)
|
||||
{
|
||||
if (!logger.IsEnabled(logLevel))
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
var state = global::Microsoft.Extensions.Logging.LoggerMessageHelper.ThreadLocalState;
|
||||
|
||||
_ = state.ReserveTagSpace(2);
|
||||
state.TagArray[1] = new("{OriginalFormat}", "Frontend {FrontendName} was added. However, your current license does not support multiple frontends.\r\nIf you are running in production you are required to have a license for each frontend.\r\nPlease start a conversation with us: https://duende.link/l/bff/contact\r\n\r\nSee https://duende.link/l/bff/threshold for more information.");
|
||||
state.TagArray[0] = new("FrontendName", frontendName);
|
||||
|
||||
logger.Log(
|
||||
logLevel,
|
||||
new(289456605, nameof(NotLicensedForMultiFrontend)),
|
||||
state,
|
||||
null,
|
||||
[global::System.CodeDom.Compiler.GeneratedCodeAttribute("Microsoft.Gen.Logging", "10.0.0.0")] static string (s, _) =>
|
||||
{
|
||||
var frontendName = s.TagArray[0].Value ?? "(null)";
|
||||
#if NET
|
||||
return string.Create(global::System.Globalization.CultureInfo.InvariantCulture, $"Frontend {frontendName} was added. However, your current license does not support multiple frontends.\r\nIf you are running in production you are required to have a license for each frontend.\r\nPlease start a conversation with us: https://duende.link/l/bff/contact\r\n\r\nSee https://duende.link/l/bff/threshold for more information.");
|
||||
#else
|
||||
return global::System.FormattableString.Invariant($"Frontend {frontendName} was added. However, your current license does not support multiple frontends.\r\nIf you are running in production you are required to have a license for each frontend.\r\nPlease start a conversation with us: https://duende.link/l/bff/contact\r\n\r\nSee https://duende.link/l/bff/threshold for more information.");
|
||||
#endif
|
||||
});
|
||||
|
||||
state.Clear();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -3683,7 +3527,6 @@ namespace Duende.Bff.Otel
|
|||
|
||||
state.Clear();
|
||||
}
|
||||
|
||||
public static string Sanitize(this string toSanitize) => toSanitize.ReplaceLineEndings(string.Empty);
|
||||
|
||||
public static string Sanitize(this PathString toSanitize) => toSanitize.ToString().ReplaceLineEndings(string.Empty);
|
||||
|
|
|
|||
|
|
@ -445,8 +445,6 @@
|
|||
// message: $"Failed to add frontend change to {{{OTelParameters.Frontend}}} to queue")]
|
||||
// public static partial void FailedToAddFrontendToQueue(this ILogger logger, LogLevel logLevel, BffFrontendName frontend);
|
||||
//
|
||||
//
|
||||
//
|
||||
// public static string Sanitize(this string toSanitize) => toSanitize.ReplaceLineEndings(string.Empty);
|
||||
//
|
||||
// public static string Sanitize(this PathString toSanitize) => toSanitize.ToString().ReplaceLineEndings(string.Empty);
|
||||
|
|
|
|||
|
|
@ -0,0 +1,58 @@
|
|||
// Copyright (c) Duende Software. All rights reserved.
|
||||
// See LICENSE in the project root for license information.
|
||||
|
||||
using Duende.Bff.AccessTokenManagement;
|
||||
using Duende.Bff.Internal;
|
||||
using Duende.Bff.Licensing;
|
||||
using Duende.IdentityModel;
|
||||
using Microsoft.AspNetCore.Authentication.Cookies;
|
||||
using Microsoft.Extensions.Logging;
|
||||
using Microsoft.Extensions.Options;
|
||||
|
||||
namespace Duende.Bff.SessionManagement.Configuration;
|
||||
|
||||
/// <summary>
|
||||
/// Cookie configuration to check license validity when a user authenticates.
|
||||
/// </summary>
|
||||
internal class PostConfigureApplicationCookieTrialModeCheck(
|
||||
ActiveCookieAuthenticationScheme activeCookieScheme,
|
||||
LicenseValidator licenseValidator,
|
||||
TrialModeAuthenticatedSessionTracker authenticatedSessionTracker,
|
||||
ILogger<PostConfigureApplicationCookieTrialModeCheck> logger)
|
||||
: IPostConfigureOptions<CookieAuthenticationOptions>
|
||||
{
|
||||
/// <inheritdoc />
|
||||
public void PostConfigure(string? name, CookieAuthenticationOptions options)
|
||||
{
|
||||
if (!activeCookieScheme.ShouldConfigureScheme(Scheme.ParseOrDefault(name)))
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
if (!licenseValidator.CheckLicense())
|
||||
{
|
||||
options.Events.OnSigningIn = CreateCallback(options.Events.OnSigningIn);
|
||||
}
|
||||
}
|
||||
|
||||
private Func<CookieSigningInContext, Task> CreateCallback(Func<CookieSigningInContext, Task> inner)
|
||||
{
|
||||
async Task Callback(CookieSigningInContext ctx)
|
||||
{
|
||||
var subjectId = ctx.Principal?.FindFirst(JwtClaimTypes.Subject)?.Value
|
||||
?? "unknown";
|
||||
|
||||
authenticatedSessionTracker.RecordAuthenticatedSession(subjectId);
|
||||
|
||||
if (authenticatedSessionTracker.UniqueAuthenticatedSessions >
|
||||
LicenseValidator.MaximumAllowedSessionsInTrialMode)
|
||||
{
|
||||
logger.TrialModeWarning(LogLevel.Error, LicenseValidator.MaximumAllowedSessionsInTrialMode);
|
||||
}
|
||||
|
||||
await inner.Invoke(ctx);
|
||||
}
|
||||
|
||||
return Callback;
|
||||
}
|
||||
}
|
||||
|
|
@ -1,8 +1,8 @@
|
|||
// Copyright (c) Duende Software. All rights reserved.
|
||||
// See LICENSE in the project root for license information.
|
||||
|
||||
using Duende.Bff.Licensing;
|
||||
using Duende.Bff.Tests.TestInfra;
|
||||
using Microsoft.Extensions.Time.Testing;
|
||||
using Xunit.Abstractions;
|
||||
|
||||
namespace Duende.Bff.Tests;
|
||||
|
|
@ -16,37 +16,95 @@ public class LicensingTests(ITestOutputHelper output) : BffTestBase(output)
|
|||
|
||||
await InitializeAsync();
|
||||
var bffLogMessages = Context.LogMessages.ToString().Split(Environment.NewLine).Where(x => x.StartsWith("bff"));
|
||||
bffLogMessages.ShouldContain(x => x.Contains("You do not have a valid license key for the Duende software."));
|
||||
bffLogMessages.ShouldContain(x =>
|
||||
x.Contains("[Error]")
|
||||
&& x.Contains("You do not have a valid license key for the Duende software."));
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public async Task Given_expired_license_then_log_error()
|
||||
public async Task Given_expired_license_then_log_warning()
|
||||
{
|
||||
Bff.LicenseKey =
|
||||
"eyJhbGciOiJQUzI1NiIsImtpZCI6IklkZW50aXR5U2VydmVyTGljZW5zZWtleS83Y2VhZGJiNzgxMzA0NjllODgwNjg5MTAyNTQxNGYxNiIsInR5cCI6ImxpY2Vuc2Urand0In0.eyJpc3MiOiJodHRwczovL2R1ZW5kZXNvZnR3YXJlLmNvbSIsImF1ZCI6IklkZW50aXR5U2VydmVyIiwiaWF0IjoxNzA0MDY3MjAwLCJleHAiOjE3MzE2Mjg4MDAsImNvbXBhbnlfbmFtZSI6Il90ZXN0IiwiY29udGFjdF9pbmZvIjoiam9lQGR1ZW5kZXNvZnR3YXJlLmNvbSIsImVkaXRpb24iOiJTdGFydGVyIiwiaWQiOiI3ODk2IiwiZmVhdHVyZSI6ImJmZiJ9.YcRGLlVuNBSqNuO1mdXk4GvvVEQFfQUNAnTkzs9W2iNKCxLXrZ5mDPuyTNsDSwEqsfXG8bUCVFxFGp1Bfkxs8hUIBiKuVXfeIB_lmpj5f-KueZ_XlWm0pYT-ROAzVbDdNgMR9YqCPAw8ANclk7HwRcXc0VnLNcKRFrZ0OOWNysFIanTmg7hRIQmDuMLNc2j8HCZSRJ06fijecS72lM4Vv9a6myJvAsASQhKnWTLzQvdzW7T99eobLy45qJu39LMTQkPkkJUS41YPmi2_kEmeMcRucgU4dQKHD5zT9KmzPVWJwsyowWIJ6U7lZ8FXZ8c9POsQeTeQEJY6FheJ2Ut-6Q";
|
||||
SetupExpiredLicense();
|
||||
|
||||
await InitializeAsync();
|
||||
var bffLogMessages = Context.LogMessages.ToString().Split(Environment.NewLine).Where(x => x.StartsWith("bff"));
|
||||
bffLogMessages.ShouldContain(x => x.Contains("Your license for the Duende Software has expired on "));
|
||||
bffLogMessages.ShouldContain(x =>
|
||||
x.Contains("[Warning]")
|
||||
&& x.Contains("Your license for the Duende software has expired"));
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public async Task Given_valid_license_then_details()
|
||||
public async Task Given_valid_but_expired_license_then_no_valid_or_trial_mode_logs()
|
||||
{
|
||||
SetupValidLicenseWithoutFrontends();
|
||||
SetupExpiredLicense();
|
||||
|
||||
await InitializeAsync();
|
||||
|
||||
AddOrUpdateFrontend(Some.BffFrontend());
|
||||
|
||||
for (var i = 0; i <= LicenseValidator.MaximumAllowedSessionsInTrialMode; i++)
|
||||
{
|
||||
var subjectId = Guid.NewGuid().ToString();
|
||||
await Bff.BrowserClient.CreateIdentityServerSessionCookieAsync(IdentityServer, subjectId);
|
||||
await Bff.BrowserClient.Login();
|
||||
}
|
||||
|
||||
var bffLogMessages = Context.LogMessages.ToString().Split(Environment.NewLine).Where(x => x.StartsWith("bff"))
|
||||
.ToList();
|
||||
bffLogMessages.ShouldNotContain(x => x.Contains("You do not have a valid license key for the Duende software."));
|
||||
bffLogMessages.ShouldNotContain(x => x.Contains("Your license for the Duende Software has expired on "));
|
||||
|
||||
bffLogMessages.ShouldNotContain(x =>
|
||||
x.Contains("You do not have a valid license key for the Duende software."));
|
||||
|
||||
bffLogMessages.ShouldContain(x => x.Contains("Your license for the Duende software has expired on "));
|
||||
|
||||
bffLogMessages.ShouldNotContain(x =>
|
||||
x.Contains("BFF is running in trial mode. The maximum number of allowed authenticated sessions "));
|
||||
}
|
||||
|
||||
private void SetupValidLicenseWithoutFrontends()
|
||||
[Fact]
|
||||
public async Task Should_not_log_error_when_below_trial_mode_authenticated_session_limit()
|
||||
{
|
||||
The.Clock = new FakeTimeProvider(new DateTimeOffset(2024, 1, 1, 1, 1, 1, TimeSpan.Zero));
|
||||
Bff.LicenseKey =
|
||||
"eyJhbGciOiJQUzI1NiIsImtpZCI6IklkZW50aXR5U2VydmVyTGljZW5zZWtleS83Y2VhZGJiNzgxMzA0NjllODgwNjg5MTAyNTQxNGYxNiIsInR5cCI6ImxpY2Vuc2Urand0In0.eyJpc3MiOiJodHRwczovL2R1ZW5kZXNvZnR3YXJlLmNvbSIsImF1ZCI6IklkZW50aXR5U2VydmVyIiwiaWF0IjoxNzA0MDY3MjAwLCJleHAiOjE3MzE2Mjg4MDAsImNvbXBhbnlfbmFtZSI6Il90ZXN0IiwiY29udGFjdF9pbmZvIjoiam9lQGR1ZW5kZXNvZnR3YXJlLmNvbSIsImVkaXRpb24iOiJTdGFydGVyIiwiaWQiOiI3ODk2IiwiZmVhdHVyZSI6ImJmZiJ9.YcRGLlVuNBSqNuO1mdXk4GvvVEQFfQUNAnTkzs9W2iNKCxLXrZ5mDPuyTNsDSwEqsfXG8bUCVFxFGp1Bfkxs8hUIBiKuVXfeIB_lmpj5f-KueZ_XlWm0pYT-ROAzVbDdNgMR9YqCPAw8ANclk7HwRcXc0VnLNcKRFrZ0OOWNysFIanTmg7hRIQmDuMLNc2j8HCZSRJ06fijecS72lM4Vv9a6myJvAsASQhKnWTLzQvdzW7T99eobLy45qJu39LMTQkPkkJUS41YPmi2_kEmeMcRucgU4dQKHD5zT9KmzPVWJwsyowWIJ6U7lZ8FXZ8c9POsQeTeQEJY6FheJ2Ut-6Q";
|
||||
await InitializeAsync();
|
||||
|
||||
AddOrUpdateFrontend(Some.BffFrontend());
|
||||
|
||||
for (var i = 0; i < LicenseValidator.MaximumAllowedSessionsInTrialMode; i++)
|
||||
{
|
||||
var subjectId = Guid.NewGuid().ToString();
|
||||
await Bff.BrowserClient.CreateIdentityServerSessionCookieAsync(IdentityServer, subjectId);
|
||||
await Bff.BrowserClient.Login();
|
||||
}
|
||||
|
||||
var bffLogMessages = Context.LogMessages.ToString().Split(Environment.NewLine).Where(x => x.StartsWith("bff"))
|
||||
.ToList();
|
||||
bffLogMessages.ShouldNotContain(x =>
|
||||
x.Contains("[Error]")
|
||||
&& x.Contains("BFF is running in trial mode. The maximum number of allowed authenticated sessions "));
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public async Task Should_log_error_when_trial_mode_authenticated_session_limit_exceeded()
|
||||
{
|
||||
await InitializeAsync();
|
||||
|
||||
AddOrUpdateFrontend(Some.BffFrontend());
|
||||
|
||||
for (var i = 0; i < LicenseValidator.MaximumAllowedSessionsInTrialMode + 6; i++)
|
||||
{
|
||||
var subjectId = Guid.NewGuid().ToString();
|
||||
await Bff.BrowserClient.CreateIdentityServerSessionCookieAsync(IdentityServer, subjectId);
|
||||
await Bff.BrowserClient.Login();
|
||||
}
|
||||
|
||||
var bffLogMessages = Context.LogMessages.ToString().Split(Environment.NewLine).Where(x => x.StartsWith("bff"))
|
||||
.ToList();
|
||||
|
||||
var trialModeLogCount = bffLogMessages.Count(x =>
|
||||
x.Contains("[Error]")
|
||||
&& x.Contains("BFF is running in trial mode. The maximum number of allowed authenticated sessions "));
|
||||
trialModeLogCount.ShouldBe(6);
|
||||
}
|
||||
|
||||
private void SetupExpiredLicense() => Bff.LicenseKey =
|
||||
"eyJhbGciOiJQUzI1NiIsImtpZCI6IklkZW50aXR5U2VydmVyTGljZW5zZWtleS83Y2VhZGJiNzgxMzA0NjllODgwNjg5MTAyNTQxNGYxNiIsInR5cCI6ImxpY2Vuc2Urand0In0.eyJpc3MiOiJodHRwczovL2R1ZW5kZXNvZnR3YXJlLmNvbSIsImF1ZCI6IklkZW50aXR5U2VydmVyIiwiaWF0IjoxNzA0MDY3MjAwLCJleHAiOjE3MzE2Mjg4MDAsImNvbXBhbnlfbmFtZSI6Il90ZXN0IiwiY29udGFjdF9pbmZvIjoiam9lQGR1ZW5kZXNvZnR3YXJlLmNvbSIsImVkaXRpb24iOiJTdGFydGVyIiwiaWQiOiI3ODk2IiwiZmVhdHVyZSI6ImJmZiJ9.YcRGLlVuNBSqNuO1mdXk4GvvVEQFfQUNAnTkzs9W2iNKCxLXrZ5mDPuyTNsDSwEqsfXG8bUCVFxFGp1Bfkxs8hUIBiKuVXfeIB_lmpj5f-KueZ_XlWm0pYT-ROAzVbDdNgMR9YqCPAw8ANclk7HwRcXc0VnLNcKRFrZ0OOWNysFIanTmg7hRIQmDuMLNc2j8HCZSRJ06fijecS72lM4Vv9a6myJvAsASQhKnWTLzQvdzW7T99eobLy45qJu39LMTQkPkkJUS41YPmi2_kEmeMcRucgU4dQKHD5zT9KmzPVWJwsyowWIJ6U7lZ8FXZ8c9POsQeTeQEJY6FheJ2Ut-6Q";
|
||||
}
|
||||
|
|
|
|||
Loading…
Reference in a new issue