@version 1
condition triggered_by: transaction, on: deposit(level) do
now = Time.now() - Math.rem(Time.now(), 3600)
if transaction.timestamp >= 1848657600 do
throw(message: "deposit impossible once farm is closed", code: 1001)
end
end_timestamp_from_level_or_throw(level, now)
if get_user_transfer_amount_or_throw() < 0.00000143 do
throw(message: "deposit's minimum amount is 0.00000143", code: 1002)
end
true
end
actions triggered_by: transaction, on: deposit(level) do
now = Time.now() - Math.rem(Time.now(), 3600)
end_timestamp = end_timestamp_from_level_or_throw(level, now)
level = normalize_level(level, now)
start = nil
if level != "0" do
start = now
end
transfer_amount = get_user_transfer_amount_or_throw()
user_genesis_address = get_user_genesis()
deposits = nil
if now > 1722513600 do
res = calculate_new_rewards()
deposits = res.deposits
State.set("rewards_reserved", res.rewards_reserved)
State.set("last_calculation_timestamp", res.last_calculation_timestamp)
State.set("lp_tokens_deposited_by_level", res.lp_tokens_deposited_by_level)
else
deposits = State.get("deposits", Map.new())
end
# ================================================
# MERGE DEPOSITS (same end)
# ================================================
user_deposits = Map.get(deposits, user_genesis_address, [])
same_deposit = nil
new_user_deposits = []
for user_deposit in user_deposits do
if user_deposit.end == end_timestamp do
same_deposit = user_deposit
else
new_user_deposits = List.prepend(new_user_deposits, user_deposit)
end
end
new_deposit = nil
if same_deposit == nil do
new_deposit = [
amount: transfer_amount,
reward_amount: 0,
level: level,
start: start,
end: end_timestamp,
id: String.from_number(Time.now())
]
new_user_deposits = List.prepend(new_user_deposits, new_deposit)
else
new_deposit = Map.set(same_deposit, "amount", same_deposit.amount + transfer_amount)
new_user_deposits = List.prepend(new_user_deposits, new_deposit)
end
deposits = Map.set(deposits, user_genesis_address, new_user_deposits)
State.set("deposits", deposits)
lp_tokens_deposited = State.get("lp_tokens_deposited", 0)
State.set("lp_tokens_deposited", lp_tokens_deposited + transfer_amount)
lp_tokens_deposited_by_level = State.get("lp_tokens_deposited_by_level", Map.new())
lp_tokens_deposited_by_level =
Map.set(
lp_tokens_deposited_by_level,
new_deposit.level,
Map.get(lp_tokens_deposited_by_level, new_deposit.level, 0) + transfer_amount
)
State.set("lp_tokens_deposited_by_level", lp_tokens_deposited_by_level)
end
condition triggered_by: transaction, on: claim(deposit_id) do
if transaction.timestamp <= 1722513600 do
throw(message: "farm is not started yet", code: 2001)
end
user_genesis_address = get_user_genesis()
res = calculate_new_rewards()
user_deposit = get_user_deposit_or_throw(res.deposits, user_genesis_address, deposit_id)
if user_deposit.end > Time.now() do
throw(message: "claiming before end of lock", code: 2002)
end
if user_deposit.reward_amount <= 0 do
throw(message: "no reward to claim", code: 2003)
end
true
end
actions triggered_by: transaction, on: claim(deposit_id) do
user_genesis_address = get_user_genesis()
res = calculate_new_rewards()
State.set("last_calculation_timestamp", res.last_calculation_timestamp)
State.set("lp_tokens_deposited_by_level", res.lp_tokens_deposited_by_level)
user_deposit = get_user_deposit_or_throw(res.deposits, user_genesis_address, deposit_id)
if "UCO" == "UCO" do
Contract.add_uco_transfer(to: transaction.address, amount: user_deposit.reward_amount)
else
Contract.add_token_transfer(
to: transaction.address,
amount: user_deposit.reward_amount,
token_address: "UCO"
)
end
rewards_distributed = State.get("rewards_distributed", 0)
State.set("rewards_distributed", rewards_distributed + user_deposit.reward_amount)
State.set("rewards_reserved", res.rewards_reserved - user_deposit.reward_amount)
user_deposit = Map.set(user_deposit, "reward_amount", 0)
State.set("deposits", set_user_deposit(res.deposits, user_genesis_address, user_deposit))
end
condition triggered_by: transaction, on: withdraw(amount, deposit_id) do
user_genesis_address = get_user_genesis()
user_deposit =
get_user_deposit_or_throw(State.get("deposits", Map.new()), user_genesis_address, deposit_id)
if amount > user_deposit.amount do
throw(message: "amount requested is greater than amount deposited", code: 3001)
end
if user_deposit.end > Time.now() do
throw(message: "withdrawing before end of lock", code: 3002)
end
true
end
actions triggered_by: transaction, on: withdraw(amount, deposit_id) do
user_genesis_address = get_user_genesis()
deposits = nil
rewards_reserved = nil
if Time.now() > 1722513600 do
res = calculate_new_rewards()
deposits = res.deposits
rewards_reserved = res.rewards_reserved
State.set("last_calculation_timestamp", res.last_calculation_timestamp)
State.set("lp_tokens_deposited_by_level", res.lp_tokens_deposited_by_level)
else
deposits = State.get("deposits", Map.new())
rewards_reserved = State.get("rewards_reserved", 0)
end
user_deposit = get_user_deposit_or_throw(deposits, user_genesis_address, deposit_id)
if user_deposit.reward_amount > 0 do
if "UCO" == "UCO" do
Contract.add_uco_transfer(to: transaction.address, amount: user_deposit.reward_amount)
else
Contract.add_token_transfer(
to: transaction.address,
amount: user_deposit.reward_amount,
token_address: "UCO"
)
end
rewards_distributed = State.get("rewards_distributed", 0)
State.set("rewards_distributed", rewards_distributed + user_deposit.reward_amount)
rewards_reserved = rewards_reserved - user_deposit.reward_amount
end
State.set("rewards_reserved", rewards_reserved)
Contract.add_token_transfer(
to: transaction.address,
amount: amount,
token_address: 0x00006394EF24DFDC6FDFC3642FDC83827591A485704BB997221C0B9F313A468BDEAF
)
lp_tokens_deposited = State.get("lp_tokens_deposited", 0)
State.set("lp_tokens_deposited", lp_tokens_deposited - amount)
lp_tokens_deposited_by_level = State.get("lp_tokens_deposited_by_level", Map.new())
lp_tokens_deposited_by_level =
Map.set(
lp_tokens_deposited_by_level,
user_deposit.level,
Map.get(lp_tokens_deposited_by_level, user_deposit.level, 0) - amount
)
State.set("lp_tokens_deposited_by_level", lp_tokens_deposited_by_level)
if amount == user_deposit.amount do
deposits = remove_user_deposit(deposits, user_genesis_address, deposit_id)
else
user_deposit = Map.set(user_deposit, "reward_amount", 0)
user_deposit = Map.set(user_deposit, "amount", user_deposit.amount - amount)
deposits = set_user_deposit(deposits, user_genesis_address, user_deposit)
end
State.set("deposits", deposits)
end
condition triggered_by: transaction, on: relock(level, deposit_id) do
now = Time.now() - Math.rem(Time.now(), 3600)
if transaction.timestamp >= 1848657600 do
throw(message: "relock impossible once farm is closed", code: 4001)
end
end_timestamp = end_timestamp_from_level_or_throw(level, now)
level = normalize_level(level, now)
if level == "0" do
throw(message: "can't relock to flexible", code: 4002)
end
user_genesis_address = get_user_genesis()
user_deposit =
get_user_deposit_or_throw(State.get("deposits", Map.new()), user_genesis_address, deposit_id)
if level <= user_deposit.level do
throw(message: "Relock's level must be greater than current level", code: 4003)
end
true
end
actions triggered_by: transaction, on: relock(level, deposit_id) do
now = Time.now() - Math.rem(Time.now(), 3600)
end_timestamp = end_timestamp_from_level_or_throw(level, now)
level = normalize_level(level, now)
user_genesis_address = get_user_genesis()
res = calculate_new_rewards()
State.set("last_calculation_timestamp", res.last_calculation_timestamp)
user_deposit = get_user_deposit_or_throw(res.deposits, user_genesis_address, deposit_id)
if user_deposit.reward_amount > 0 do
if "UCO" == "UCO" do
Contract.add_uco_transfer(to: transaction.address, amount: user_deposit.reward_amount)
else
Contract.add_token_transfer(
to: transaction.address,
amount: user_deposit.reward_amount,
token_address: "UCO"
)
end
end
rewards_distributed = State.get("rewards_distributed", 0)
State.set("rewards_distributed", rewards_distributed + user_deposit.reward_amount)
State.set("rewards_reserved", res.rewards_reserved - user_deposit.reward_amount)
lp_tokens_deposited_by_level =
Map.set(
res.lp_tokens_deposited_by_level,
user_deposit.level,
Map.get(res.lp_tokens_deposited_by_level, user_deposit.level, 0) - user_deposit.amount
)
lp_tokens_deposited_by_level =
Map.set(
lp_tokens_deposited_by_level,
level,
Map.get(lp_tokens_deposited_by_level, level, 0) + user_deposit.amount
)
State.set("lp_tokens_deposited_by_level", lp_tokens_deposited_by_level)
user_deposit = Map.set(user_deposit, "reward_amount", 0)
user_deposit = Map.set(user_deposit, "start", now)
user_deposit = Map.set(user_deposit, "end", end_timestamp)
user_deposit = Map.set(user_deposit, "level", level)
State.set("deposits", set_user_deposit(res.deposits, user_genesis_address, user_deposit))
end
condition triggered_by: transaction, on: calculate_rewards() do
true
end
actions triggered_by: transaction, on: calculate_rewards() do
res = calculate_new_rewards()
State.set("last_calculation_timestamp", res.last_calculation_timestamp)
State.set("deposits", res.deposits)
State.set("rewards_reserved", res.rewards_reserved)
State.set("lp_tokens_deposited_by_level", res.lp_tokens_deposited_by_level)
end
condition(
triggered_by: transaction,
on: update_code(),
as: [
previous_public_key:
(
# Pool code can only be updated from the router contract of the dex
# Transaction is not yet validated so we need to use previous address
# to get the genesis address
previous_address = Chain.get_previous_address()
Chain.get_genesis_address(previous_address) == 0x000066CD867DA536A73D39CF05174387923358DC0009A29CC7162D4AED00675DAB55
)
]
)
actions triggered_by: transaction, on: update_code() do
params = [
0x00006394EF24DFDC6FDFC3642FDC83827591A485704BB997221C0B9F313A468BDEAF,
1722513600,
1848657600,
"UCO",
0x0000caf8d5baa374a2878fd87760a2a4ac9f5232dbb4f1143157a2006f95fff1b40e
]
new_code = Contract.call_function(0x000086E60124C986EBCAA5AFFB7A3DB8213072A132233FE61CF45651FDCF3C4CECEA, "get_farm_lock_code", params)
if Code.is_valid?(new_code) && !Code.is_same?(new_code, contract.code) do
Contract.set_type("contract")
Contract.set_code(new_code)
end
end
fun get_user_transfer_amount_or_throw() do
transfers = Map.get(transaction.token_transfers, 0x0000caf8d5baa374a2878fd87760a2a4ac9f5232dbb4f1143157a2006f95fff1b40e, [])
transfer = List.at(transfers, 0)
if transfer == nil do
throw(message: "no transfer found to the farm", code: 1003)
end
if transfer.token_address != 0x00006394EF24DFDC6FDFC3642FDC83827591A485704BB997221C0B9F313A468BDEAF do
throw(message: "invalid token transfered to the farm", code: 1004)
end
transfer.amount
end
fun calculate_new_rewards() do
rounded_now = Time.now() - Math.rem(Time.now(), 3600)
lp_tokens_deposited = State.get("lp_tokens_deposited", 0)
lp_tokens_deposited_by_level = State.get("lp_tokens_deposited_by_level", Map.new())
deposits = State.get("deposits", Map.new())
rewards_reserved = State.get("rewards_reserved", 0)
last_calculation_timestamp = State.get("last_calculation_timestamp", 1722513600)
if last_calculation_timestamp < rounded_now && last_calculation_timestamp < 1848657600 &&
lp_tokens_deposited > 0 do
duration_by_level = Map.new()
duration_by_level = Map.set(duration_by_level, "0", 0)
duration_by_level = Map.set(duration_by_level, "1", 7 * 86400)
duration_by_level = Map.set(duration_by_level, "2", 30 * 86400)
duration_by_level = Map.set(duration_by_level, "3", 90 * 86400)
duration_by_level = Map.set(duration_by_level, "4", 180 * 86400)
duration_by_level = Map.set(duration_by_level, "5", 365 * 86400)
duration_by_level = Map.set(duration_by_level, "6", 730 * 86400)
duration_by_level = Map.set(duration_by_level, "7", 1095 * 86400)
weight_by_level = Map.new()
weight_by_level = Map.set(weight_by_level, "0", 0)
weight_by_level = Map.set(weight_by_level, "1", 0.013)
weight_by_level = Map.set(weight_by_level, "2", 0.024)
weight_by_level = Map.set(weight_by_level, "3", 0.043)
weight_by_level = Map.set(weight_by_level, "4", 0.077)
weight_by_level = Map.set(weight_by_level, "5", 0.139)
weight_by_level = Map.set(weight_by_level, "6", 0.251)
weight_by_level = Map.set(weight_by_level, "7", 0.453)
rewards_allocated_at_each_year_end = Map.new()
rewards_allocated_at_each_year_end =
Map.set(rewards_allocated_at_each_year_end, "1", 45_000)
rewards_allocated_at_each_year_end =
Map.set(rewards_allocated_at_each_year_end, "2", 45_000 + 22_500)
rewards_allocated_at_each_year_end =
Map.set(
rewards_allocated_at_each_year_end,
"3",
45_000 + 22_500 + 11_250
)
rewards_allocated_at_each_year_end =
Map.set(
rewards_allocated_at_each_year_end,
"4",
45_000 + 22_500 + 11_250 + 8_750
)
# remaining reward balance
remaining_rewards_balance = 0
if "UCO" == "UCO" do
remaining_rewards_balance = contract.balance.uco
else
key = [token_address: "UCO", token_id: 0]
remaining_rewards_balance = Map.get(contract.balance.tokens, key, 0)
end
# giveaways are distributed linearly over time
time_elapsed_since_last_calc =
rounded_now - State.get("last_calculation_timestamp", 1722513600)
time_remaining_until_farm_end =
1848657600 - State.get("last_calculation_timestamp", 1722513600)
giveaways =
remaining_rewards_balance + State.get("rewards_distributed", 0) -
(45_000 + 22_500 + 11_250 + 8_750)
giveaways_to_allocate =
giveaways * (time_elapsed_since_last_calc / time_remaining_until_farm_end)
# loop through all the hours since last calculation
# period count is always minimum 1 because we ensure previously
# rounded_now > last_calculation_timestamp
periods_count =
(rounded_now - State.get("last_calculation_timestamp", 1722513600)) / 3600
last_calculation_timestamp = State.get("last_calculation_timestamp", 1722513600)
for i in 1..periods_count do
period_to = last_calculation_timestamp + 3600
# find year / seconds remaining
year = nil
seconds_until_end_of_year = nil
if last_calculation_timestamp < 1722513600 + 365 * 86400 do
year = "1"
seconds_until_end_of_year =
1722513600 + 365 * 86400 - last_calculation_timestamp
end
if year == nil && last_calculation_timestamp < 1722513600 + 730 * 86400 do
year = "2"
seconds_until_end_of_year =
1722513600 + 730 * 86400 - last_calculation_timestamp
end
if year == nil && last_calculation_timestamp < 1722513600 + 1095 * 86400 do
year = "3"
seconds_until_end_of_year =
1722513600 + 1095 * 86400 - last_calculation_timestamp
end
if year == nil do
year = "4"
seconds_until_end_of_year = 1848657600 - last_calculation_timestamp
end
rewards_to_allocate = 0
if period_to >= 1848657600 do
rewards_to_allocate = remaining_rewards_balance - rewards_reserved
else
giveaway_for_period =
giveaways_to_allocate *
((period_to - last_calculation_timestamp) / time_elapsed_since_last_calc)
# calculate reward for this period
rewards_to_allocate =
(rewards_allocated_at_each_year_end[year] - State.get("rewards_distributed", 0) -
rewards_reserved) *
((period_to - last_calculation_timestamp) / seconds_until_end_of_year) +
giveaway_for_period
end
# calculate tokens_weighted for each level
tokens_weighted_by_level = Map.new()
tokens_weighted_by_level =
Map.set(
tokens_weighted_by_level,
"0",
Map.get(lp_tokens_deposited_by_level, "0", 0) * weight_by_level["0"]
)
tokens_weighted_by_level =
Map.set(
tokens_weighted_by_level,
"1",
Map.get(lp_tokens_deposited_by_level, "1", 0) * weight_by_level["1"]
)
tokens_weighted_by_level =
Map.set(
tokens_weighted_by_level,
"2",
Map.get(lp_tokens_deposited_by_level, "2", 0) * weight_by_level["2"]
)
tokens_weighted_by_level =
Map.set(
tokens_weighted_by_level,
"3",
Map.get(lp_tokens_deposited_by_level, "3", 0) * weight_by_level["3"]
)
tokens_weighted_by_level =
Map.set(
tokens_weighted_by_level,
"4",
Map.get(lp_tokens_deposited_by_level, "4", 0) * weight_by_level["4"]
)
tokens_weighted_by_level =
Map.set(
tokens_weighted_by_level,
"5",
Map.get(lp_tokens_deposited_by_level, "5", 0) * weight_by_level["5"]
)
tokens_weighted_by_level =
Map.set(
tokens_weighted_by_level,
"6",
Map.get(lp_tokens_deposited_by_level, "6", 0) * weight_by_level["6"]
)
tokens_weighted_by_level =
Map.set(
tokens_weighted_by_level,
"7",
Map.get(lp_tokens_deposited_by_level, "7", 0) * weight_by_level["7"]
)
# calculate tokens weighted total
tokens_weighted_total = 0
for weighted_amount in Map.values(tokens_weighted_by_level) do
tokens_weighted_total = tokens_weighted_total + weighted_amount
end
if tokens_weighted_total > 0 do
# calculate rewards per level
rewards_to_allocated_by_level = Map.new()
rewards_to_allocated_by_level =
Map.set(
rewards_to_allocated_by_level,
"0",
tokens_weighted_by_level["0"] / tokens_weighted_total * rewards_to_allocate
)
rewards_to_allocated_by_level =
Map.set(
rewards_to_allocated_by_level,
"1",
tokens_weighted_by_level["1"] / tokens_weighted_total * rewards_to_allocate
)
rewards_to_allocated_by_level =
Map.set(
rewards_to_allocated_by_level,
"2",
tokens_weighted_by_level["2"] / tokens_weighted_total * rewards_to_allocate
)
rewards_to_allocated_by_level =
Map.set(
rewards_to_allocated_by_level,
"3",
tokens_weighted_by_level["3"] / tokens_weighted_total * rewards_to_allocate
)
rewards_to_allocated_by_level =
Map.set(
rewards_to_allocated_by_level,
"4",
tokens_weighted_by_level["4"] / tokens_weighted_total * rewards_to_allocate
)
rewards_to_allocated_by_level =
Map.set(
rewards_to_allocated_by_level,
"5",
tokens_weighted_by_level["5"] / tokens_weighted_total * rewards_to_allocate
)
rewards_to_allocated_by_level =
Map.set(
rewards_to_allocated_by_level,
"6",
tokens_weighted_by_level["6"] / tokens_weighted_total * rewards_to_allocate
)
rewards_to_allocated_by_level =
Map.set(
rewards_to_allocated_by_level,
"7",
tokens_weighted_by_level["7"] / tokens_weighted_total * rewards_to_allocate
)
# update each deposit with the rewards
updated_deposits = Map.new()
for user_address in Map.keys(deposits) do
user_deposits = deposits[user_address]
updated_user_deposits = []
for user_deposit in user_deposits do
if user_deposit.level != "0" do
# calc rewards
user_deposit =
Map.set(
user_deposit,
"reward_amount",
user_deposit.reward_amount +
user_deposit.amount * weight_by_level[user_deposit.level] /
tokens_weighted_by_level[user_deposit.level] *
rewards_to_allocated_by_level[user_deposit.level]
)
# on level change, update cursors and deposit
previous_level = String.from_number(String.to_number(user_deposit.level) - 1)
if user_deposit.end - duration_by_level[previous_level] <= period_to do
lp_tokens_deposited_by_level =
Map.set(
lp_tokens_deposited_by_level,
user_deposit.level,
Map.get(lp_tokens_deposited_by_level, user_deposit.level, 0) -
user_deposit.amount
)
lp_tokens_deposited_by_level =
Map.set(
lp_tokens_deposited_by_level,
previous_level,
Map.get(lp_tokens_deposited_by_level, previous_level, 0) + user_deposit.amount
)
user_deposit = Map.set(user_deposit, "level", previous_level)
if previous_level == "0" do
user_deposit = Map.set(user_deposit, "start", nil)
user_deposit = Map.set(user_deposit, "end", 0)
end
end
end
updated_user_deposits = List.prepend(updated_user_deposits, user_deposit)
end
updated_deposits = Map.set(updated_deposits, user_address, updated_user_deposits)
end
deposits = updated_deposits
rewards_reserved = rewards_reserved + rewards_to_allocate
last_calculation_timestamp = period_to
end
end
else
# edge case when lp_tokens_deposited = 0
if last_calculation_timestamp < rounded_now && last_calculation_timestamp < 1848657600 do
last_calculation_timestamp = rounded_now
end
end
[
deposits: deposits,
rewards_reserved: rewards_reserved,
last_calculation_timestamp: last_calculation_timestamp,
lp_tokens_deposited_by_level: lp_tokens_deposited_by_level
]
end
export fun(get_farm_infos()) do
now = Time.now() - Math.rem(Time.now(), 3600)
reward_year1 = 0
reward_year2 = 0
reward_year3 = 0
reward_year4 = 0
if now < 1722513600 + 365 * 86400 - 1 do
reward_year1 =
45_000 - State.get("rewards_reserved", 0) - State.get("rewards_distributed", 0)
reward_year2 = 22_500
reward_year3 = 11_250
reward_year4 = 8_750
end
if reward_year1 == 0 && now < 1722513600 + 730 * 86400 - 1 do
reward_year2 =
45_000 + 22_500 - State.get("rewards_reserved", 0) -
State.get("rewards_distributed", 0)
reward_year3 = 11_250
reward_year4 = 8_750
end
if reward_year2 == 0 && now < 1722513600 + 1095 * 86400 - 1 do
reward_year3 =
45_000 + 22_500 + 11_250 - State.get("rewards_reserved", 0) -
State.get("rewards_distributed", 0)
reward_year4 = 8_750
end
if reward_year3 == 0 && now < 1848657600 do
reward_year4 =
45_000 + 22_500 + 11_250 + 8_750 -
State.get("rewards_reserved", 0) - State.get("rewards_distributed", 0)
end
years = [
[
year: 1,
start: 1722513600,
end: 1722513600 + 365 * 86400 - 1,
rewards: reward_year1
],
[
year: 2,
start: 1722513600 + 365 * 86400,
end: 1722513600 + 730 * 86400 - 1,
rewards: reward_year2
],
[
year: 3,
start: 1722513600 + 730 * 86400,
end: 1722513600 + 1095 * 86400 - 1,
rewards: reward_year3
],
[
year: 4,
start: 1722513600 + 1095 * 86400,
end: 1848657600,
rewards: reward_year4
]
]
reward_token_balance = nil
if "UCO" == "UCO" do
reward_token_balance = contract.balance.uco
else
key = [token_address: "UCO", token_id: 0]
reward_token_balance = Map.get(contract.balance.tokens, key, 0)
end
weight_by_level = Map.new()
weight_by_level = Map.set(weight_by_level, "0", 0)
weight_by_level = Map.set(weight_by_level, "1", 0.013)
weight_by_level = Map.set(weight_by_level, "2", 0.024)
weight_by_level = Map.set(weight_by_level, "3", 0.043)
weight_by_level = Map.set(weight_by_level, "4", 0.077)
weight_by_level = Map.set(weight_by_level, "5", 0.139)
weight_by_level = Map.set(weight_by_level, "6", 0.251)
weight_by_level = Map.set(weight_by_level, "7", 0.453)
available_levels = Map.new()
available_levels = Map.set(available_levels, "0", now + 0)
available_levels = Map.set(available_levels, "1", now + 7 * 86400)
available_levels = Map.set(available_levels, "2", now + 30 * 86400)
available_levels = Map.set(available_levels, "3", now + 90 * 86400)
available_levels = Map.set(available_levels, "4", now + 180 * 86400)
available_levels = Map.set(available_levels, "5", now + 365 * 86400)
available_levels = Map.set(available_levels, "6", now + 730 * 86400)
available_levels = Map.set(available_levels, "7", now + 1095 * 86400)
filtered_levels = Map.new()
end_reached = false
for level in Map.keys(available_levels) do
start_level = Map.get(available_levels, level)
if start_level < 1848657600 do
filtered_levels = Map.set(filtered_levels, level, start_level)
else
if !end_reached && Map.size(filtered_levels) > 0 do
filtered_levels = Map.set(filtered_levels, level, 1848657600)
end_reached = true
end
end
end
lp_tokens_deposited_by_level = State.get("lp_tokens_deposited_by_level", Map.new())
lp_tokens_deposited_weighted = 0
for level in Map.keys(lp_tokens_deposited_by_level) do
lp_tokens_deposited_weighted =
lp_tokens_deposited_weighted +
lp_tokens_deposited_by_level[level] * weight_by_level[level]
end
deposits_count_by_level = Map.new()
for user_deposits in Map.values(State.get("deposits", Map.new())) do
for user_deposit in user_deposits do
deposits_count_by_level =
Map.set(
deposits_count_by_level,
user_deposit.level,
Map.get(deposits_count_by_level, user_deposit.level, 0) + 1
)
end
end
stats = Map.new()
for level in Map.keys(available_levels) do
remaining_rewards = []
for y in years do
rewards = 0
if lp_tokens_deposited_weighted > 0 do
rewards =
Map.get(lp_tokens_deposited_by_level, level, 0) * weight_by_level[level] /
lp_tokens_deposited_weighted * y.rewards
end
remaining_rewards =
List.append(remaining_rewards, start: y.start, end: y.end, remaining_rewards: rewards)
end
stats =
Map.set(stats, level,
weight: weight_by_level[level],
lp_tokens_deposited: Map.get(lp_tokens_deposited_by_level, level, 0),
deposits_count: Map.get(deposits_count_by_level, level, 0),
remaining_rewards: remaining_rewards
)
end
[
lp_token_address: 0x00006394EF24DFDC6FDFC3642FDC83827591A485704BB997221C0B9F313A468BDEAF,
reward_token: "UCO",
start_date: 1722513600,
end_date: 1848657600,
lp_tokens_deposited: State.get("lp_tokens_deposited", 0),
remaining_rewards: reward_token_balance - State.get("rewards_reserved", 0),
rewards_distributed: State.get("rewards_distributed", 0),
available_levels: filtered_levels,
stats: stats
]
end
export fun(get_user_infos(user_genesis_address)) do
reply = []
for user_deposit in Map.get(
State.get("deposits", Map.new()),
String.to_hex(user_genesis_address),
[]
) do
info = [
id: user_deposit.id,
amount: user_deposit.amount,
reward_amount: user_deposit.reward_amount,
level: user_deposit.level
]
if user_deposit.end > Time.now() do
info = Map.set(info, "end", user_deposit.end)
info = Map.set(info, "start", user_deposit.start)
end
reply = List.append(reply, info)
end
reply
end
fun get_user_genesis() do
Chain.get_genesis_address(Chain.get_previous_address(transaction))
end
fun get_user_deposit_or_throw(deposits, user_genesis_address, deposit_id) do
reply = nil
for user_deposit in Map.get(deposits, user_genesis_address, []) do
if user_deposit.id == deposit_id do
reply = user_deposit
end
end
if reply == nil do
throw(message: "deposit not found", code: 6004)
end
reply
end
fun set_user_deposit(deposits, user_genesis_address, deposit) do
updated_user_deposits = []
for user_deposit in Map.get(deposits, user_genesis_address, []) do
if user_deposit.id == deposit.id do
updated_user_deposits = List.prepend(updated_user_deposits, deposit)
else
updated_user_deposits = List.prepend(updated_user_deposits, user_deposit)
end
end
Map.set(deposits, user_genesis_address, updated_user_deposits)
end
fun remove_user_deposit(deposits, user_genesis_address, deposit_id) do
updated_user_deposits = []
for user_deposit in Map.get(deposits, user_genesis_address, []) do
if user_deposit.id != deposit_id do
updated_user_deposits = List.prepend(updated_user_deposits, user_deposit)
end
end
if List.size(updated_user_deposits) == 0 do
Map.delete(deposits, user_genesis_address)
else
Map.set(deposits, user_genesis_address, updated_user_deposits)
end
end
fun end_timestamp_from_level_or_throw(level, rounded_now) do
end_timestamp = nil
if !List.in?(["max", "flex", "0", "1", "2", "3", "4", "5", "6", "7"], level) do
throw(message: "invalid level", code: 6000)
end
if level == "max" do
if 1848657600 - rounded_now < 3 * 365 * 86400 do
end_timestamp = 1848657600
else
throw(message: "max only available when less than 3 years remaining", code: 6001)
end
else
if List.in?(["flex", "0"], level) do
end_timestamp = 0
else
duration_by_level = Map.new()
duration_by_level = Map.set(duration_by_level, "1", 7 * 86400)
duration_by_level = Map.set(duration_by_level, "2", 30 * 86400)
duration_by_level = Map.set(duration_by_level, "3", 90 * 86400)
duration_by_level = Map.set(duration_by_level, "4", 180 * 86400)
duration_by_level = Map.set(duration_by_level, "5", 365 * 86400)
duration_by_level = Map.set(duration_by_level, "6", 730 * 86400)
duration_by_level = Map.set(duration_by_level, "7", 1095 * 86400)
end_timestamp = rounded_now + duration_by_level[level]
if end_timestamp > 1848657600 do
throw(message: "lock's end cannot be greater than farm's end", code: 6002)
end
if end_timestamp <= 1722513600 do
throw(message: "lock's end cannot be lesser than farm's start", code: 6003)
end
end
end
end_timestamp
end
fun normalize_level(level, rounded_now) do
normalized_level = nil
if List.in?(["0", "1", "2", "3", "4", "5", "6", "7"], level) do
normalized_level = level
end
if level == "flex" do
normalized_level = "0"
end
if level == "max" do
duration_by_level = Map.new()
duration_by_level = Map.set(duration_by_level, "0", 0)
duration_by_level = Map.set(duration_by_level, "1", 7 * 86400)
duration_by_level = Map.set(duration_by_level, "2", 30 * 86400)
duration_by_level = Map.set(duration_by_level, "3", 90 * 86400)
duration_by_level = Map.set(duration_by_level, "4", 180 * 86400)
duration_by_level = Map.set(duration_by_level, "5", 365 * 86400)
duration_by_level = Map.set(duration_by_level, "6", 730 * 86400)
duration_by_level = Map.set(duration_by_level, "7", 1095 * 86400)
for l in Map.keys(duration_by_level) do
if normalize_level == nil && end_timestamp <= rounded_now + duration_by_level[l] do
normalize_level = l
end
end
end
normalized_level
end
Content (0 B)
{
"deposits": {
"00000BC0EBA2DBCE4455B46F5E51AFAABA6EB4C7FBA1D4E2E6DABD55DC70F9A04D6F": [
{
"amount": 1.0,
"end": 1728640800,
"id": "1726050537",
"level": "2",
"reward_amount": 202.53485376,
"start": 1726048800
},
{
"amount": 1.0,
"end": 0,
"id": "1725552158",
"level": "0",
"reward_amount": 913.99563398,
"start": null
},
{
"amount": 1.0e-5,
"end": 1757088000,
"id": "1725552233",
"level": "5",
"reward_amount": 0.09368918,
"start": 1725552000
}
],
"00006AFF130BEB6BE9B02B80FFC13DB5EABFB0A7D167BAFC9F2DF8F141D7755FB39F": [
{
"amount": 17.97108234,
"end": 0,
"id": "1724890822",
"level": "0",
"reward_amount": 933.29617689,
"start": null
}
]
},
"last_calculation_timestamp": 1726218000,
"lp_tokens_deposited": 19.97109234,
"lp_tokens_deposited_by_level": {
"0": 18.97108234,
"1": 0.0,
"2": 1.0,
"5": 1.0e-5
},
"rewards_distributed": 0,
"rewards_reserved": 2049.92036606
}
-
Secret shared with 1 key
Encoded secret
4D70C2B342A7A643C4D37338735BEFF590BF811602F4BE4F24B9B114034961577F80F7239E36DF60AD7384FB92D902FC658976A8C04BFD7F32EEECCA
Authorized keys
- 00017877BCF4122095926A49489009649603AB129822A19EF9D573B8FD714911ED7F
Contract recipients (0)
Inputs (0)
Contract inputs (0)
Unspent outputs (0)
Previous public key
00019C1A417F8E021A2D30FE6311D5E0CE4168FD16E23FF37A73C75FCAC8D213CCEF
Previous signature
FE3A26588B80F91156B74E399E521E7DCA31A104FA13AC4C78383C66EBA56CDE99721BA6864CFC49FE24352589BF6772F1F6C6ACAE693A6A61E9863B1EC8460B
Origin signature
304402202ED9B71D397D7D86BFC094AEECB129047CFE7A9E48ADF9A14FBDE5FE78F664A802207940CDAECC8BA44E7BCA8684FD57B2F1831123B40F5E71B2CDF3B73B81C8A841
Proof of work
010204AA023E1E039788AD4B8F713C8871CA39A177414A99A0788993AD725B1FBB7AD5E4CAC86151A9E03451DCACB1EFC100B1E450FCEDAF5E5005F3A4C503D1D29712
Proof of integrity
007F92B514F009436E090E313021DF317AA08B621E4E0154277DBBE72B461684B3
Coordinator signature
071507C367EA1BEC6EA00A9DE650306BE3410A5AE4F2569A75B41AE89382335F9E9B658393EB7F2B2AE3B0F7FC515D6B74D747F231AB04D2F8DAA3999FB1C80A
Validator #1 public key
0001AAFBD70CD1928E509736D7A3F072694F7AD7AA7BF5716FB0239146EE4B633F45
Validator #1 signature
C2F54ADB5ACB076E94982BFD545A4B126EC53099CAF51EE28321EE3295FCBBA0B47AB91C6798F5135306CFFD61D518A6698650AEA3012D6E11FD1B372DB5F001
Validator #2 public key
00016204A6DD6BA17388994E74A6529F509D1479FEFB67D8D55D1E450E30A30982D2
Validator #2 signature
68EB79E178CDCC58195AF0CBF1ACA660E6C08619B20BE8B809995888DBA166E6DB977B228CBFF73BF30B872B8B74C010DB178BD3B206116556E216C191628D07