Skip to content

Release 4.1.0

Latest

Choose a tag to compare

@Ramiz69 Ramiz69 released this 08 Nov 07:16
· 1 commit to main since this release
a509944

New: currentEntitlement(for:)

hasEntitlement(for:) says whether the customer may use a product. currentEntitlement(for:) returns the
transaction behind that answer, with its dates, so you no longer need to import StoreKit next to the kit to
get them:

if let trial = await purchases.currentEntitlement(for: "app.trial") {
    let trialEnds = trial.purchaseDate.addingTimeInterval(14 * 86_400)
}

A typical use is a free trial for a one-time purchase. App Review requires it to be a free non-consumable
(guideline 3.1.1), and the app computes the trial's end from when it was "bought". That date comes from the
App Store, so it survives a reinstall and is the same on every device in a Family Sharing group.

  • The source is Transaction.currentEntitlements(for:), the same as for hasEntitlement(for:), so a
    transaction comes back exactly when hasEntitlement(for:) returns true. It also updates the cached flag
    and the purchasedProducts event the same way.

  • When several transactions qualify, the rule is fixed:

    • revoked transactions are skipped;
    • the customer's own purchase wins over a Family Sharing grant;
    • then the earliest purchaseDate wins, then the lowest id.

    The answer does not depend on StoreKit's order and does not change when a second grant appears later.

Compatibility

Nothing breaks. The new PurchasesProtocol requirement has a default implementation that returns nil, so
conformers written for 4.0, including the mocks used in tests and previews, still compile. A mock whose
hasEntitlement(for:) returns true should implement currentEntitlement(for:) too, otherwise the two
methods disagree.

.package(url: "https://github.com/Ramiz69/PurchaseKit.git", from: "4.1.0")