Skip to content

Verify Subscription improvements + added quantity and originalTransaction to Payment

Compare
Choose a tag to compare
@bizz84 bizz84 released this 11 May 10:54
· 450 commits to master since this release

NOTE This release introduces some API breaking changes (see #202). Change-set:

#198: Subscription verification unit tests

#199 (fixes #192, #190 and #65): Add ReceiptItem to VerifyPurchaseResult, VerifySubscriptionResult

This change introduces a new strong-typed ReceiptItem struct:

public struct ReceiptItem {
    // The product identifier of the item that was purchased. This value corresponds to the productIdentifier property of the SKPayment object stored in the transaction’s payment property.
    public let productId: String
    // The number of items purchased. This value corresponds to the quantity property of the SKPayment object stored in the transaction’s payment property.
    public let quantity: Int
    // The transaction identifier of the item that was purchased. This value corresponds to the transaction’s transactionIdentifier property.
    public let transactionId: String
    // For a transaction that restores a previous transaction, the transaction identifier of the original transaction. Otherwise, identical to the transaction identifier. This value corresponds to the original transaction’s transactionIdentifier property. All receipts in a chain of renewals for an auto-renewable subscription have the same value for this field.
    public let originalTransactionId: String
    // The date and time that the item was purchased. This value corresponds to the transaction’s transactionDate property.
    public let purchaseDate: Date
    // For a transaction that restores a previous transaction, the date of the original transaction. This value corresponds to the original transaction’s transactionDate property. In an auto-renewable subscription receipt, this indicates the beginning of the subscription period, even if the subscription has been renewed.
    public let originalPurchaseDate: Date
    // The primary key for identifying subscription purchases.
    public let webOrderLineItemId: String
    // The expiration date for the subscription, expressed as the number of milliseconds since January 1, 1970, 00:00:00 GMT. This key is only present for auto-renewable subscription receipts.
    public let subscriptionExpirationDate: Date?
    // For a transaction that was canceled by Apple customer support, the time and date of the cancellation. Treat a canceled receipt the same as if no purchase had ever been made.
    public let cancellationDate: Date?

    public let isTrialPeriod: Bool
}

This is parsed from the receipt and returned as part of the verifySubscription and verifyPurchase methods:

// Result for Consumable and NonConsumable
public enum VerifyPurchaseResult {
    case purchased(item: ReceiptItem)
    case notPurchased
}

// Verify subscription result
public enum VerifySubscriptionResult {
    case purchased(expiryDate: Date, items: [ReceiptItem])
    case expired(expiryDate: Date, items: [ReceiptItem])
    case notPurchased
}

Note that when one or more subscriptions are found for a given product id, they are returned as a ReceiptItem array ordered by expiryDate, with the first one being the newest.

This is useful to get all the valid date ranges for a given subscription.

#202 (fix for #200): It's now possible to specify the quantity when making a purchase. Quantity is also accessible in the callback.

This is an API breaking change. Product has been renamed to Purchase:

public struct Purchase {
    public let productId: String
    public let quantity: Int
    public let transaction: PaymentTransaction
    public let needsFinishTransaction: Bool
}

PurchaseResult

public enum PurchaseResult {
    //case success(product: Product) // old
    case success(purchase: Purchase) // new
    case error(error: SKError)
}

RestoreResults

public struct RestoreResults {
    //public let restoredProducts: [Product] // old
    //public let restoreFailedProducts: [(SKError, String?)] // old
    public let restoredPurchases: [Purchase] // new
    public let restoreFailedPurchases: [(SKError, String?)] // new
}

#203 (fix for #193): Add originalTransaction from SKPaymentTransaction.original to Payment type