Smart Contract
SHRD
A.d01e482eb680ec9f.SHRD
1import FungibleToken from 0xf233dcee88fe0abe
2import MotoGPAdmin from 0xa49cc0ee46c54bfb
3
4// The SRHD Fungible Token is designed to be uncapped, mintable and burnable,
5// corresponding to the SHRD ERC-20 on Ethereum.
6
7pub contract SHRD: FungibleToken {
8
9 pub fun getVersion(): String {
10 return "1.0.0"
11 }
12
13 // TODO: SHRD contract has a private minter link that links a minter with a private capability
14 // Only the vaultguard can access the private minter
15
16 // Interface to enable creation of a private-pathed capability for minting
17 pub resource interface SHRDMinterPrivate {
18 pub fun mint(amount: UFix64): @SHRD.Vault
19 }
20 // Resource to enable creation of a private-pathed capability for minting
21 // By accessing minting in this way, all mint functions can have access(contract) visibility
22 pub resource SHRDMinter: SHRDMinterPrivate {
23 pub fun mint(amount: UFix64): @SHRD.Vault {
24 return <- SHRD.mint(amount: amount)
25 }
26 }
27
28 // Total minted supply
29 pub var totalSupply: UFix64
30
31 // Event that is emitted when the contract is created
32 pub event TokensInitialized(initialSupply: UFix64)
33
34 // Event that is emitted when tokens are withdrawn from a Vault
35 pub event TokensWithdrawn(amount: UFix64, from: Address?)
36
37 // Event that is emitted when tokens are deposited to a Vault
38 pub event TokensDeposited(amount: UFix64, to: Address?)
39
40 // Event that is emitted when new tokens are minted
41 pub event TokensMinted(amount: UFix64)
42
43 // Event that is emitted when tokens are burned
44 pub event TokensBurned(amount: UFix64)
45
46 // The public path for the token balance
47 pub let SHRDBalancePublicPath: PublicPath
48
49 // The public path for the token receiver
50 pub let SHRDReceiverPublicPath: PublicPath
51
52 // The storage path for the token vault
53 pub let SHRDVaultStoragePath: StoragePath
54
55 // The private path for the token vault
56 pub let SHRDVaultPrivatePath: PrivatePath
57
58 // The storage path for the SHRDMinter
59 pub let SHRDMinterStoragePath: StoragePath
60
61 // The private path for the SHRDMinter which will be accessed by mintguards
62 pub let SHRDMinterPrivatePath: PrivatePath // suffix '2' should be removed after SHRDMinterPrivatePath has been deprecated and deleted (before mainnet deployment)
63
64 // Vault
65 //
66 // Each user stores an instance of the Vault in their storage
67 // The functions in the Vault are governed by the pre and post conditions
68 // in FungibleToken when they are called.
69 // The checks happen at runtime whenever a function is called.
70 //
71 // Resources can only be created in the context of the contract that they
72 // are defined in, so there is no way for a malicious user to create Vaults
73 // out of thin air.
74 //
75 pub resource Vault: FungibleToken.Provider, FungibleToken.Receiver, FungibleToken.Balance {
76
77 // holds the balance of a users tokens
78 pub var balance: UFix64
79
80 // initialize the balance at resource creation time
81 init(balance: UFix64) {
82 self.balance = balance
83 }
84
85 // withdraw
86 //
87 // Function that takes an amount as an argument
88 // and withdraws that amount from the Vault.
89 // It creates a new temporary Vault that is used to hold
90 // the money that is being transferred. It returns the newly
91 // created Vault to the context that called so it can be deposited
92 // elsewhere.
93 // @event TokensWithdrawn
94 //
95 pub fun withdraw(amount: UFix64): @FungibleToken.Vault {
96 self.balance = self.balance - amount
97 emit TokensWithdrawn(amount: amount, from: self.owner?.address)
98 return <-create Vault(balance: amount)
99 }
100
101 // deposit
102 //
103 // Function that takes a Vault object as an argument and adds
104 // its balance to the balance of the owners Vault.
105 // It is allowed to destroy the sent Vault because the Vault
106 // was a temporary holder of the tokens. The Vault's balance has
107 // been consumed and therefore the vault can be destroyed.
108 // @event TokensDeposited
109 //
110 pub fun deposit(from: @FungibleToken.Vault) {
111 let vault <- from as! @SHRD.Vault
112 self.balance = self.balance + vault.balance
113 emit TokensDeposited(amount: vault.balance, to: self.owner?.address)
114 vault.balance = 0.0
115 destroy vault
116 }
117
118 // destroy
119 //
120 // SHRD are burnable
121 // @event TokensBurned - emitted if a vault with balance larger than 0 is destroyed
122 //
123 destroy() {
124 SHRD.totalSupply = SHRD.totalSupply - self.balance
125 if self.balance > 0.0 {
126 emit TokensBurned(amount: self.balance)
127 }
128 }
129 }
130
131 // createEmptyVault
132 //
133 // Function that creates a new Vault with a balance of zero
134 // and returns it to the calling context. A user must call this function
135 // and store the returned Vault in their storage in order to allow their
136 // account to be able to receive deposits of this token type.
137 //
138 pub fun createEmptyVault(): @FungibleToken.Vault {
139 return <-create Vault(balance: 0.0)
140 }
141
142 // mint
143 //
144 access(contract) fun mint(amount: UFix64): @SHRD.Vault {
145 pre {
146 amount > 0.0 : "Mint amount must be larger than 0.0"
147 }
148 self.totalSupply = self.totalSupply + amount
149 let vault <- create Vault(balance: amount)
150 emit TokensMinted(amount: amount)
151 return <- vault
152 }
153
154 // mint with SHRD mint guard
155
156 // init
157 //
158 // Contract constructor
159 //
160 // @event TokensInitialized
161
162 init() {
163 // Init supply fields
164 self.totalSupply = UFix64(0)
165
166 //Initialize the path fields
167 //
168 self.SHRDBalancePublicPath = /public/shrdBalance
169
170 self.SHRDReceiverPublicPath = /public/shrdReceiver
171
172 self.SHRDVaultStoragePath = /storage/shrdVault
173
174 self.SHRDVaultPrivatePath = /private/shrdVault
175
176 self.SHRDMinterStoragePath = /storage/shrdMinter
177
178 self.SHRDMinterPrivatePath= /private/shrdMinter
179
180 self.account.save(<- create SHRDMinter(), to: self.SHRDMinterStoragePath)
181 self.account.link<&SHRDMinter{SHRDMinterPrivate}>(self.SHRDMinterPrivatePath, target: self.SHRDMinterStoragePath)
182
183 emit TokensInitialized(initialSupply: self.totalSupply)
184 }
185}