Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/swift/20.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/video/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Ios Swift应用内购买非消耗品_Ios_Swift_In App Purchase_Nsuserdefaults - Fatal编程技术网

Ios Swift应用内购买非消耗品

Ios Swift应用内购买非消耗品,ios,swift,in-app-purchase,nsuserdefaults,Ios,Swift,In App Purchase,Nsuserdefaults,我正在开发非消耗品的IAP功能(删除广告)。 我已经为所有的操作创建了一个助手,一切都很好 当用户购买/恢复购买时,我设置: let save = UserDefaults.standard save.set(true, forKey: "Purchase") save.synchronize() 只要用户从不删除该应用程序,这就可以正常工作 我在想。。。 有没有办法知道用户(删除并重新安装应用程序后)是否已经购买了?因此,要将按钮标题从“购买”更改为“恢复”?如果您提供登录系统,您将很容易知

我正在开发非消耗品的IAP功能(删除广告)。 我已经为所有的操作创建了一个助手,一切都很好

当用户购买/恢复购买时,我设置:

let save = UserDefaults.standard
save.set(true, forKey: "Purchase")
save.synchronize()
只要用户从不删除该应用程序,这就可以正常工作

我在想。。。
有没有办法知道用户(删除并重新安装应用程序后)是否已经购买了?因此,要将按钮标题从“购买”更改为“恢复”?

如果您提供登录系统,您将很容易知道,否则

没有其他方法可以让您为支付设置购买和恢复按钮,或者将此键值存储在 设备密钥链并在第一次设置中读取它们,但您应该从ios 10.3中知道,如果您删除了应用程序,相关的密钥链项目将被删除


注意:Apple声明所有具有IAP的应用程序都应设置恢复支付功能,因此,如果有变通应用程序将被Apple

拒绝,则Apple要求您为每个应用程序添加“恢复购买”按钮。这正是你所面临的问题。它将为以前购买的每个IAP重新创建
SKPaymentTransaction
,当前已在App Store登录的iCloud帐户的状态为“已还原”,并将其放入
SKPaymentQueue

当用户在应用程序中进行交互时,在代码中进行收据验证可能是有意义的。(苹果文档:)

  func receiptValidation() {
            self.logger.log.debug("In receipt validation")
            if let appStoreReceiptURL = Bundle.main.appStoreReceiptURL,
                FileManager.default.fileExists(atPath: appStoreReceiptURL.path) {

                do {
                    let receiptData = try Data(contentsOf: appStoreReceiptURL, options: .alwaysMapped)

                    let receiptString = receiptData.base64EncodedString(options: [])
                    let dict = ["receipt-data" : receiptString, "password" : "YOUR_PASSWORD"] as [String : Any]
                    // Getting the receipt data from the JSON file and other logic
                    // ...
                    // ...
          }
       }
    }
看看这个小例子:

初始化您的产品请求:

if SKPaymentQueue.canMakePayments() {
        print("starting IAPS")
        let productIdentifiers = Set(["YOUR_IAPP_IDENTIFIER#1", "YOUR_IAPP_IDENTIFIER#1"])
        let request = SKProductsRequest(productIdentifiers: productIdentifiers as Set<String>)
        request.delegate = self
        request.start()

} else {
        print("please enable IAPS")
}
验证示例

  func receiptValidation() {
            self.logger.log.debug("In receipt validation")
            if let appStoreReceiptURL = Bundle.main.appStoreReceiptURL,
                FileManager.default.fileExists(atPath: appStoreReceiptURL.path) {

                do {
                    let receiptData = try Data(contentsOf: appStoreReceiptURL, options: .alwaysMapped)

                    let receiptString = receiptData.base64EncodedString(options: [])
                    let dict = ["receipt-data" : receiptString, "password" : "YOUR_PASSWORD"] as [String : Any]
                    // Getting the receipt data from the JSON file and other logic
                    // ...
                    // ...
          }
       }
    }

请让我知道,如果你需要更多的澄清这一点。此外,您只需使用PaymentQueue(Apple文档:)将其还原即可。

谢谢您的回答。。。我所做的一切都符合产品要求。但我对斯威夫特有点陌生(只有几个月),从未见过验证。。。你能再解释一下我怎么用它吗?它是否从商店返回有关购买的数据?我已经实现了恢复部分。。。我只是想显示不同的按钮标签,这取决于是第一次购买还是他已经购买。。。在用户删除/重新安装应用程序之前,使用userDefaults一直有效。。。很明显,这个值不再设置了…我已经将它存储在钥匙链中。。。我已经实现了恢复的可能性。。。我只是想看看是否有办法改变按钮标签,如果它是第一次购买或恢复。。。我的钥匙链问题是,正如你所说,如果用户删除/重新安装应用程序,那么它将不会存储任何价值…现在实现这一点的方法是,如果你查看几乎任何带有IAP的iOS应用程序,你会发现它们都有一个“恢复购买”按钮——苹果顺便说一句——即使你从未购买过。所有发生的事情就是你的购买被恢复——这意味着除了检查购买之外什么都不会发生。为什么您希望您的应用程序的行为与每个iOS用户预期的不同?正确的方法是实现“恢复购买”按钮,因此,如果用户删除应用程序,用户始终可以使用此选项恢复它。应该有另一种方法,比如在钥匙链中保存购买状态(即使重新安装了应用程序也会持续),或者使用云。小心那些!顺便说一句,在代码中,不需要使用.syncronize()