KLAYswap
Search…
Set Airdrop Operator

1. Contract Deploy

Deploy Guide
AirdropOperator Smart Contract Code
  • The LP and token to be airdropped are determined at the time of creation and cannot be modified.
  • Please check whether the Contract is deployed in the public environment.
  • Please pay attention to the security of the Owner account.
  • Please refer to Klaytn's Smart contract deployment here.
  • When using KLAY as an Airdrop Token, the Token Address must be set to 0x00000000000000000000000000000000000000000000.
1
pragma solidity 0.5.6;
2
3
interface IKIP7 {
4
function balanceOf(address account) external view returns (uint256);
5
function transfer(address recipient, uint256 amount) external returns (bool);
6
function approve(address spender, uint256 amount) external returns (bool);
7
function decimals() external view returns (uint8);
8
}
9
10
interface DistributionLike {
11
function estimateEndBlock() external view returns (uint);
12
function totalAmount() external view returns (uint);
13
function blockAmount() external view returns (uint);
14
function distributableBlock() external view returns (uint);
15
function distribution() external view returns (uint);
16
function targetEntries(uint) external view returns (address);
17
function targetCount() external view returns (uint);
18
function distributionRate(address) external view returns (uint);
19
}
20
21
interface TreasuryLike {
22
function fee() external view returns (uint);
23
function validOperator(address) external view returns (bool);
24
function distributions(address, address) external view returns (address);
25
function createKlayDistribution(uint, uint, address[] calldata, uint[] calldata) external payable;
26
function createTokenDistribution(address, uint, uint, uint, address[] calldata, uint[] calldata) external;
27
function depositKlay() external payable;
28
function depositToken(address, uint) external;
29
function refixBlockAmount(address, uint) external;
30
function refixDistributionRate(address, address[] calldata, uint[] calldata) external;
31
}
32
33
interface FactoryLike {
34
function poolExist(address) external view returns (bool);
35
}
36
37
contract Operator {
38
address constant public treasury = 0x29990aaF04f3D5Ac7d8C88beab1A009C1Ab4936e;
39
address constant public ksp = 0xC6a2Ad8cC6e4A7E08FC37cC5954be07d499E7654;
40
41
address public owner;
42
address public nextOwner;
43
address public token;
44
address public lp;
45
46
constructor(address _token, address _lp) public {
47
owner = msg.sender;
48
49
token = _token;
50
if(token != address(0)) require(IKIP7(token).decimals() != 0);
51
52
lp = _lp;
53
require(FactoryLike(ksp).poolExist(lp));
54
}
55
56
function version() external pure returns (string memory) {
57
return "AirdropOperator20210824";
58
}
59
60
// valid fallback
61
function () payable external { }
62
63
// ======================= owner method ===========================
64
65
modifier onlyOwner {
66
require(msg.sender == owner);
67
_;
68
}
69
70
function changeNextOwner(address _nextOwner) public onlyOwner {
71
nextOwner = _nextOwner;
72
}
73
74
function changeOwner() public {
75
require(msg.sender == nextOwner);
76
77
owner = nextOwner;
78
nextOwner = address(0);
79
}
80
81
//withdraw tokens remaining in the operator contract
82
function withdraw(address tokenAddr) public onlyOwner {
83
uint balance = 0;
84
if(tokenAddr == address(0)){
85
balance = (address(this)).balance;
86
if(balance > 0){
87
(bool res, ) = owner.call.value(balance)("");
88
require(res);
89
}
90
}
91
else{
92
balance = IKIP7(tokenAddr).balanceOf(address(this));
93
if(balance > 0){
94
require(IKIP7(tokenAddr).transfer(owner, balance));
95
}
96
}
97
}
98
99
// ====================== Stat ====================================
100
101
function getAirdropStat() public view returns (
102
address distributionContract, // airdrop distribution contract address
103
uint totalAmount, // Total amount of tokens to be distributed
104
uint blockAmount, // Amount of tokens to be distributed per block
105
uint distributableBlock, // Block number to airdrop start
106
uint endBlock, // Block number to airdrop end
107
uint distributed, // Amount of tokens distributed
108
uint remain, // amount remaining in the contract
109
uint targetCount, // airdrop target LP count
110
address[] memory targets, // airdrop target LP list
111
uint[] memory rates // airdrop target lp rate list
112
){
113
distributionContract = TreasuryLike(treasury).distributions(address(this), token);
114
115
DistributionLike dis = DistributionLike(distributionContract);
116
totalAmount = dis.totalAmount();
117
blockAmount = dis.blockAmount();
118
distributableBlock = dis.distributableBlock();
119
endBlock = dis.estimateEndBlock();
120
distributed = dis.distribution();
121
if(token == address(0)){
122
remain = (distributionContract).balance;
123
}
124
else{
125
remain = IKIP7(token).balanceOf(distributionContract);
126
}
127
128
targetCount = dis.targetCount();
129
targets = new address[](targetCount);
130
rates = new uint[](targetCount);
131
132
for(uint i = 0; i < targetCount; i++){
133
targets[i] = dis.targetEntries(i);
134
rates[i] = dis.distributionRate(targets[i]);
135
}
136
}
137
138
// ===================== Airdrop method ===========================
139
///@param totalAmount : Total amount of tokens to be distributed
140
///@param blockAmount : Amount of tokens to be distributed per block
141
///@param startBlock : Block number to airdrop start
142
function createDistribution(
143
uint totalAmount,
144
uint blockAmount,
145
uint startBlock
146
) public onlyOwner {
147
TreasuryLike Treasury = TreasuryLike(treasury);
148
149
require(Treasury.validOperator(address(this)));
150
require(Treasury.distributions(address(this), token) == address(0));
151
require(startBlock >= block.number);
152
153
address[] memory targets = new address[](1);
154
targets[0] = lp;
155
156
uint[] memory rates = new uint[](1);
157
rates[0] = 100;
158
159
if(Treasury.fee() > 0){
160
require(IKIP7(ksp).balanceOf(address(this)) >= Treasury.fee());
161
require(IKIP7(ksp).approve(treasury, Treasury.fee()));
162
}
163
164
if(token == address(0)){
165
require((address(this)).balance >= totalAmount);
166
Treasury.createKlayDistribution.value(totalAmount)(blockAmount, startBlock, targets, rates);
167
}
168
else {
169
require(IKIP7(token).balanceOf(address(this)) >= totalAmount);
170
require(IKIP7(token).approve(treasury, totalAmount));
171
Treasury.createTokenDistribution(token, totalAmount, blockAmount, startBlock, targets, rates);
172
}
173
}
174
175
// Airdrop token deposit
176
///@param amount : Amount of airdrop token to deposit
177
function deposit(uint amount) public onlyOwner {
178
TreasuryLike Treasury = TreasuryLike(treasury);
179
180
require(Treasury.validOperator(address(this)));
181
require(Treasury.distributions(address(this), token) != address(0));
182
require(amount != 0);
183
184
if(token == address(0)){
185
require((address(this)).balance >= amount);
186
Treasury.depositKlay.value(amount)();
187
}
188
else{
189
require(IKIP7(token).balanceOf(address(this)) >= amount);
190
require(IKIP7(token).approve(treasury, amount));
191
Treasury.depositToken(token, amount);
192
}
193
}
194
195
// Airdrop amount per block modification function
196
// The function is applied immediately from the called block
197
///@param blockAmount : airdrop block amount to change
198
function refixBlockAmount(uint blockAmount) public onlyOwner {
199
TreasuryLike Treasury = TreasuryLike(treasury);
200
201
require(Treasury.validOperator(address(this)));
202
require(Treasury.distributions(address(this), token) != address(0));
203
require(blockAmount != 0);
204
205
Treasury.refixBlockAmount(token, blockAmount);
206
}
207
}
208
Copied!

2. Contract Submission

3. ValidOperator Request

  • Operator registration request ([email protected])
  • Set Valid Operator after confirming contract distributed with Public AirdropOperator Code.