Licence par abonnement avec code Pro chiffré
Une licence par abonnement à durée limitée, avec une période de grâce, dont le code réservé aux abonnés est protégé par le chiffrement du code de Babel Obfuscator.
Les abonnements exigent deux comportements qu’une simple date d’expiration n’offre pas : une période de grâce, pour que les clients qui paient ne perdent pas l’accès dès qu’un renouvellement a du retard, et un contrôle impossible à contourner en modifiant un fichier de configuration. Cet exemple réalise les deux et lie les fonctionnalités premium (« pro ») à l’abonnement avec le chiffrement du code : la méthode pro ne s’exécute que tant que l’abonnement est valide, période de grâce comprise, car la machine virtuelle Babel obtient son mot de passe de déchiffrement dans la licence.
Exemple de code
git clone https://github.com/babelfornet/subscription-license-console-example.gitProSuite est une application console qui comporte une fonctionnalité de base gratuite et une
fonctionnalité pro chiffrée ; LicenseGenerator émet des licences par abonnement dont la durée et
la période de grâce sont configurables.
Deux dates : renouvellement et date butoir
La licence contient deux dates :
- la propriété
ExpireDate, appliquée par le moteur et fixée à la fin de la période de grâce (la date butoir), et - un champ indicatif
subscription-end, qui marque la date Ă laquelle le renouvellement est dĂ».
DateTime subscriptionEnd = now.AddDays(days); // soft end — renewal due
DateTime hardCutoff = subscriptionEnd.AddDays(grace); // engine-enforced end of grace
var license = new StringLicense { ExpireDate = hardCutoff };
license
.ForAssembly(assemblyFullName)
.WithUniqueId("SUBSCR-")
.WithHardwareKey(HardwareId.Create().ToMachineKey())
.WithField(Secrets.SubscriptionEndField, subscriptionEnd.ToString("O"))
.WithField(Secrets.ProSource, Secrets.ProPassword.Encrypt(Secrets.FieldSecret))
.LicensedTo("Demo Customer", "demo@example.com", "ACME Corp");Babel Licensing rejette automatiquement la licence une fois ExpireDate dépassée, si bien que la
date butoir ne demande aucun code particulier. L’application doit seulement distinguer l’état
actif de l’état en période de grâce, ce qu’elle fait en comparant le champ indicatif
subscription-end à l’heure actuelle :
var now = DateTime.UtcNow;
if (subEnd.HasValue && now > subEnd.Value)
{
int graceDaysLeft = (int)Math.Ceiling(((license.ExpireDate ?? now) - now).TotalDays);
return new SubscriptionStatus(SubscriptionState.Grace, subEnd, graceDaysLeft,
$"Subscription lapsed — grace period active ({graceDaysLeft} day(s) left). Please renew.");
}La fonctionnalité pro chiffrée
La méthode pro est chiffrée ; son mot de passe provient de la licence par l’intermédiaire du hook
get password. C’est ce qui lie le code chiffré à l’abonnement : tant que la licence est validée
(active ou en période de grâce), le hook renvoie le mot de passe et la méthode s’exécute ; une fois
la date butoir dépassée, Validate() lève une exception et le hook ne peut plus fournir le mot de passe.
[Obfuscation(Feature = "msil encryption:internal=true;source=pro;password=Pr0-Su1te-2026-K3y", Exclude = false)]
public static string Forecast(double[] series) { /* premium analytics */ }
[Obfuscation(Feature = "msil encryption get password")]
internal static string GetSourcePassword(string source)
{
var license = Validate(); // throws once past the end of grace
var field = license.Fields.FirstOrDefault(f => f.Name == source)
?? throw new InvalidOperationException($"License does not grant source '{source}'.");
return field.Value.Decrypt(Secrets.FieldSecret);
}Exécuter l’exemple
# Build in Release — Babel encrypts Pro.Forecast.
dotnet build src/ProSuite/ProSuite.csproj -c Release
# Mint a subscription license: active for 30 days, 7-day grace.
dotnet run --project src/LicenseGenerator -- --days 30 --grace 7
cp ProSuite.lic src/ProSuite/bin/Release/net8.0/
dotnet src/ProSuite/bin/Release/net8.0/ProSuite.dllÉmettez de nouveau la licence pour parcourir tous les états :
dotnet run --project src/LicenseGenerator -- --days -2 --grace 7 # lapsed, in grace
dotnet run --project src/LicenseGenerator -- --expired # past grace| État | Condition | Fonctionnalité pro |
|---|---|---|
| Actif | avant la fin de l’abonnement | s’exécute |
| Période de grâce | après la fin de l’abonnement, avant la date butoir | s’exécute, avec un avertissement de renouvellement |
| Expiré | après la date butoir | verrouillée : la BVM ne peut pas la déchiffrer |
Après la période de grâce, l’application en fait la démonstration en essayant malgré tout d’appeler la méthode pro :
Subscription expired: License expired
Basic average: 13.63
Pro forecast is locked. Renew your subscription to restore access.
(proof) encrypted Pro.Forecast blocked: License expiredPour une facturation récurrente, la même licence est normalement émise et renouvelée par le Babel Licensing Service, qui peut raccourcir la période de validité et transmettre automatiquement les renouvellements. La licence fichier hors ligne présentée ici est le moyen le plus simple de montrer les transitions entre les états actif, en période de grâce et expiré.
keys.pem et les mots de passe de l’exemple servent uniquement à la démonstration. Conservez la clé
privée RSA hors ligne et émettez les licences côté éditeur ; seule la clé publique est livrée avec
l’application.