Discrepancy in documentation regarding non-consumable products in Google Play

Reading the documentation: Defold In-app purchase extension API documentation

Here it is mentioned:

The Google Play store does only support consumable products. If you need non-consumable products it is recommended to use manual fulfilment of purchases and never finish purchases for products that should be non-consumable. As long as a purchase isn’t finished it will be returned as an active purchase when iap.set_listener() is called. If you do not call iap.finish() on a purchase you still need to indicate to Google Play that the purchase has been handled. You can do this by calling iap.acknowledge(). If you do not call iap.acknowledge() the purchase will be automatically refunded by Google after a few days.

But then in the next section, we have mentioned:

Google Play and Apple supports three different product types: subscriptions, consumable and non-consumable products.

Which one is it, does Google Play support non-consumable products such as a one time purchase of “Disable Ads”.

Will I have to go the route of not calling iap.finish() for such purchases? or will the extension handle this? Since its mentioned in next section that Google supports this kind of product.

Thanks

Google Play supports both consumable and non-consumable one time products:

A consumable product is bought and consumed (and then can be bought again), while a non-consumable product is bought and never consumed (and can not be bought again).

The difference is in how you treat the products in your purchase flow. For a non-consumable product you call acknowledge() but not finish(). I will make sure to clarify the docs.

3 Likes

Thank you. Thats much clearer now.

So for non-consumable iap, such as disable-ads, we do not call iap.finish(), but we must call iap.acknowledge() otherwise the purchase will be refunded.

So looking at the example script in the github:

local function buy_listener(self, transaction, error)
	pprint(transaction)
	if error then
		log("iap.buy() error %s - %s", tostring(error.error), tostring(error.reason))
		return
	end

	if iap.get_provider_id() == iap.PROVIDER_ID_GOOGLE and transaction.ident == NON_CONSUMABLE then
		log("iap.buy() ok - google")
		gui.set_color(gui.get_node("reset/larrylabel"), vmath.vector4(1,1,1,1))
		product_items["reset"] = transaction
	else
		log("iap.buy() ok %s", transaction.ident)
		if self.finish then
			log("iap.finish() %s", transaction.ident)
			iap.finish(transaction)
		elseif self.acknowledge then
			log("iap.acknowledge() %s", transaction.ident)
			iap.acknowledge(transaction)
		end
	end
end

should we add iap.acknowledge(transaction) at the end of if block?

Thanks

1 Like

It is not necessary to call acknowledge() if you call iap.finish()

Yes, but for transaction.ident == NON_CONSUMABLE, we dont call iap.finish()right? Then in that case we should call iap.acknowledge? As per documentation, otherwise the purchase will be refunded.

I was just trying to clarify if the example code in the github repository missed to call acknowledge() as we are supposed to.

Also, one more thing please, I keep reading in the API docs: if `auto_finish_transactions` is disabled in project settings... And also in the code example in the API

  local function iap_listener(self, transaction, error)
    if error == nil then
      -- purchase is successful.
      print(transaction.date)
      -- required if auto finish transactions is disabled in project settings
      if (transaction.state == iap.TRANS_STATE_PURCHASED) then
        -- do server-side verification of purchase here..
        iap.finish(transaction)
      end
    else
      print(error.error, error.reason)
    end
  end

  function init(self)
      iap.set_listener(iap_listener)
      iap.buy("my_iap")
  end

But I cant find auto finish transactions anywhere in the game.project file. Is this related to a previous version of the extension?

Ah, thanks for pointing this out. This used to be part of game.project but that is no longer the case. The developer needs to open game.project and manually add it:

[iap]
auto_finish_transactions = 0

The default value is true: extension-iap/extension-iap/src/iap_android.cpp at master · defold/extension-iap · GitHub

Could you please report this in the extension repository? I’d like to fix these documentation issues when we updated to Android Billing 8.0.0 later this year.

1 Like