Already purchased subscriptions in StoreKit

余生长醉 提交于 2019-12-04 21:10:45

问题


I am using renewable subscriptions in app purchases in an iOS app. When a user attempts to purchase a subscription that they already have paid for a message is displayed from iTunes "You're currently subscribed to this".

How I can detect when this event has occurred so that I can process the transaction and grant access to my app.

In the paymentQueue:updatedTransactions: method of the observer it is coming through as a SKPaymentTransactionStateFailed. How do I distinguish between this type of failure and other failures such as the user pressing the cancel buttons?

Do I submit the transaction that is returned or do I need to call restorePreviousTransactions.

In the Apple documents it states "If the user attempts to purchase a non-consumable product or a renewable subscription they have already purchased, your application receives a regular transaction for that item, not a restore transaction. However, the user is not charged again for that product. Your application should treat these transactions identically to those of the original transaction."


回答1:


Q: How I can detect when this event (currently subscribed) has occurred so that I can process the transaction and grant access to my app.

You detect when the subscription exists via validation with Apple (I use php website code to do this), you get a "status code" response back, and can verify whether it is a code 21006 (subscription is expired), or others (I consider anything other than 0 and 21006 to be an actual error).

The way I do things is I store the transaction details inside a PLIST file which I store in the documents directory.

You could add extra fields to the PLIST such as expiryDates, boolean flags, etc.

This way you have a copy of the receipt, although you should always validate it because it might have expired.

Q: In the paymentQueue:updatedTransactions: method of the observer it is coming through as a SKPaymentTransactionStateFailed. How do I distinguish between this type of failure and other failures such as the user pressing the cancel buttons?

You use a switch statement in the updatedTransactions method to determine the different types of responses.

Example

-(void)paymentQueue:(SKPaymentQueue *)queue restoreCompletedTransactionsFailedWithError:(NSError *)error
{    
    NSString *message = [NSString stringWithFormat:@"Transaction failed with error - %@", error.localizedDescription];
    NSLog(@"Error - %@", message);

    UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Error" 
                                                        message:message 
                                                       delegate:nil
                                              cancelButtonTitle:@"OK" 
                                              otherButtonTitles:nil];
    [alertView show];
    [alertView release];
}

-(void)paymentQueue:(SKPaymentQueue *)queue updatedTransactions:(NSArray *)transactions
{
    NSLog(@"updatedTransactions");
    for (SKPaymentTransaction *transaction in transactions)
    {
        switch (transaction.transactionState)
        {
            case SKPaymentTransactionStatePurchasing:
                // take action whilst processing payment
                break;

            case SKPaymentTransactionStatePurchased:
                // take action when feature is purchased
                break;

            case SKPaymentTransactionStateRestored:
                // take action to restore the app as if it was purchased            
                break;


            case SKPaymentTransactionStateFailed:
                if (transaction.error.code != SKErrorPaymentCancelled)
                {
                // Do something with the error
                } // end if
                break;

            default:
                break;
        } // end switch

    } // next

The TransactionStateFailed handles the failures, although I do not code for cancellation as there is no reason for me to do so in my app.

Q: Do I submit the transaction that is returned or do I need to call restorePreviousTransactions.

I believe StoreKit handles this internally with finishTransaction method and restorePreviousTransaction methods

ie,

[[SKPaymentQueue defaultQueue] finishTransaction: transaction];

to finish off transactions

I hope this helps



来源:https://stackoverflow.com/questions/6177940/already-purchased-subscriptions-in-storekit

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!