diff --git a/packages/tokens/non-fungible/src/non_fungible.rs b/packages/tokens/non-fungible/src/non_fungible.rs index 421c7c40a..3f684bb97 100644 --- a/packages/tokens/non-fungible/src/non_fungible.rs +++ b/packages/tokens/non-fungible/src/non_fungible.rs @@ -174,7 +174,8 @@ pub trait NonFungibleToken { /// /// Only a single account can be approved at a time for a `token_id`. /// To remove an approval, the approver can approve their own address, - /// effectively removing the previous approved address. + /// effectively removing the previous approved address. Alternatively, + /// setting the `live_until_ledger` to `0` will also revoke the approval. /// /// # Arguments /// @@ -184,7 +185,7 @@ pub trait NonFungibleToken { /// * `approved` - The address receiving the approval. /// * `token_id` - Token id as a number. /// * `live_until_ledger` - The ledger number at which the allowance - /// expires. + /// expires. If `live_until_ledger` is `0`, the approval is revoked. /// /// # Errors /// diff --git a/packages/tokens/non-fungible/src/storage.rs b/packages/tokens/non-fungible/src/storage.rs index e1abf7352..2da9c10ad 100644 --- a/packages/tokens/non-fungible/src/storage.rs +++ b/packages/tokens/non-fungible/src/storage.rs @@ -322,7 +322,8 @@ impl Base { /// `operator`). /// * `approved` - The address receiving the approval. /// * `token_id` - The identifier of the token to be approved. - /// * `live_until_ledger` - The ledger number at which the approval expires. + /// * `live_until_ledger` - The ledger number at which the allowance + /// expires. If `live_until_ledger` is `0`, the approval is revoked. /// /// # Errors /// @@ -497,12 +498,19 @@ impl Base { panic_with_error!(e, NonFungibleTokenError::InvalidApprover); } + let key = StorageKey::Approval(token_id); + + if live_until_ledger == 0 { + e.storage().temporary().remove(&key); + + emit_approve(e, approver, approved, token_id, live_until_ledger); + return; + } + if live_until_ledger < e.ledger().sequence() { panic_with_error!(e, NonFungibleTokenError::InvalidLiveUntilLedger); } - let key = StorageKey::Approval(token_id); - let approval_data = ApprovalData { approved: approved.clone(), live_until_ledger }; e.storage().temporary().set(&key, &approval_data);