Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat(p/grc721): add SetTokenURI to IGRC721 #1309

Merged
merged 16 commits into from
Dec 21, 2023
Merged
Show file tree
Hide file tree
Changes from 11 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
19 changes: 19 additions & 0 deletions examples/gno.land/p/demo/grc/grc721/basic_nft.gno
Original file line number Diff line number Diff line change
Expand Up @@ -69,6 +69,25 @@ func (s *basicNFT) TokenURI(tid TokenID) (string, error) {
return uri.(string), nil
}

func (s *basicNFT) SetTokenURI(tid TokenID, tURI TokenURI) (bool, error) {
// check for invalid TokenID
if !s.exists(tid) {
return false, ErrInvalidTokenId
thehowl marked this conversation as resolved.
Show resolved Hide resolved
}

// check for the right owner
owner, err := s.OwnerOf(tid)
if err != nil {
return false, err
}
caller := std.PrevRealm().Addr()
if caller != owner {
return false, ErrCallerIsNotOwner
}
s.tokenURIs.Set(string(tid), string(tURI))
return true, nil
}

// IsApprovedForAll returns true if operator is approved for all by the owner.
// Otherwise, returns false
func (s *basicNFT) IsApprovedForAll(owner, operator std.Address) bool {
Expand Down
46 changes: 46 additions & 0 deletions examples/gno.land/p/demo/grc/grc721/basic_nft_test.gno
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ import (
"testing"

"gno.land/r/demo/users"
"gno.land/p/demo/testutils"
)

var (
Expand Down Expand Up @@ -367,3 +368,48 @@ func TestBurn(t *testing.T) {
t.Errorf("should result in error")
}
}

func TestSetTokenURI(t *testing.T) {
dummy := NewBasicNFT(dummyNFTName, dummyNFTSymbol)
if dummy == nil {
t.Errorf("should not be nil")
}

addr1 := users.AddressOrName("g1var589z07ppjsjd24ukm4uguzwdt0tw7g47cgm")
addr2 := users.AddressOrName("g1us8428u2a5satrlxzagqqa5m6vmuze025anjlj")
tokenURI := "http://example.com/token"

std.TestSetOrigCaller(std.Address(addr1)) // addr1

dummy.mint(addr1.Resolve(), TokenID("1"))
_, derr := dummy.SetTokenURI(TokenID("1"), TokenURI(tokenURI))

if derr != nil {
t.Errorf("Should not result in error ", derr.Error())
}

// Test case: Invalid token ID
_, err := dummy.SetTokenURI(TokenID("3"), TokenURI(tokenURI))
if err != ErrInvalidTokenId {
t.Errorf("Expected error %v, got %v", ErrInvalidTokenId, err)
}

std.TestSetOrigCaller(std.Address(addr2)) // addr2

_, cerr := dummy.SetTokenURI(TokenID("1"), TokenURI(tokenURI)) // addr2 trying to set URI for token 1
if cerr != ErrCallerIsNotOwner {
t.Errorf("Expected error %v, got %v", ErrCallerIsNotOwner, err)
}

// Test case: Retrieving TokenURI
std.TestSetOrigCaller(std.Address(addr1)) // addr1

dummyTokenURI, err := dummy.TokenURI(TokenID("1"))
if err != nil {
t.Errorf("TokenURI error: %v, ", err.Error())
}
if dummyTokenURI != tokenURI {
t.Errorf("Expected URI %v, got %v", tokenURI, dummyTokenURI)
}

}
1 change: 1 addition & 0 deletions examples/gno.land/p/demo/grc/grc721/errors.gno
Original file line number Diff line number Diff line change
Expand Up @@ -13,5 +13,6 @@ var (
ErrTransferFromIncorrectOwner = errors.New("transfer from incorrect owner")
ErrTransferToNonGRC721Receiver = errors.New("transfer to non GRC721Receiver implementer")
ErrCallerIsNotOwnerOrApproved = errors.New("caller is not token owner or approved")
ErrTokenURINotSet = errors.New("tokeURIs not set")
thehowl marked this conversation as resolved.
Show resolved Hide resolved
ErrTokenIdAlreadyExists = errors.New("token id already exists")
)
2 changes: 2 additions & 0 deletions examples/gno.land/p/demo/grc/grc721/igrc721.gno
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ import "std"
type IGRC721 interface {
BalanceOf(owner std.Address) (uint64, error)
OwnerOf(tid TokenID) (std.Address, error)
SetTokenURI(tid TokenID, tURI TokenURI) (bool, error)
SafeTransferFrom(from, to std.Address, tid TokenID) error
TransferFrom(from, to std.Address, tid TokenID) error
Approve(approved std.Address, tid TokenID) error
Expand All @@ -14,6 +15,7 @@ type IGRC721 interface {
}

type TokenID string
type TokenURI string

type TransferEvent struct {
From std.Address
Expand Down
Loading