Ecosyste.ms: Awesome

An open API service indexing awesome lists of open source software.

Awesome Lists | Featured Topics | Projects

https://github.com/programmer-ke/token-vendor

speedrun eth challenge 2
https://github.com/programmer-ke/token-vendor

Last synced: 9 days ago
JSON representation

speedrun eth challenge 2

Awesome Lists containing this project

README

        

# ๐Ÿšฉ Challenge 2: ๐Ÿต Token Vendor ๐Ÿค–

![readme-2](https://github.com/scaffold-eth/se-2-challenges/assets/55535804/b427171f-3f20-41a5-b76f-05d67e2b9959)

๐Ÿค– Smart contracts are kind of like "always on" _vending machines_ that **anyone** can access. Let's make a decentralized, digital currency. Then, let's build an unstoppable vending machine that will buy and sell the currency. We'll learn about the "approve" pattern for ERC20s and how contract to contract interactions work.

๐Ÿต Create `YourToken.sol` smart contract that inherits the **ERC20** token standard from OpenZeppelin. Set your token to `_mint()` **1000** (\* 10 \*\* 18) tokens to the `msg.sender`. Then create a `Vendor.sol` contract that sells your token using a payable `buyTokens()` function.

๐ŸŽ› Edit the frontend that invites the user to input an amount of tokens they want to buy. We'll display a preview of the amount of ETH it will cost with a confirm button.

๐Ÿ” It will be important to verify your token's source code in the block explorer after you deploy. Supporters will want to be sure that it has a fixed supply and you can't just mint more.

๐ŸŒŸ The final deliverable is an app that lets users purchase your ERC20 token, transfer it, and sell it back to the vendor. Deploy your contracts on your public chain of choice and then `yarn vercel` your app to a public web server. Submit the url on [SpeedRunEthereum.com](https://speedrunethereum.com)!

> ๐Ÿ’ฌ Meet other builders working on this challenge and get help in the [Challenge 2 Telegram](https://t.me/joinchat/IfARhZFc5bfPwpjq)!

---

## Checkpoint 0: ๐Ÿ“ฆ Environment ๐Ÿ“š

Before you begin, you need to install the following tools:

- [Node (v18 LTS)](https://nodejs.org/en/download/)
- Yarn ([v1](https://classic.yarnpkg.com/en/docs/install/) or [v2+](https://yarnpkg.com/getting-started/install))
- [Git](https://git-scm.com/downloads)

Then download the challenge to your computer and install dependencies by running:

```sh
git clone https://github.com/scaffold-eth/se-2-challenges.git challenge-2-token-vendor
cd challenge-2-token-vendor
git checkout challenge-2-token-vendor
yarn install
```

> in the same terminal, start your local network (a blockchain emulator in your computer):

```sh
yarn chain
```

> in a second terminal window, ๐Ÿ›ฐ deploy your contract (locally):

```sh
cd challenge-2-token-vendor
yarn deploy
```

> in a third terminal window, start your ๐Ÿ“ฑ frontend:

```sh
cd challenge-2-token-vendor
yarn start
```

๐Ÿ“ฑ Open http://localhost:3000 to see the app.

> ๐Ÿ‘ฉโ€๐Ÿ’ป Rerun `yarn deploy` whenever you want to deploy new contracts to the frontend. If you haven't made any contract changes, you can run `yarn deploy --reset` for a completely fresh deploy.

---

## Checkpoint 1: ๐ŸตYour Token ๐Ÿ’ต

> ๐Ÿ‘ฉโ€๐Ÿ’ป Edit `YourToken.sol` to inherit the **ERC20** token standard from OpenZeppelin

> Mint **1000** (\* 10 \*\* 18) to your frontend address using the `constructor()`.

(Your frontend address is the address in the top right of http://localhost:3000)

> You can `yarn deploy --reset` to deploy your contract until you get it right.

### ๐Ÿฅ… Goals

- [ ] Can you check the `balanceOf()` your frontend address in the `Debug Contracts` tab? (**YourToken** contract)
- [ ] Can you `transfer()` your token to another account and check _that_ account's `balanceOf`?

![debugContractsYourToken](https://github.com/scaffold-eth/se-2-challenges/assets/55535804/5fb4daeb-5d05-4522-96b3-76f052a68418)

> ๐Ÿ’ฌ Hint: Use an incognito window to create a new address and try sending to that new address. Can use the `transfer()` function in the `Debug Contracts` tab.

---

## Checkpoint 2: โš–๏ธ Vendor ๐Ÿค–

> ๐Ÿ‘ฉโ€๐Ÿ’ป Edit the `Vendor.sol` contract with a **payable** `buyTokens()` function

Use a price variable named `tokensPerEth` set to **100**:

```solidity
uint256 public constant tokensPerEth = 100;
```

> ๐Ÿ“ The `buyTokens()` function in `Vendor.sol` should use `msg.value` and `tokensPerEth` to calculate an amount of tokens to `yourToken.transfer()` to `msg.sender`.

> ๐Ÿ“Ÿ Emit **event** `BuyTokens(address buyer, uint256 amountOfETH, uint256 amountOfTokens)` when tokens are purchased.

Edit `packages/hardhat/deploy/01_deploy_vendor.js` to deploy the `Vendor` (uncomment Vendor deploy lines).

Uncomment the `Buy Tokens` sections in `packages/nextjs/pages/token-vendor.tsx` to show the UI to buy tokens on the Token Vendor tab.

### ๐Ÿฅ… Goals

- [ ] When you try to buy tokens from the vendor, you should get an error: **'ERC20: transfer amount exceeds balance'**

โš ๏ธ This is because the Vendor contract doesn't have any YourTokens yet!

โš”๏ธ Side Quest: send tokens from your frontend address to the Vendor contract address and _then_ try to buy them.

> โœ๏ธ We can't hard code the vendor address like we did above when deploying to the network because we won't know the vendor address at the time we create the token contract.

> โœ๏ธ So instead, edit `YourToken.sol` to mint the tokens to the `msg.sender` (deployer) in the **constructor()**.

> โœ๏ธ Then, edit `deploy/01_deploy_vendor.js` to transfer 1000 tokens to `vendor.address`.

```js
await yourToken.transfer(vendor.address, hre.ethers.utils.parseEther("1000"));
```

> ๐Ÿ”Ž Look in `packages/nextjs/pages/token-vendor.tsx` for code to uncomment to display the Vendor ETH and Token balances.

> You can `yarn deploy --reset` to deploy your contract until you get it right.

![TokenVendorBuy](https://github.com/scaffold-eth/se-2-challenges/assets/55535804/7669cc68-e942-4630-95c8-91cd21af5ba0)

### ๐Ÿฅ… Goals

- [ ] Does the `Vendor` address start with a `balanceOf` **1000** in `YourToken` on the `Debug Contracts` tab?
- [ ] Can you buy **10** tokens for **0.1** ETH?
- [ ] Can you transfer tokens to a different account?

> ๐Ÿ“ Edit `Vendor.sol` to inherit _Ownable_.

`contract Vendor is Ownable {`

โš ๏ธ You will also need to import the Ownable.sol contract!

In `deploy/01_deploy_vendor.js` you will need to call `transferOwnership()` on the `Vendor` to make _your frontend address_ the `owner`:

```js
await vendor.transferOwnership("**YOUR FRONTEND ADDRESS**");
```

### ๐Ÿฅ… Goals

- [ ] Is your frontend address the `owner` of the `Vendor`?

> ๐Ÿ“ Finally, add a `withdraw()` function in `Vendor.sol` that lets the owner withdraw all the ETH from the vendor contract.

### ๐Ÿฅ… Goals

- [ ] Can **only** the `owner` withdraw the ETH from the `Vendor`?

### โš”๏ธ Side Quests

- [ ] What if you minted **2000** and only sent **1000** to the `Vendor`?

---

## Checkpoint 3: ๐Ÿค” Vendor Buyback ๐Ÿคฏ

๐Ÿ‘ฉโ€๐Ÿซ The hardest part of this challenge is to build your `Vendor` to buy the tokens back.

๐Ÿง The reason why this is hard is the `approve()` pattern in ERC20s.

๐Ÿ˜• First, the user has to call `approve()` on the `YourToken` contract, approving the `Vendor` contract address to take some amount of tokens.

๐Ÿคจ Then, the user makes a _second transaction_ to the `Vendor` contract to `sellTokens(uint256 amount)`.

๐Ÿค“ The `Vendor` should call `yourToken.transferFrom(msg.sender, address(this), theAmount)` and if the user has approved the `Vendor` correctly, tokens should transfer to the `Vendor` and ETH should be sent to the user.

> ๐Ÿ“ Edit `Vendor.sol` and add a `sellTokens(uint256 amount)` function!

โš ๏ธ You will need extra UI for calling `approve()` before calling `sellTokens(uint256 amount)`.

๐Ÿ”จ Use the `Debug Contracts` tab to call the approve and sellTokens() at first but then...

๐Ÿ” Look in the `packages/nextjs/pages/token-vendor.tsx` for the extra approve/sell UI to uncomment!

![VendorBuyBack](https://github.com/scaffold-eth/se-2-challenges/assets/55535804/99063aaa-368d-4156-997d-08dff99af11b)

### ๐Ÿฅ… Goal

- [ ] Can you sell tokens back to the vendor?
- [ ] Do you receive the right amount of ETH for the tokens?

### โš”๏ธ Side Quests

- [ ] Should we disable the `owner` withdraw to keep liquidity in the `Vendor`?
- [ ] It would be a good idea to display Sell Token Events .Create an **event** `SellTokens(address seller, uint256 amountOfTokens, uint256 amountOfETH)` and `emit` it in your `Vendor.sol` and uncomment `SellTokens Events` section in your `packages/nextjs/pages/events.tsx` to update your frontend.

![Events](https://github.com/scaffold-eth/se-2-challenges/assets/55535804/662c96b5-d53f-4efa-af4a-d3106bfd47f0)

### โš ๏ธ Test it!

- Now is a good time to run `yarn test` to run the automated testing function. It will test that you hit the core checkpoints. You are looking for all green checkmarks and passing tests!

---

## Checkpoint 4: ๐Ÿ’พ Deploy your contracts! ๐Ÿ›ฐ

๐Ÿ“ก Edit the `defaultNetwork` to [your choice of public EVM networks](https://ethereum.org/en/developers/docs/networks/) in `packages/hardhat/hardhat.config.ts`

๐Ÿ” You will need to generate a **deployer address** using `yarn generate` This creates a mnemonic and saves it locally.

๐Ÿ‘ฉโ€๐Ÿš€ Use `yarn account` to view your deployer account balances.

โ›ฝ๏ธ You will need to send ETH to your deployer address with your wallet, or get it from a public faucet of your chosen network.

๐Ÿš€ Run `yarn deploy` to deploy your smart contract to a public network (selected in `hardhat.config.ts`)

> ๐Ÿ’ฌ Hint: You can set the `defaultNetwork` in `hardhat.config.ts` to `sepolia` **OR** you can `yarn deploy --network sepolia`.

> ๐Ÿ’ฌ Hint: For faster loading of your _"Events"_ page, consider updating the `fromBlock` passed to `useScaffoldEventHistory` in [`packages/nextjs/pages/events.tsx`](https://github.com/scaffold-eth/se-2-challenges/blob/challenge-2-token-vendor/packages/nextjs/pages/events.tsx) to `blocknumber - 10` at which your contract was deployed. Example: `fromBlock: 3750241n` (where `n` represents its a [BigInt](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/BigInt)). To find this blocknumber, search your contract's address on Etherscan and find the `Contract Creation` transaction line.

---

## Checkpoint 5: ๐Ÿšข Ship your frontend! ๐Ÿš

โœ๏ธ Edit your frontend config in `packages/nextjs/scaffold.config.ts` to change the `targetNetwork` to `chains.sepolia` or any other public network.

๐Ÿ’ป View your frontend at http://localhost:3000 and verify you see the correct network.

๐Ÿ“ก When you are ready to ship the frontend app...

๐Ÿ“ฆ Run `yarn vercel` to package up your frontend and deploy.

> Follow the steps to deploy to Vercel. Once you log in (email, github, etc), the default options should work. It'll give you a public URL.

> If you want to redeploy to the same production URL you can run `yarn vercel --prod`. If you omit the `--prod` flag it will deploy it to a preview/test URL.

> ๐ŸฆŠ Since we have deployed to a public testnet, you will now need to connect using a wallet you own or use a burner wallet. By default ๐Ÿ”ฅ `burner wallets` are only available on `hardhat` . You can enable them on every chain by setting `onlyLocalBurnerWallet: false` in your frontend config (`scaffold.config.ts` in `packages/nextjs/`)

#### Configuration of Third-Party Services for Production-Grade Apps.

By default, ๐Ÿ— Scaffold-ETH 2 provides predefined API keys for popular services such as Alchemy and Etherscan. This allows you to begin developing and testing your applications more easily, avoiding the need to register for these services.
This is great to complete your **SpeedRunEthereum**.

For production-grade applications, it's recommended to obtain your own API keys (to prevent rate limiting issues). You can configure these at:

- ๐Ÿ”ท`ALCHEMY_API_KEY` variable in `packages/hardhat/.env` and `packages/nextjs/.env.local`. You can create API keys from the [Alchemy dashboard](https://dashboard.alchemy.com/).

- ๐Ÿ“ƒ`ETHERSCAN_API_KEY` variable in `packages/hardhat/.env` with your generated API key. You can get your key [here](https://etherscan.io/myapikey).

> ๐Ÿ’ฌ Hint: It's recommended to store env's for nextjs in Vercel/system env config for live apps and use .env.local for local testing.

---

## Checkpoint 6: ๐Ÿ“œ Contract Verification

Run the `yarn verify --network your_network` command to verify your contracts on etherscan ๐Ÿ›ฐ

๐Ÿ‘€ You may see an address for both YouToken and Vendor. You will want the Vendor address.

๐Ÿ‘‰ Search this address on Etherscan to get the URL you submit to ๐Ÿƒโ€โ™€๏ธ[SpeedRunEthereum.com](https://speedrunethereum.com).

---

> ๐Ÿƒ Head to your next challenge [here](https://speedrunethereum.com).

> ๐Ÿ’ฌ Problems, questions, comments on the stack? Post them to the [๐Ÿ— scaffold-eth developers chat](https://t.me/joinchat/F7nCRK3kI93PoCOk)