サブスクリプションライセンスと暗号化された Pro コード
猶予期間のある期間限定のサブスクリプションライセンスです。サブスクリプション専用のコードは、Babel Obfuscator のコード暗号化で保護します。
サブスクリプションには、単純な有効期限では実現できない 2 つの動作が必要です。1 つは猶予期間で、更新が遅れた途端に、料金を支払っている顧客が使えなくなることを防ぎます。もう 1 つは、構成ファイルを編集しても回避できない強制です。このサンプルは両方を実現し、さらにコード暗号化でプレミアム(「pro」)機能をサブスクリプションに紐付けます。Babel Virtual Machine は復号用のパスワードをライセンスから取得するため、pro メソッドは、猶予期間を含めてサブスクリプションが有効な間だけ実行されます。
コード例
git clone https://github.com/babelfornet/subscription-license-console-example.gitProSuite は、無料の基本機能と暗号化された pro 機能を備えたコンソールアプリケーションです。LicenseGenerator は、期間と猶予期間を設定できるサブスクリプションライセンスを発行します。
2 つの日付:更新期日と最終期限
ライセンスには 2 つの日付が含まれます。
- エンジンが適用する
ExpireDate。猶予期間の終了日(最終期限)に設定します。 - 強制力を持たない
subscription-endフィールド。更新期日を示します。
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");ExpireDate を過ぎると Babel Licensing がライセンスを自動的に拒否するため、最終期限のためのコードを書く必要はありません。アプリケーションは「アクティブ」と「猶予期間中」を区別するだけでよく、そのために、強制力を持たない subscription-end フィールドを現在の時刻と比較します。
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.");
}暗号化された Pro 機能
pro メソッドは暗号化されており、そのパスワードは「get password」フックを通じてライセンスから取得されます。これが、暗号化されたコードをサブスクリプションに紐付ける仕組みです。ライセンスの検証に成功する間(アクティブまたは猶予期間中)は、フックがパスワードを返し、メソッドが実行されます。最終期限を過ぎると Validate() が例外をスローし、フックはパスワードを渡せなくなります。
[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);
}実行
# 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ライセンスを発行し直すと、すべての状態を順に確認できます。
dotnet run --project src/LicenseGenerator -- --days -2 --grace 7 # lapsed, in grace
dotnet run --project src/LicenseGenerator -- --expired # past grace| 状態 | 条件 | Pro 機能 |
|---|---|---|
| アクティブ | サブスクリプションの終了日より前 | 実行される |
| 猶予期間 | サブスクリプションの終了日より後で、最終期限より前 | 更新を促す警告付きで実行される |
| 期限切れ | 最終期限より後 | ロックされる(BVM が復号できない) |
猶予期間を過ぎると、アプリケーションは 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 expired定期的な課金の場合、同じライセンスは通常 Babel Licensing Service が発行および更新します。このサービスは、有効期間を短くして、更新を自動的に配信できます。ここで示したオフラインのファイルライセンスは、アクティブ、猶予期間、期限切れの遷移を示す最も簡単な方法です。
サンプルの keys.pem とパスワードは、デモ専用です。RSA 秘密キーはオフラインで保管し、ライセンスはベンダー側で発行してください。アプリケーションと一緒に配布するのは公開キーだけです。