Skip to content

Instantly share code, notes, and snippets.

@pguso
Created November 2, 2022 15:14
Show Gist options
  • Save pguso/26f0707d02bd7fe63133f846cc276508 to your computer and use it in GitHub Desktop.
Save pguso/26f0707d02bd7fe63133f846cc276508 to your computer and use it in GitHub Desktop.
Elrond Crowdfunding Smart Contract
#![no_std]
elrond_wasm::imports!();
elrond_wasm::derive_imports!();
#[derive(TopEncode, TopDecode, TypeAbi, PartialEq, Eq, Clone, Copy, Debug)]
pub enum Status {
FundingPeriod,
Successful,
Failed,
}
#[elrond_wasm::contract]
pub trait Crowdfunding {
#[init]
fn init(&self, target: BigUint, deadline: u64) {
require!(target > 0, "Target must be more than 0");
self.target().set(target);
require!(
deadline > self.get_current_time(),
"Deadline can't be in the past"
);
self.deadline().set(deadline);
}
#[endpoint]
#[payable("EGLD")]
fn fund(&self) {
let payment = self.call_value().egld_value();
require!(
self.status() == Status::FundingPeriod,
"cannot fund after deadline"
);
let caller = self.blockchain().get_caller();
self.deposit(&caller).update(|deposit| *deposit += payment);
}
#[view]
fn status(&self) -> Status {
if self.get_current_time() <= self.deadline().get() {
Status::FundingPeriod
} else if self.get_current_funds() >= self.target().get() {
Status::Successful
} else {
Status::Failed
}
}
#[view(getCurrentFunds)]
fn get_current_funds(&self) -> BigUint {
self.blockchain().get_sc_balance(&EgldOrEsdtTokenIdentifier::egld(), 0)
}
#[endpoint]
fn claim(&self) {
match self.status() {
Status::FundingPeriod => sc_panic!("cannot claim before deadline"),
Status::Successful => {
let caller = self.blockchain().get_caller();
require!(
caller == self.blockchain().get_owner_address(),
"only owner can claim successful funding"
);
let sc_balance = self.get_current_funds();
self.send().direct_egld(&caller, &sc_balance);
},
Status::Failed => {
let caller = self.blockchain().get_caller();
let deposit = self.deposit(&caller).get();
if deposit > 0u32 {
self.deposit(&caller).clear();
self.send().direct_egld(&caller, &deposit);
}
},
}
}
// private
fn get_current_time(&self) -> u64 {
self.blockchain().get_block_timestamp()
}
// storage
#[view(getTarget)]
#[storage_mapper("target")]
fn target(&self) -> SingleValueMapper<BigUint>;
#[view(getDeadline)]
#[storage_mapper("deadline")]
fn deadline(&self) -> SingleValueMapper<u64>;
#[view(getDeposit)]
#[storage_mapper("deposit")]
fn deposit(&self, donor: &ManagedAddress) -> SingleValueMapper<BigUint>;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment