diff --git a/public/images/quickstarts/circuit-breaker/automation-change-checkdata.png b/public/images/quickstarts/circuit-breaker/automation-change-checkdata.png new file mode 100644 index 000000000000..ffc7154f8860 Binary files /dev/null and b/public/images/quickstarts/circuit-breaker/automation-change-checkdata.png differ diff --git a/public/images/quickstarts/circuit-breaker/automation-edit-checkdata.png b/public/images/quickstarts/circuit-breaker/automation-edit-checkdata.png new file mode 100644 index 000000000000..6415d033cfd0 Binary files /dev/null and b/public/images/quickstarts/circuit-breaker/automation-edit-checkdata.png differ diff --git a/public/images/quickstarts/circuit-breaker/check-counter.png b/public/images/quickstarts/circuit-breaker/check-counter.png new file mode 100644 index 000000000000..67279269b765 Binary files /dev/null and b/public/images/quickstarts/circuit-breaker/check-counter.png differ diff --git a/public/images/quickstarts/circuit-breaker/circuit-breaker-copy-address.png b/public/images/quickstarts/circuit-breaker/circuit-breaker-copy-address.png new file mode 100644 index 000000000000..dc3d9bdd1349 Binary files /dev/null and b/public/images/quickstarts/circuit-breaker/circuit-breaker-copy-address.png differ diff --git a/public/images/quickstarts/circuit-breaker/example-implementation-deploy-expanded.png b/public/images/quickstarts/circuit-breaker/example-implementation-deploy-expanded.png new file mode 100644 index 000000000000..8309f1d36e8c Binary files /dev/null and b/public/images/quickstarts/circuit-breaker/example-implementation-deploy-expanded.png differ diff --git a/public/images/quickstarts/circuit-breaker/example-implementation-deploy.png b/public/images/quickstarts/circuit-breaker/example-implementation-deploy.png new file mode 100644 index 000000000000..ccd4c5f3d9a8 Binary files /dev/null and b/public/images/quickstarts/circuit-breaker/example-implementation-deploy.png differ diff --git a/public/images/quickstarts/circuit-breaker/hashex-abi-encoder-address.png b/public/images/quickstarts/circuit-breaker/hashex-abi-encoder-address.png new file mode 100644 index 000000000000..a6272903794d Binary files /dev/null and b/public/images/quickstarts/circuit-breaker/hashex-abi-encoder-address.png differ diff --git a/public/images/quickstarts/giveaway/1-ui-connect-wallet.png b/public/images/quickstarts/giveaway/1-ui-connect-wallet.png new file mode 100644 index 000000000000..915cce08330f Binary files /dev/null and b/public/images/quickstarts/giveaway/1-ui-connect-wallet.png differ diff --git a/public/images/quickstarts/giveaway/10-ui-select-dynamic-type.png b/public/images/quickstarts/giveaway/10-ui-select-dynamic-type.png new file mode 100644 index 000000000000..9dff53ce657a Binary files /dev/null and b/public/images/quickstarts/giveaway/10-ui-select-dynamic-type.png differ diff --git a/public/images/quickstarts/giveaway/11-ui-create-dynamic-giveaway.png b/public/images/quickstarts/giveaway/11-ui-create-dynamic-giveaway.png new file mode 100644 index 000000000000..c5f938bd65e9 Binary files /dev/null and b/public/images/quickstarts/giveaway/11-ui-create-dynamic-giveaway.png differ diff --git a/public/images/quickstarts/giveaway/12-ui-click-dynamic-giveaway.png b/public/images/quickstarts/giveaway/12-ui-click-dynamic-giveaway.png new file mode 100644 index 000000000000..71bb3379a069 Binary files /dev/null and b/public/images/quickstarts/giveaway/12-ui-click-dynamic-giveaway.png differ diff --git a/public/images/quickstarts/giveaway/13-ui-dynamic-giveaway-options.png b/public/images/quickstarts/giveaway/13-ui-dynamic-giveaway-options.png new file mode 100644 index 000000000000..d1e27fbebd0a Binary files /dev/null and b/public/images/quickstarts/giveaway/13-ui-dynamic-giveaway-options.png differ diff --git a/public/images/quickstarts/giveaway/14-ui-staged-status.png b/public/images/quickstarts/giveaway/14-ui-staged-status.png new file mode 100644 index 000000000000..721b3fec4f03 Binary files /dev/null and b/public/images/quickstarts/giveaway/14-ui-staged-status.png differ diff --git a/public/images/quickstarts/giveaway/15-ui-dynamic-pick-winners.png b/public/images/quickstarts/giveaway/15-ui-dynamic-pick-winners.png new file mode 100644 index 000000000000..06451d35e337 Binary files /dev/null and b/public/images/quickstarts/giveaway/15-ui-dynamic-pick-winners.png differ diff --git a/public/images/quickstarts/giveaway/16-ui-pick-winners-confirmation.png b/public/images/quickstarts/giveaway/16-ui-pick-winners-confirmation.png new file mode 100644 index 000000000000..d64024c8e9d8 Binary files /dev/null and b/public/images/quickstarts/giveaway/16-ui-pick-winners-confirmation.png differ diff --git a/public/images/quickstarts/giveaway/17-ui-view-winners.png b/public/images/quickstarts/giveaway/17-ui-view-winners.png new file mode 100644 index 000000000000..cf85ae1c3508 Binary files /dev/null and b/public/images/quickstarts/giveaway/17-ui-view-winners.png differ diff --git a/public/images/quickstarts/giveaway/2-ui-create-giveaway.png b/public/images/quickstarts/giveaway/2-ui-create-giveaway.png new file mode 100644 index 000000000000..5d3dfb554ee2 Binary files /dev/null and b/public/images/quickstarts/giveaway/2-ui-create-giveaway.png differ diff --git a/public/images/quickstarts/giveaway/3-ui-create-static-giveaway.png b/public/images/quickstarts/giveaway/3-ui-create-static-giveaway.png new file mode 100644 index 000000000000..b7a4c64d28dc Binary files /dev/null and b/public/images/quickstarts/giveaway/3-ui-create-static-giveaway.png differ diff --git a/public/images/quickstarts/giveaway/4-ui-click-giveaway.png b/public/images/quickstarts/giveaway/4-ui-click-giveaway.png new file mode 100644 index 000000000000..2df06664ba9c Binary files /dev/null and b/public/images/quickstarts/giveaway/4-ui-click-giveaway.png differ diff --git a/public/images/quickstarts/giveaway/5-ui-pick-winners.png b/public/images/quickstarts/giveaway/5-ui-pick-winners.png new file mode 100644 index 000000000000..30d7a2d72c82 Binary files /dev/null and b/public/images/quickstarts/giveaway/5-ui-pick-winners.png differ diff --git a/public/images/quickstarts/giveaway/6-ui-pick-winners-confirmation.png b/public/images/quickstarts/giveaway/6-ui-pick-winners-confirmation.png new file mode 100644 index 000000000000..d031060c92b2 Binary files /dev/null and b/public/images/quickstarts/giveaway/6-ui-pick-winners-confirmation.png differ diff --git a/public/images/quickstarts/giveaway/7-ui-upload-contestants-csv.png b/public/images/quickstarts/giveaway/7-ui-upload-contestants-csv.png new file mode 100644 index 000000000000..4534da5d29e1 Binary files /dev/null and b/public/images/quickstarts/giveaway/7-ui-upload-contestants-csv.png differ diff --git a/public/images/quickstarts/giveaway/8-ui-check-winners.png b/public/images/quickstarts/giveaway/8-ui-check-winners.png new file mode 100644 index 000000000000..71ead29018e6 Binary files /dev/null and b/public/images/quickstarts/giveaway/8-ui-check-winners.png differ diff --git a/public/images/quickstarts/giveaway/9-ui-giveaway-winners.png b/public/images/quickstarts/giveaway/9-ui-giveaway-winners.png new file mode 100644 index 000000000000..8b833f60188c Binary files /dev/null and b/public/images/quickstarts/giveaway/9-ui-giveaway-winners.png differ diff --git a/src/config/sidebar.ts b/src/config/sidebar.ts index 47474b89b155..f0d2d116c28e 100644 --- a/src/config/sidebar.ts +++ b/src/config/sidebar.ts @@ -278,6 +278,14 @@ export const SIDEBAR: Partial> = { title: "Automate Top-Up for VRF Subscriptions", url: "quickstarts/vrf-subscription-monitor", }, + { + title: "Data Feed Circuit Breaker", + url: "quickstarts/circuit-breaker", + }, + { + title: "Giveaway Manager", + url: "quickstarts/giveaway", + }, ], }, { @@ -521,6 +529,15 @@ export const SIDEBAR: Partial> = { }, ], }, + { + section: "Examples", + contents: [ + { + title: "Functions Demo App", + url: "quickstarts/functions-demo-app", + }, + ], + }, { section: "Resources", contents: [ @@ -1286,6 +1303,15 @@ export const SIDEBAR: Partial> = { }, ], }, + { + section: "Examples", + contents: [ + { + title: "Chainlink Demo App", + url: "quickstarts/chainlink-demo-app", + }, + ], + }, ], legacy: [ { diff --git a/src/content/quickstarts/chainlink-demo-app.mdx b/src/content/quickstarts/chainlink-demo-app.mdx new file mode 100644 index 000000000000..1fd04ecaf868 --- /dev/null +++ b/src/content/quickstarts/chainlink-demo-app.mdx @@ -0,0 +1,136 @@ +--- +section: global +date: Last Modified +title: "Chainlink Demo App" +whatsnext: { "Learn more about Data Feeds": "/data-feeds", "Learn more about VRF": "/vrf/v2/introduction" } +--- + +import { Aside } from "@components" + +The Chainlink Demo App is an end-to-end implementation of several Chainlink services. It uses the Hardhat development environment and the Next.js frontend framework. This guide shows you how to deploy this app yourself and use it as a starting point for building your own decentralized applications. + +Try out the demo at [chainlink-demo.app](https://chainlink-demo.app). + +See the code on [GitHub](https://github.com/smartcontractkit/chainlink-fullstack). + + + +## Objective + +This guide shows you how to deploy a demo app, which requires several steps common to Web3 apps. You will learn the basics for how to use the Hardhat development environment and the Next.js frontend framework. + +## Before you begin + +Before you start this tutorial, complete the following items: + +- If you are new to smart contract development, learn how to [Deploy Your First Smart Contract](/getting-started/deploy-your-first-contract). +- Set up a cryptocurrency wallet such as [MetaMask](https://metamask.io/). +- To deploy this contract on testnets, ensure the deployer account has testnet ERC-677 LINK. Use the [LINK faucet](https://faucets.chain.link/) to retrieve testnet LINK. +- [Install Node](https://nodejs.org/en/download/) +- [Install Yarn](https://classic.yarnpkg.com/en/docs/install/#mac-stable) +- [Install Git](https://git-scm.com/downloads) + +## Steps to implement + +### Configure your local files + +1. Clone the repo and change directories: + + ```bash + git clone https://github.com/smartcontractkit/chainlink-fullstack && cd chainlink-fullstack + ``` + +1. Inititalize the submodule: + + ```bash + git submodule init + ``` + +1. Update the submodule: + + ```bash + git submodule update + ``` + +1. Install the dependencies: + + ```bash + yarn install + ``` + +1. Start up the local Hardhat network and deploy all contracts: + + ```bash + yarn chain + ``` + +1. In a second terminal start up the local development server run the front-end app: + + ```bash + yarn dev + ``` + +To interact with the local network, follow this step-by-step guide on how to use [MetaMask with a Hardhat node](https://support.chainstack.com/hc/en-us/articles/4408642503449-Using-MetaMask-with-a-Hardhat-node). + +If you've set the mnemonic from MetaMask the first 20 accounts will be funded with ETH. + +### Configure environment variables + +1. Use the `.env.example` file in the `hardhat` workspace. Copy it to new `.env` files and replace the values with the following values: + + - `NETWORK_RPC_URL` - An RPC is required to deploy to public networks. You can obtain one from [Infura](https://infura.io). + - `MNEMONIC` - This is used to derive accounts from a wallet seed phrase from Metamask. The first account must have enough ETH to deploy the contracts as well as LINK which can be obtained from [Chainlink's faucets](https://faucets.chain.link). + - `PRIVATE_KEY` - This is an alternative to using the mnemonic. Some changes are required in `hardhat.config.js` + - `ETHERSCAN_API_KEY` - This can be obtained from an Etherscan account, and is used to verify your contract code on Etherscan. + +1. In the `frontend` workspace, configure a new `.env` file with the following value: + + - `NEXT_PUBLIC_INFURA_KEY` - Used for read-only mode and WalletConnect. + +### Deploy the contracts + +1. Before deploying the `RandomSVG` contract on a public network, you need to [create and fund a VRF subscription](/vrf/v2/subscription/ui/). +1. Set the ID of your VRF subscription in `./packages/hardhat/helper-hardhat-config.ts`. +1. Deploy on a public network: + + ```bash + yarn deploy --network sepolia + ``` + +1. Confirm the contract onchain: + + ```bash + npx hardhat verify --network + ``` + + example: + + ```bash + npx hardhat verify --network sepolia 0x9279791897f112a41FfDa267ff7DbBC46b96c296 "0x9326BFA02ADD2366b30bacB125260Af641031331" + ``` + +## Run the example + +Start the front end to test your deployed application. + +1. Change to the frontend directory. + + ```bash + yarn start + ``` + +1. Navigate to the locally hosted web server to interact with the app. + +When you are done, try making modifications to the code to improve it, redeploy the contract, and run the example again. + +## Examine the code + +You can learn how the frontend works with deployed contracts by analyzing the code on [GitHub](https://github.com/smartcontractkit/chainlink-fullstack). diff --git a/src/content/quickstarts/circuit-breaker.mdx b/src/content/quickstarts/circuit-breaker.mdx new file mode 100644 index 000000000000..15850cd0eb45 --- /dev/null +++ b/src/content/quickstarts/circuit-breaker.mdx @@ -0,0 +1,220 @@ +--- +section: automation +date: Last Modified +title: "Data Feed Circuit Breaker Using Chainlink Automation" +metadata: + linkToWallet: true +whatsnext: + { + "Find the list of supported networks": "/chainlink-automation/supported-networks/", + "Automation FAQs": "/chainlink-automation/faqs", + "Data feeds": "/data-feeds/using-data-feeds", + } +--- + +import { Address, Aside, ClickToZoom, CodeSample, CopyText } from "@components" + +Circuit breakers are useful for pausing dApps and processes when adverse events are detected on-chain. These circuit breakers can prevent loss of assets during volatile market events, unstable network conditions, or if systems that your dApp relies on become compromised. + +The example circuit breaker contract is a highly configurable proof of concept that can be used with [Data Feeds](/data-feeds). It is capable of emitting events or calling custom functions based on predefined conditions, and it comes with an interactive UI that allows users to easily configure and manage the contract. + +{/* prettier-ignore */} + + + + +## Objective + +The [Circuit Breaker repository](https://github.com/smartcontractkit/quickstarts-circuitbreaker) contains an example implementation of a circuit breaker that can be used with any OCR price feed. You can monitor a given contract, specify the price when the circuit breaker will be triggered based on predefined conditions, and specify the underlying logic of what happens when the circuit breaker is triggered. + +## Before you begin + + + +You can run this example on Linux, MacOS, or the [Windows Subsystem for Linux](https://learn.microsoft.com/en-us/windows/wsl/about). + +Before you start this tutorial, install the required tools: + +- Install [git](https://git-scm.com/book/en/v2/Getting-Started-Installing-Git) + - Run `git --version` to check the installation. You should see an output similar to `git version x.x.x`. +- Install [Nodejs](https://nodejs.org/en/) 16.0.0 or higher + - Run `node --version` to check the installation. You should see an output similar to `v16.x.x`. +- Install and configure a cryptocurrency wallet like [MetaMask](https://metamask.io/). +- Add the Avalanche Fuji testnet and LINK to your wallet: + {" "} + + Avalanche Fuji testnet + +- Add testnet funds to your wallet. You will need both ERC-677 LINK and the gas currency for the chain where your contract is deployed. For this example, use Avalanche Fuji and testnet LINK. You can get both at [faucets.chain.link](https://faucets.chain.link/fuji). + +## Setup the example + +To set up this example, clone the source and install the required packages. + +1. Clone the [smartcontractkit/quickstarts-circuitbreaker](https://github.com/smartcontractkit/quickstarts-circuitbreaker) repository and change directories: + + ```shell + git clone https://github.com/smartcontractkit/quickstarts-circuitbreaker.git && \ + cd quickstarts-circuitbreaker + ``` + +1. Install the `chainlink/contracts` npm package: + + ```shell + npm install @chainlink/contracts@0.6.1 --save + ``` + + For this tutorial, disregard the resulting `npm` warnings. + +## Run the example + +In this section, you will deploy two contracts and then set up Chainlink Automation. + +### Deploy contracts + +1. Open the `ExampleImplementation.sol` contract in Remix: + + {/* prettier-ignore */} + + +1. On the **Solidity compiler** tab, click **Compile `ExampleImplementation.sol`**. +1. On the **Deploy and run transactions** tab, select _Injected Provider - MetaMask_ for the **Environment** field. Make sure the `ExampleImplementation.sol` contract is selected in the **Contract** field. +1. Scroll down to the **Deploy** section: + + {" "} + + + + Click the dropdown carat to expand the **Deploy** section: + + {" "} + + + +1. Enter the following input to the constructor: + + | Item | Value | + | -------------------- | --------------------------------------------------------------------------------------------------------- | + | `_MAXBALANCE` | | + | `_FEEDADDRESS` |
| + | `_EMERGENCYPOSSIBLE` | | + + - The `maxBalance` in sats. For example, for a max balance of $20,000. + - The proxy contract address of the price feed. For example, the address for the BTC/USD price feed on Fuji is
. Find other price feed addresses [here](/data-feeds/price-feeds/addresses). + - The `isEmergencyPossible` flag: set this to `true` if you want the circuit breaking condition to be checked. You can turn off this check by setting this value to `false`. + +1. Click **Deploy** and confirm the transaction in your wallet. + +Next, deploy the the `CircuitBreaker.sol` contract: + +1. Open the `CircuitBreaker.sol` contract in Remix: + + {/* prettier-ignore */} + + +1. On the **Solidity compiler** tab, click **Compile `CircuitBreaker.sol`**. +1. On the **Deploy and run transactions** tab, select _Injected Provider - MetaMask_ for the **Environment** field. Make sure the `CircuitBreaker.sol` contract is selected in the **Contract** field. +1. There are no constructor inputs for this contract. Click **Deploy** and confirm the transaction in your wallet. + +### Register and fund an upkeep + +Registering an upkeep on Chainlink Automation creates a smart contract that will run your circuit breaker contract. + +{/* prettier-ignore */} +{" "} + + + +1. Click **Register new Upkeep**. + +1. Select the _Custom logic_ trigger. + +1. For _Target contract address_, input the address of your deployed `CircuitBreaker.sol` contract. You can find this in your wallet's transaction history or copy it from Remix: + +{" "} + + + +There may be a warning that says "Unable to verify if this is an Automation compatible contract." The `CircuitBreaker.sol` contract does implement the `AutomationCompatibleInterface` so you can disregard this warning. Click **Next**. + +1. For **Upkeep details**, add the following: + + - A name for your upkeep + - A starting balance of 2 testnet LINK + - The admin address and gas limit are prefilled for you. + - Although the **Check data** field is marked optional, it is **required** for this tutorial. You'll fill this in during the next step. + +1. For your upkeep's **Check data** field, you need to ABI encode the address of your deployed `ExampleImplementation.sol` contract. + + 1. Navigate to the [HashEx Online ABI Encoder](https://abi.hashex.org/). + 1. Click **Add argument** and select **Address** as the argument type from the dropdown menu. 1. Enter the address of your deployed `ExampleImplementation.sol` contract. + + + + 1. From the **Encoded data** field, copy the encoded address. + 1. Navigate back to the Chainlink Automation app. In the **Check Data** field, enter `0x` and paste in the ABI encoded address of the `ExampleImplementation.sol` contract. + +1. Click **Register upkeep** and confirm the transaction in your wallet. + +### Check emergency action + +Now the Chainlink Automation network will watch your contract for these trigger parameters. If the price from the feed you provided is above the `maxBalance` threshold that was specified, the `executeEmergencyAction()` function will trigger. As defined in `ExampleImplementation.sol`, the function increments a counter: + +```solidity +/** + * executes emergency action + */ +function executeEmergencyAction() external { + counter += 1; + circuitbrokenflag = true; + emit emergencyActionPerformed(counter, feedAddress); +} +``` + +1. Navigate to your upkeep in the Chainlink Automation app. If the `executeEmergencyAction()` function is triggered, you will see "Perform upkeep" logs listed in the **History** section. +1. Navigate to Remix and expand the details for your deployed `ExampleImplementation.sol` contract. Click the **counter** button to view the value of the `counter` variable. +1. If the counter was incremented once, you should see `0: uint256: 1` as the output: + + +### Update the example implementation contract + +If you want to update your `ExampleImplementation.sol` contract, you can redeploy it with updated values and then use the same Automation upkeep. For example, to update the `maxBalance`: + +1. Redeploy the `ExampleImplementation.sol` contract with your updated `maxBalance` value. +1. ABI encode the address of your newly deployed `ExampleImplementation.sol` contract. +1. In the Chainlink Automation app, within the **Actions** menu for your existing upkeep, click **Edit check data**: + + + +1. Enter `0x`, paste the new ABI-encoded contract address, and click **Change check data**. MetaMask opens and prompts you to confirm the transaction. + + +You can use the same process to make other changes to your example implementation contract, like changing the logic in `executeEmergencyAction()` or changing the price feed that you're monitoring. + +## Cleanup + +If you want to experiment further with this tutorial, you can pause the Automation upkeep so that it stops running while you work on updating your example implementation contract. Otherwise, you can cancel the upkeep to reclaim any unused testnet LINK back to your wallet. Both options are located in the Chainlink Automation app within the **Actions** menu on your upkeep's details page. diff --git a/src/content/quickstarts/functions-demo-app.mdx b/src/content/quickstarts/functions-demo-app.mdx new file mode 100644 index 000000000000..21d2b3900e1f --- /dev/null +++ b/src/content/quickstarts/functions-demo-app.mdx @@ -0,0 +1,109 @@ +--- +section: chainlinkFunctions +date: Last Modified +title: "Chainlink Functions Demo App" +whatsnext: { "FAQs": "/chainlink-automation/faqs" } +--- + +import { Aside } from "@components" + +The [Chainlink Functions Demo App](https://github.com/smartcontractkit/chainlink-functions-demo-app) is designed to run on the Mumbai testnet (Polygon). It uses [Chainlink Functions](/chainlink-functions). The functionality allows users to donate MATIC to their favorite GitHub creators. Authors of those repositories can then claim their donations. Donations are made in an amount of MATIC per amount of Stars the repository has. + +Chainlink Functions is used to determine the total donation amount by multiplying the MATIC amount by the star count. There's no back-end involved in the whole donation process. + + + +## Objective + +You will create and manage a ledger contract to be used by the dApp. Tracking interaction between accounts gives a better insight into how the dApp functions. Using a different wallet for contract creation and dApp usage is preferable. + +## Before you begin + +Before you start this tutorial, complete the following items: + +- If you are new to smart contract development, learn how to [Deploy Your First Smart Contract](/getting-started/deploy-your-first-contract). +- Set up a cryptocurrency wallet such as [MetaMask](https://metamask.io/). +- To deploy this contract on testnets, ensure the deployer account has testnet ERC-677 LINK. Use the [LINK faucet](https://faucets.chain.link/) to retrieve testnet LINK. + - Get testnet MATIC from [faucet.polygon.technology](https://faucet.polygon.technology) to pay for your on-chain transactions. + - Get at least 2 ERC-677 testnet LINK from [faucets.chain.link/mumbai](https://faucets.chain.link/mumbai). +- Install [Node.js](https://nodejs.org/en/download). +- Install pnpm: `npm install -g pnpm` +- Optional: If you want to verify your contracts onchain, create an account on [Polygonscan](http://polygonscan.com) and get an API key. Note that you'll need to create an account for the main network, which also works for the testnet. + +### Steps to implement + +Run these from the project directory where you've cloned this repo. + +1. Clone the repo and change directories: + + ```bash + git clone https://github.com/smartcontractkit/chainlink-functions-demo-app.git && cd chainlink-functions-demo-app + ``` + +1. Install the dependencies using `pnpm`: + + ```bash + pnpm install + ``` + +1. Create a `.env` file from the template: + + ```bash + cp .env.example .env + ``` + +1. In the `.env` file specify the following variables: + + - `PRIVATE_KEY` - Private key of your wallet used for deploying contracts. + - `NEXT_PUBLIC_GA_TRACKING_ID` - Optional - Set to your Google Analytics tracking id to enable GA. + - `POLYGONSCAN_API_KEY` - Optional - API key for Polygonscan to verify and read contracts. + +1. Generate and build all required files: + + ```bash + pnpm build + ``` + +1. Deploy the Ledger contract: + + ```bash + npx hardhat project:deploy + ``` + +1. The deployment script prints the deployed contract address to your terminal. Add the address in the `NEXT_PUBLIC_CONTRACT_ADDRESS` environment variable to your `.env` file. + +1. Optionally, you can verify the contract. This allows you to decode the bytecode on Polygonscan. Verify the contract with `npx hardhat verify`: + + ```bash + npx hardhat verify --constructor-args arguments.js $NEXT_PUBLIC_CONTRACT_ADDRESS + ``` + + Replace `$NEXT_PUBLIC_CONTRACT_ADDRESS` with your contract address if you don't have the address in your shell environment. + +1. Create a Chainlink Functions subscription and fund it using the `project:fund` script: + + ```bash + npx hardhat project:fund + ``` + + For more information on how to manage your subscription, read [the official documentation](https://docs.chain.link/chainlink-functions/resources/subscriptions). + +1. Store the subscription ID in the `NEXT_PUBLIC_SUBSCRIPTION_ID` environment variable in your `.env` file. + +## Run the example + +1. Run the dev server: + + ```bash + pnpm dev + ``` + +1. In the terminal output, you'll see a URL with a port number. Open this URL in your browser to see the UI running locally. diff --git a/src/content/quickstarts/giveaway.mdx b/src/content/quickstarts/giveaway.mdx new file mode 100644 index 000000000000..fe9a2f8c6e9e --- /dev/null +++ b/src/content/quickstarts/giveaway.mdx @@ -0,0 +1,431 @@ +--- +section: automation +date: Last Modified +title: Giveaway Manager +whatsnext: { "FAQs": "/chainlink-automation/faqs" } +--- + +import { Aside, ClickToZoom, CopyText } from "@components" +import { TabsContent } from "@components/Tabs" + +The Giveaway Manager app is a highly configurable proof of concept for provably-fair giveaways using Chainlink Automation and VRF. It is capable of drawing winners from a CSV list or onchain entries using VRF Direct Funding and Automation. Fulfillment is not included, and this app demonstrates provably fair selection only. + +![image](https://i.imgur.com/lCIAVrR.png) + +## Objective + +In this tutorial, you will deploy a local user interface to enable giveaways using Chainlink VRFv2 Direct Funding. The UI was designed to run simple drawings and giveaways with just a CSV list of participants. Chainlink Automation provisioning and setup is also covered to enable timed-based, dynamic drawings. + +You can use this to run: + +- Static Giveaways: Fairly and transparently pick winners from a participant list in CSV format. Unique participant IDs can be anything (emails, numbers, addresses). They are hashed so no user data is stored on-chain. +- Dynamic Giveaways: Create a giveaway that participants can enter on their own via tx, then fairly and transparently pick winners whenever you'd like. This allows participants to register over a set period of time without the admin needing a full participant list like a static giveaway. + + + +## Before you begin + + + +Before you start this tutorial, complete the following items: + +- Set up a cryptocurrency wallet such as [MetaMask](https://metamask.io/). +- Fund your wallet with the following testnet tokens: + - Get testnet MATIC from [faucet.polygon.technology](https://faucet.polygon.technology) to pay for your on-chain transactions. + - Request ERC-677 testnet LINK from [faucets.chain.link/mumbai](https://faucets.chain.link/mumbai). You will need [at least 5.1 LINK](#required-balance-amounts) to set up each giveaway with this app. + +## Setup steps + +Setting up the app requires several steps: + +1. [Clone the repo](#clone-the-repo) +1. [Create a block explorer API key](#create-a-block-explorer-api-key) +1. [Set contract environment variables](#set-contract-environment-variables) +1. [Install Foundry](#install-foundry) +1. [Install contract dependencies](#install-contract-dependencies) +1. [Deploy contract](#deploy-contract) +1. [Install UI dependencies](#install-ui-dependencies) +1. [Run and view the UI](#run-and-view-the-ui) +1. [Testing](#testing) + +### Clone the repo + +- Run `git --version` to check your `git` installation. You should see an output similar to `git version x.x.x`. If not, install [git](https://git-scm.com/book/en/v2/Getting-Started-Installing-Git). +- Install [NodeJS](https://nodejs.org/) +- Install [yarn](https://yarnpkg.com/) + +```bash +git clone https://github.com/smartcontractkit/quickstart-giveaway.git +``` + +### Create a block explorer API key + +The recommended networks for this app are: + +- Ethereum mainnet and Goerli testnet (Sepolia is not supported) +- Polygon mainnet and Mumbai testnet + +For demo purposes, use Polygon Mumbai for this tutorial. Create a block explorer API key to verify contracts on your preferred network: + +- [Polygonscan](https://docs.polygonscan.com/getting-started/viewing-api-usage-statistics) +- [Etherscan](https://docs.etherscan.io/getting-started/viewing-api-usage-statistics) + +### Set contract environment variables + +1. Prepare the following values: + + - The RPC URL for your deployment network, using an [RPC node provider](https://ethereum.org/en/developers/docs/nodes-and-clients/nodes-as-a-service/) such as [Infura](https://www.infura.io/) or [Alchemy](https://www.alchemy.com/). + - The private key for your deployer account. If your deployer account is in MetaMask, [export your private key from MetaMask](https://support.metamask.io/hc/en-us/articles/360015289632-How-to-export-an-account-s-private-key). + - The block explorer API key from Etherscan or Polygonscan that you [created earlier](#create-a-block-explorer-api-key). + + | Parameter | Description | Example | + | ----------------- | --------------------------------------------------------------------------------------- | ------------------------------------------------------ | + | `NETWORK_RPC_URL` | The RPC URL for the network you want to deploy to. | `https://polygon-mumbai.g.alchemy.com/v2/your-api-key` | + | `PRIVATE_KEY` | The private key of the account you want to deploy from.
Add `0x` before your key. | `0xabc123abc123abc123abc123abc123...` | + | `EXPLORER_KEY` | The block explorer API key needed for contract verification. | `ABC123ABC123ABC123ABC123ABC123ABC1` | + +1. In the `contracts` directory, create a `.env` file for your contract environment variables: + + ```bash + # /contracts + $ touch .env + $ open .env + ``` + + If you're going to push this to your own repo, make sure this `.env` file is untracked, and consider using a secure env management package instead. + +1. Add this content to your file and fill in the values. Do not use quotation marks when filling in the values. Add `0x` to the beginning of your private key. + + ```bash + # Do NOT use quotes to assign values! + + # Network RPCs + export RPC_URL= + + # Private key for contract deployment + export PRIVATE_KEY= + + # Explorer API key used to verify contracts + export EXPLORER_KEY= + ``` + +### Install Foundry + +Refer to the [Foundry installation instructions](https://book.getfoundry.sh/getting-started/installation). + +1. Download foundryup: + + ```bash + # Download foundry + $ curl -L https://foundry.paradigm.xyz | bash + ``` + +1. Restart your terminal session, then install Foundry by running: + + ```bash + foundryup + ``` + + + +### Install contract dependencies + +Install [GNU make](https://www.gnu.org/software/make/) if you do not already have it. The functionality of the project is wrapped in the [makefile](https://github.com/smartcontractkit/quickstarts-giveaway/blob/main/contracts/Makefile). Reference the below commands based on your OS or go to [Make documentation](https://www.gnu.org/software/make/manual/make.html). + +{/* prettier-ignore */} + + macOS + Windows + + 1. The Xcode command line tools include `make`. If you've previously installed Xcode, skip to step 2 to verify your installation. Otherwise, open a Terminal window and run: + ```sh + xcode-select --install + ``` + Alternatively, if you prefer to [use Homebrew](https://formulae.brew.sh/formula/make), be aware that GNU `make` is installed as `gmake`. + 1. Verify your `make` installation: + ```sh + make + ``` + If `make` is installed successfully, you will get the following output: + ```sh + make: *** No targets specified or no makefile found. Stop. + ``` + + + 1. If you're using WSL, open an Ubuntu terminal and run: + ```sh + sudo apt install make + ``` + 1. [Edit your path variable to include `make`](https://help.ubuntu.com/community/EnvironmentVariables#Persistent_environment_variables). + 1. Verify your `make` installation: + ```sh + make + ``` + If `make` is installed successfully, you will get the following output: + ```sh + make: *** No targets specified or no makefile found. Stop. + ``` + + + +Install contract dependencies if changes have been made to contracts: + +```bash +# /contracts +$ make install +``` + +### Deploy contract + +```bash +# /contracts +$ make deploy +``` + +Save the deployed contract address from your terminal output. This is the giveaway contract manager address that you will need when you [run the UI](#run-and-view-the-ui). Scroll up in the terminal output and look for your contract address, which appears shortly after the `Success` message: + +```shell +##### mumbai +✅ [Success]Hash: 0x6feb039ea7533c2ad1b385d73370a38ccb330f76360dfa1444b26c8ba57c6e0a +Contract Address: 0x97fD95333b827dae8c58BC74394Cc8E7d83fDEbA +Block: 40656570 +Paid: 0.01104793954 ETH (5469277 gas * 2.02 gwei) +``` + +### Install UI dependencies + +1. To install the UI dependencies, navigate to the `client` directory and run: + + ```bash + # /client + # (Mac) you may need to run 'source ~/.nvm/nvm.sh' + nvm use + ``` + + You may be prompted to install `nvm` and node v14.17.4. This process takes a few minutes. + +1. After your node version is set, run: + + ```bash + yarn + ``` + +### Run and view the UI + +Set environment variables to run the UI and then view it locally. + +1. Prepare your UI environment variables. These are needed for each time you want to run the UI: + + | Item | Value | + | -------------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | + | `UI_GIVEAWAY_MANAGER_CONTRACT_ADDRESS` | The address of the Giveaway Contract Manager contract that you [deployed earlier](#deploy-contract) | + | `UI_LINK_TOKEN_CONTRACT_ADDRESS` | For Polygon Mumbai:
See all [LINK token contract addresses](/resources/link-token-contracts) | + | `UI_KEEPER_REGISTRY_CONTRACT_ADDRESS` | For Polygon Mumbai:
This app currently supports Automation v1.2. See all [Automation registry contract addresses](/chainlink-automation/supported-networks/) | + +1. Navigate to the `/client/packages/ui` directory, and run these commands to set up your UI environment variables. Do not use quotes to assign values: + ```bash + # /client/packages/ui + export UI_GIVEAWAY_MANAGER_CONTRACT_ADDRESS= + export UI_LINK_TOKEN_CONTRACT_ADDRESS= + export UI_KEEPER_REGISTRY_CONTRACT_ADDRESS= + ``` +1. After setting the environment variables, run the UI locally: + ```bash + yarn start + ``` +1. To view the UI, open your browser at [localhost:3005](localhost:3005). + +## Implement a static giveaway + +1. Navigate to http://localhost:3005/ in your browser. +1. In the upper right corner, click **Connect wallet**. Connect your wallet and ensure the proper network is selected. + + + +1. Click **Create giveaway**. + + + +1. Static giveaway is selected by default. Fill in the details to configure the giveaway: + + - Create a CSV file with a list of giveaway participants. Below the **Participants** field, download the example CSV participant file and fill it in. For testing, you can use a list of dummy wallet addresses. + - Fill in the rest of the fields and upload your CSV list of participants, then **Create** and confirm the wallet transaction that pops up. + + {" "} + + + +1. After the transaction processes, you should get a "Giveaway successfully created" message. Click the UI card for the new giveaway you just created: + + + +1. The details for your giveaway are displayed. Click **Pick Winners** and confirm the wallet transaction. + + + +1. A "Pending Transaction" popup displays while the transaction is processing. Once the transaction is complete, you should see a "Successfully picked winners" message. Click **Close**. + + - Optional: You can reference the "View VRF Request" link to help prove the giveaway was fair. + + + +1. At the bottom of the Giveaway page, upload your original participants (contestants) CSV again to see who won: + + + +1. After you've uploaded the CSV, click **Check Winners**: + + + +1. A **Giveaway winners** popup displays and shows the winners. This demo used a CSV of dummy wallet addresses. You can use whichever unique identifiers you want. Since the identifier is hashed before it's put on-chain, the data remains private and visible only to you as the admin. + + + + You can export a CSV list of all the winners and share the list with participants if you wish. You can also choose to provide the VRF transaction from Step 7 as evidence that Chainlink VRF was used for fairness. + +## Implement a dynamic giveaway + +1. Navigate to http://localhost:3005/ in your browser. +1. In the upper right corner, click **Connect wallet**. Connect your wallet and ensure the proper network is selected. + + + +1. Click **Create giveaway**. + + + +1. For the **Select giveaway type** field, click **Dynamic**. + + + +1. Fill in the details to configure the giveaway: + + - If you want the Giveaway to close automatically after a certain duration, click **Enable Automation** and enter the duration. If you don't do this, you must manually close the Giveaway before drawing. + - Click **Create** and confirm the wallet transaction that pops up. + + + +1. After the transaction processes, you should get a "Giveaway successfully created" message. Click the UI card for the new giveaway you just created: + + + +1. The details for your giveaway are displayed. At the bottom, there are a few options: + + - **Join Giveaway**: Allows the admin to submit a tx to join the giveaway (useful for some use cases) + - **Pick Winners**: You can pick the winners at any time, if you specified a duration it will automatically close the giveaway so that nobody can enter anymore. You'll still need to run this to pick the winners. + - **Cancel Giveaway**: Cancel the giveaway and prevent anyone from entering. + + + +1. If you enabled a duration for the giveaway, you'll see the status change to **Staged** after the duration is complete. This means nobody else can join the giveaway and you're ready to pick winners. + + + +1. The details for your giveaway are displayed. Click **Pick Winners** and confirm the wallet transaction. + + + +1. A "Pending Transaction" popup displays while the transaction is processing. Once the transaction is complete, you should see a "Successfully picked winners" message. Click **Close**. + + - Optional: You can reference the "View VRF Request" link to help prove the giveaway was fair. + + + +1. After the transaction is confirmed, the Giveaway status changes to Finish. Click **View Winners** to see the wallet addresses of those who won. + + + + You can export a CSV list of all the winners and share the list with participants if you wish. You can also choose to provide the VRF transaction as evidence that Chainlink VRF was used for fairness. + +## Notes + +### Testing + +To test contracts, navigate to the `contracts` directory and run the following command: + +```bash +# /contracts +make test-contracts-all +``` + +To test the UI, navigate to the `/client/packages/ui` directory and run the following commands: + +```bash +# /client/packages/ui +$ yarn test +$ yarn tsc +$ yarn lint +$ yarn prettier +``` + +### Required balance amounts + +As a creator of a giveaway, the minimum token requirements are needed to ensure that your giveaway is created and finished without issues. All unused LINK token amounts are able to be withdrawn after completion of giveaway. + +- 5.1 LINK + - 0.1 (VRF request) + - 5 (Automation subscription) + +### Giveaway Status + +After picking winners is initiated in the UI, the status of the giveaway is moved to `pending`. Each subsequent block is then checked to see if the VRF request has been finished and winners picked. Once found, the status is automatically moved to `finished`. The winners are then able to be viewed and leftover LINK is able to be withdrawn. + +### Developer Integration for Entering Dynamic Giveaway + +The Giveaway contract is able to be integrated with any application that is able to send a transaction to the contract. The user will need to call the `enterGiveaway` function with the following parameters: + +- `giveawayId` - The ID of the giveaway that the user is entering +- `entries` - The amount of entries the user is purchasing +- `proof` The merkle proof of the user's entry if the giveaway is permissioned + +This is how the UI in this repo calls the `enterGiveaway` function using `wagmi`: + +```javascript +export const enterGiveaway = async (params: contracts.EnterGiveawayParams) => { + try { + const { id, proof, fee } = params + const config = await prepareWriteContract({ + address: giveawayManagerContractAddress, + abi: giveawayManagerABI, + functionName: 'enterGiveaway', + overrides: { + value: ethers.utils.parseEther(fee) + }, + args: [id, params.entries ? params.entries : 1, proof ? proof : []] + }) + const data = await writeContract(config) + return data + } catch (error: any) { + throw new Error(`Error entering giveaway: ${error.message}`) + } +} + +export interface EnterGiveawayParams { + id: number + entries?: number + proof?: string[] + fee: string +} +``` diff --git a/src/content/quickstarts/vrf-enabled-lootbox-pack.mdx b/src/content/quickstarts/vrf-enabled-lootbox-pack.mdx index 4ee28ed0abfc..077f93543296 100644 --- a/src/content/quickstarts/vrf-enabled-lootbox-pack.mdx +++ b/src/content/quickstarts/vrf-enabled-lootbox-pack.mdx @@ -221,7 +221,7 @@ Now that your example is configured, you can test, deploy, and run the example. Run the `npx hardhat run` command and replace `` with the network that you want to deploy to. The network must be configured in [`hardhat.config.ts`](https://github.com/smartcontractkit/quickstarts-lootbox/blob/main/hardhat.config.ts). ```bash -npx hardhat run scripts/deploy.js --network +npx hardhat run scripts/deploy.ts --network ``` The [deploy script](https://github.com/smartcontractkit/quickstarts-lootbox/blob/main/scripts/deploy.ts) also completes the following actions: