What would be the best way to implement a non-transfer "loyalty points" with ASA?

Hi, I want to implement a system like this: customer will earn some loyalty points every time when they purchase something on our website. While the loyalty points can be used to redeem some goods on our website, it is not transferable between customers.

So my question is, what would be the best way to implement this using ASA?

Here are 2 problems I am considering:

1, If I create this “loyalty points” as fungible ASA, seems the total supply should be infinite, because as customer purchase more and more things, they can earn more and more points, there is no need to put a “total loyalty points” ceiling number. But I don’t think the “total” parameter support “infinite” in the creating ASA SDK

2, As a fungible ASA, if 2 customers opt-in this asset, by default they will be able to transfer between each other. How would I make it non-transferable? I noticed the document says:

There is also optional functionality to place transfer restrictions on an asset that help support securities, compliance, and certification use cases.

Does the “transfer restriction” here mean utilizing the “freeze” feature?

For example, to issue a customer some points initially, the manager account will transfer some points to the customer, then use the freeze account to freeze it (I can put those 2 transactions in a transaction group with the atomic transfer feature), such that the customer won’t be able to send/receive the points further.

Next time, if system wants to put more points to this customer again, 1) freeze account first unfree this customer 2) manager account transfer more points to this customer 3) freeze account freeze it again. I can put these 3 transactions in a transaction group.

When customers want to redeem something on our website, 1) freeze account first unfree this customer, 2) transfer some points from customer to either our sink account or our manager account address 3) use freeze account to freeze the customer’s points again

This is just a rough idea, but I am not sure if I am in the right direction.

Any suggestions on those 2 problems? Thank you in advance.

If the loyalty points are not transferable, then there is no need to hanle it like ASA.
You can use a cloud database, to store loyalty point.

Thank for the reply. While it can be saved in database, save to the blockchain would make it be verifiable to the public, so it has benefits. Plus, if ASA is only meant to make transferable assets, what’s point to mention this “transfer restrictions” part in their official doc?

There is also optional functionality to place transfer restrictions on an asset that help support securities, compliance, and certification use cases.

Another example, say you want to issue a certificate to someone after they finished your training course, this certificate can be a non-fungible token, but still you won’t want the earner to have the ability to transfer it to other people who never took your course.

1 Like

Right you are. But certificates and ASA are different, are’t they?
A certificate is signed by the certificate issuer.

The ASA is signed by the owner, thereby ransferring you the ownership. Then you can also transfer ownership.

In case of certifications it doesn’t makes sense, since the Certificate Authority (CA) signes the hash of a document, which is essentially a text file stating that you (name) at that time (date time) has completed such and such an activity (course, university, etc).

By the way, how is ASA (or Algo) ownership transfer is working??
I know the mechanism for Bitcoin only.

Not sure this’s true. From browsing algorand’s document, I think “certificate” is a type of ASA, just with different parameter setup, like you can treat it as a non-fungible token.

You can check the docs/tutorials here:

Anyway, want to back to focus on my 2 questions:

1, can a “loyalty points/token” has infinite supply?
2, Am I supposed to use the “freeze” feature to implement a non-transferable token?

ASAs are a great fit for your application.
That is actually what Props is doing:

  1. You cannot get infinite supply, but if you set the supply to be e.g., 2^64-1 (the highest possible value), it is virtually infinite.
  2. You can just freeze all transfers by default. Then, you can use the clawback address to move tokens, as the clawback address bypasses freezes: Algorand Developer Docs. You can see a detailed tutorials to combine the clawback address with stateful smart contracts to allow fine-grained control over which transactions are allowed or not: Algorand Developer Portal

Don’t hesitate to ask any further question!

1 Like

ha, this is a beautiful solution, thank you!

This might be out of context but can this Custom Transfer Logic be done using Reach?
As far as I know, Reach can’t do transactions group.