Smart Contract

WE_PIN

A.8f4f599546e2d7eb.WE_PIN

Deployed

1w ago
Feb 15, 2026, 02:52:05 PM UTC

Dependents

0 imports
1/*
2 * Copyright (c) 2022 24Karat. All rights reserved.
3 *
4 * SPDX-License-Identifier: MIT
5 *
6 * This file is part of Project: 24karat flow contract (https://github.com/24karat-gld/flow-24karat-contract)
7 *
8 * This source code is licensed under the MIT License found in the
9 * LICENSE file in the root directory of this source tree or at
10 * https://opensource.org/licenses/MIT.
11 */
12 
13import FungibleToken from 0xf233dcee88fe0abe
14
15pub contract WE_PIN: FungibleToken {
16    // TokensInitialized
17    //
18    // The event that is emitted when the contract is created
19    pub event TokensInitialized(initialSupply: UFix64)
20
21    // TokensWithdrawn
22    //
23    // The event that is emitted when tokens are withdrawn from a Vault
24    pub event TokensWithdrawn(amount: UFix64, from: Address?)
25
26    // TokensDeposited
27    //
28    // The event that is emitted when tokens are deposited to a Vault
29    pub event TokensDeposited(amount: UFix64, to: Address?)
30
31    // TokensMinted
32    //
33    // The event that is emitted when new tokens are minted
34    pub event TokensMinted(amount: UFix64)
35
36    // TokensBurned
37    //
38    // The event that is emitted when tokens are destroyed
39    pub event TokensBurned(amount: UFix64)
40
41    // MinterCreated
42    //
43    // The event that is emitted when a new minter resource is created
44    pub event MinterCreated(allowedAmount: UFix64)
45
46    // Named paths
47    //
48    pub let VaultStoragePath: StoragePath
49    pub let ReceiverPublicPath: PublicPath
50    pub let BalancePublicPath: PublicPath
51    pub let AdminStoragePath: StoragePath
52
53    // Total supply of token in existence
54    pub var totalSupply: UFix64
55
56    // Vault
57    //
58    // Each user stores an instance of only the Vault in their storage
59    // The functions in the Vault and governed by the pre and post conditions
60    // in FungibleToken when they are called.
61    // The checks happen at runtime whenever a function is called.
62    //
63    // Resources can only be created in the context of the contract that they
64    // are defined in, so there is no way for a malicious user to create Vaults
65    // out of thin air. A special Minter resource needs to be defined to mint
66    // new tokens.
67    //
68    pub resource Vault: FungibleToken.Provider, FungibleToken.Receiver, FungibleToken.Balance {
69
70        // The total balance of this vault
71        pub var balance: UFix64
72
73        // initialize the balance at resource creation time
74        init(balance: UFix64) {
75            self.balance = balance
76        }
77
78        // withdraw
79        //
80        // Function that takes an amount as an argument
81        // and withdraws that amount from the Vault.
82        //
83        // It creates a new temporary Vault that is used to hold
84        // the money that is being transferred. It returns the newly
85        // created Vault to the context that called so it can be deposited
86        // elsewhere.
87        //
88        pub fun withdraw(amount: UFix64): @FungibleToken.Vault {
89            self.balance = self.balance - amount
90            emit TokensWithdrawn(amount: amount, from: self.owner?.address)
91            return <-create Vault(balance: amount)
92        }
93
94        // deposit
95        //
96        // Function that takes a Vault object as an argument and adds
97        // its balance to the balance of the owners Vault.
98        //
99        // It is allowed to destroy the sent Vault because the Vault
100        // was a temporary holder of the tokens. The Vault's balance has
101        // been consumed and therefore can be destroyed.
102        //
103        pub fun deposit(from: @FungibleToken.Vault) {
104            let vault <- from as! @WE_PIN.Vault
105            self.balance = self.balance + vault.balance
106            emit TokensDeposited(amount: vault.balance, to: self.owner?.address)
107            vault.balance = 0.0
108            destroy vault
109        }
110
111        destroy() {
112            WE_PIN.totalSupply = WE_PIN.totalSupply - self.balance
113            if(self.balance > 0.0) {
114                emit TokensBurned(amount: self.balance)
115            }
116        }
117    }
118
119    // createEmptyVault
120    //
121    // Function that creates a new Vault with a balance of zero
122    // and returns it to the calling context. A user must call this function
123    // and store the returned Vault in their storage in order to allow their
124    // account to be able to receive deposits of this token type.
125    //
126    pub fun createEmptyVault(): @Vault {
127        return <-create Vault(balance: 0.0)
128    }
129
130    pub resource Administrator {
131
132        // createNewMinter
133        //
134        // Function that creates and returns a new minter resource
135        //
136        pub fun createNewMinter(allowedAmount: UFix64): @Minter {
137            emit MinterCreated(allowedAmount: allowedAmount)
138            return <-create Minter(allowedAmount: allowedAmount)
139        }
140    }
141
142    // Minter
143    //
144    // Resource object that token admin accounts can hold to mint new tokens.
145    //
146    pub resource Minter {
147
148        // The amount of tokens that the minter is allowed to mint
149        pub var allowedAmount: UFix64
150
151        // mintTokens
152        //
153        // Function that mints new tokens, adds them to the total supply,
154        // and returns them to the calling context.
155        //
156        pub fun mintTokens(amount: UFix64): @WE_PIN.Vault {
157            pre {
158                amount > 0.0: "Amount minted must be greater than zero"
159                amount <= self.allowedAmount: "Amount minted must be less than the allowed amount"
160            }
161            WE_PIN.totalSupply = WE_PIN.totalSupply + amount
162            self.allowedAmount = self.allowedAmount - amount
163            emit TokensMinted(amount: amount)
164            return <-create Vault(balance: amount)
165        }
166
167        init(allowedAmount: UFix64) {
168            self.allowedAmount = allowedAmount
169        }
170    }
171
172    init() {
173        // Set our named paths.
174        self.VaultStoragePath = /storage/WE_PIN24KaratVault
175        self.ReceiverPublicPath = /public/WE_PIN24KaratReceiver
176        self.BalancePublicPath = /public/WE_PIN24KaratBalance
177        self.AdminStoragePath = /storage/WE_PIN24KaratAdmin
178
179        // Initialize contract state.
180        self.totalSupply = 0.0
181
182        // Create the one true Admin object and deposit it into the conttract account.
183        let admin <- create Administrator()
184        self.account.save(<-admin, to: self.AdminStoragePath)
185
186        // Emit an event that shows that the contract was initialized.
187        emit TokensInitialized(initialSupply: self.totalSupply)
188    }
189}
190