@gooddollar/goodprotocol 2.0.5 → 2.0.6

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/package.json CHANGED
@@ -1,7 +1,10 @@
1
1
  {
2
2
  "name": "@gooddollar/goodprotocol",
3
- "version": "2.0.5",
3
+ "version": "2.0.6",
4
4
  "description": "GoodDollar Protocol",
5
+ "engines": {
6
+ "node": "18.x"
7
+ },
5
8
  "scripts": {
6
9
  "prepack": "npm run minimize",
7
10
  "build": "scripts/build.sh deploy",
@@ -1,6 +1,5 @@
1
1
  import { range, chunk, uniq } from "lodash";
2
2
  import { ethers as Ethers } from "hardhat";
3
- import fetch from "node-fetch";
4
3
 
5
4
  const ONE_DAY = 24 * 60 * 60;
6
5
  const ONE_HOUR = 60 * 60;
@@ -1,5 +1,4 @@
1
1
  import { range, sortBy } from "lodash";
2
- import fetch from "node-fetch";
3
2
  import PromisePool from "async-promise-pool";
4
3
  import fs from "fs";
5
4
  import { ethers } from "hardhat";
@@ -33,9 +32,7 @@ const main = async () => {
33
32
  // );
34
33
  // fs.writeFileSync("activeWalletsBalances.json", JSON.stringify(balances));
35
34
 
36
- balances = JSON.parse(
37
- fs.readFileSync("activeWalletsBalances.json").toString()
38
- );
35
+ balances = JSON.parse(fs.readFileSync("activeWalletsBalances.json").toString());
39
36
 
40
37
  const EPOCH = 60 * 60 * 6;
41
38
  const pool = new PromisePool({ concurrency: 30 });
@@ -44,9 +41,7 @@ const main = async () => {
44
41
 
45
42
  const graphQuery = async (start, skip) => {
46
43
  const query = `{
47
- walletStats(first: 1000 skip:${skip} where: { dateAppeared_gte: ${start} dateAppeared_lt:${
48
- start + EPOCH
49
- } }) {
44
+ walletStats(first: 1000 skip:${skip} where: { dateAppeared_gte: ${start} dateAppeared_lt:${start + EPOCH} }) {
50
45
  id
51
46
  dateAppeared
52
47
  balance
@@ -57,16 +52,13 @@ const main = async () => {
57
52
  }`;
58
53
  // console.log({ query });
59
54
  try {
60
- const { data = {}, errors } = await fetch(
61
- "https://api.thegraph.com/subgraphs/name/gooddollar/gooddollarfuse",
62
- {
63
- method: "POST",
64
- headers: {
65
- "Content-Type": "application/json"
66
- },
67
- body: JSON.stringify({ query })
68
- }
69
- ).then(_ => _.json());
55
+ const { data = {}, errors } = await fetch("https://api.thegraph.com/subgraphs/name/gooddollar/gooddollarfuse", {
56
+ method: "POST",
57
+ headers: {
58
+ "Content-Type": "application/json"
59
+ },
60
+ body: JSON.stringify({ query })
61
+ }).then(_ => _.json());
70
62
  errors && console.log({ errors });
71
63
  if (data?.walletStats?.length === 1000) {
72
64
  return data.walletStats.concat(await graphQuery(start, skip + 1000));
@@ -116,9 +108,7 @@ const etl = async () => {
116
108
  .join("\r\n"); // rows starting on new lines
117
109
  }
118
110
 
119
- const balances = JSON.parse(
120
- fs.readFileSync("activeWalletsLastUsed.json").toString()
121
- );
111
+ const balances = JSON.parse(fs.readFileSync("activeWalletsLastUsed.json").toString());
122
112
 
123
113
  let result = [];
124
114
 
@@ -131,24 +121,18 @@ const etl = async () => {
131
121
  }
132
122
  const top100 = result.slice(0, 100);
133
123
  const pool = new PromisePool({ concurrency: 30 });
134
- const provider = new ethers.providers.JsonRpcBatchProvider(
135
- "https://rpc.fuse.io"
136
- );
124
+ const provider = new ethers.providers.JsonRpcBatchProvider("https://rpc.fuse.io");
137
125
 
138
126
  for (let idx in top100) {
139
127
  pool.add(async () => {
140
128
  const record = top100[idx];
141
- let isContract =
142
- (await provider.getCode(record[0]).catch(e => "0x")) !== "0x";
129
+ let isContract = (await provider.getCode(record[0]).catch(e => "0x")) !== "0x";
143
130
  record[3] = isContract;
144
131
  });
145
132
  }
146
133
  await pool.all();
147
134
  console.log({ top100 });
148
- fs.writeFileSync(
149
- "activeWalletsLastUsed.csv",
150
- arrayToCsv(sortBy(result, _ => -Number(_[1])))
151
- );
135
+ fs.writeFileSync("activeWalletsLastUsed.csv", arrayToCsv(sortBy(result, _ => -Number(_[1]))));
152
136
  };
153
137
  // main().catch(e => console.log(e));
154
138
  etl();
@@ -1,6 +1,5 @@
1
1
  import { countBy, chunk, difference, flatten, sortBy } from "lodash";
2
2
  import fs from "fs";
3
- import fetch from "node-fetch";
4
3
  import { network, ethers, upgrades } from "hardhat";
5
4
  import { Contract, Provider, setMulticallAddress } from "ethers-multicall";
6
5
  import Identity from "../../artifacts/contracts/Interfaces.sol/IIdentity.json";
@@ -54,16 +53,11 @@ const hasRefunded = async wallets => {
54
53
  let startBlock = CLAIM_START_BLOCK;
55
54
  while (startBlock <= curBlock) {
56
55
  const events = await gd.queryFilter(
57
- gd.filters.Transfer(
58
- undefined,
59
- "0xd253A5203817225e9768C05E5996d642fb96bA86"
60
- ),
56
+ gd.filters.Transfer(undefined, "0xd253A5203817225e9768C05E5996d642fb96bA86"),
61
57
  startBlock,
62
58
  toBlock
63
59
  );
64
- const accounts = events
65
- .filter(e => e.args.amount >= 9622260)
66
- .map(_ => _.args.from.toLowerCase());
60
+ const accounts = events.filter(e => e.args.amount >= 9622260).map(_ => _.args.from.toLowerCase());
67
61
  refunded.push(...accounts);
68
62
  console.log("has refunded:", {
69
63
  startBlock,
@@ -81,10 +75,7 @@ const whereIsTheMoney = async noBalance => {
81
75
  for (let batch of chunk(noBalance, 100)) {
82
76
  const tos = await Promise.all(
83
77
  batch.map(async a => {
84
- const e = await gd.queryFilter(
85
- gd.filters.Transfer(a),
86
- CLAIM_START_BLOCK
87
- );
78
+ const e = await gd.queryFilter(gd.filters.Transfer(a), CLAIM_START_BLOCK);
88
79
  const tos = e.filter(_ => _.args.amount > 1000000).map(_ => _.args.to);
89
80
  return tos;
90
81
  })
@@ -92,24 +83,14 @@ const whereIsTheMoney = async noBalance => {
92
83
  targets.push(...flatten(tos));
93
84
  }
94
85
  const targetCounter = countBy(targets, _ => _);
95
- console.log(
96
- "transfer targets:",
97
- sortBy(Object.entries(targetCounter), "1").reverse()
98
- );
86
+ console.log("transfer targets:", sortBy(Object.entries(targetCounter), "1").reverse());
99
87
  };
100
88
  const main = async () => {
101
- const wallets = JSON.parse(fs.readFileSync("torefund.json").toString()).map(
102
- _ => _.toLowerCase()
103
- );
89
+ const wallets = JSON.parse(fs.readFileSync("torefund.json").toString()).map(_ => _.toLowerCase());
104
90
  console.log("Total Claimed:", wallets.length);
105
91
  const refunded = await hasRefunded(wallets);
106
92
  const notRefunded = difference(wallets, refunded);
107
- console.log(
108
- "refunded:",
109
- refunded.length,
110
- "not refunded:",
111
- notRefunded.length
112
- );
93
+ console.log("refunded:", refunded.length, "not refunded:", notRefunded.length);
113
94
 
114
95
  const noBalanceToRefund = await hasBalanceToRefund(notRefunded);
115
96
  await whereIsTheMoney(noBalanceToRefund);
@@ -1,5 +1,4 @@
1
1
  import { range, sortBy, toPairs } from "lodash";
2
- import fetch from "node-fetch";
3
2
  import PromisePool from "async-promise-pool";
4
3
  import fs from "fs";
5
4
  import { ethers } from "hardhat";
@@ -37,14 +36,7 @@ const main = async () => {
37
36
  const dailyBalance = [];
38
37
  for (let day of days) {
39
38
  dailyBalance.push(
40
- (
41
- await archive.getBalance(
42
- "0x01ab5966C1d742Ae0CFF7f14cC0F4D85156e83d9",
43
- day
44
- )
45
- )
46
- .div(1e10)
47
- .toNumber() / 1e8
39
+ (await archive.getBalance("0x01ab5966C1d742Ae0CFF7f14cC0F4D85156e83d9", day)).div(1e10).toNumber() / 1e8
48
40
  );
49
41
  }
50
42
  let curBlock = startBlock;
@@ -60,19 +52,15 @@ const main = async () => {
60
52
  const toBlock = Math.min(fromBlock + blockStep, endBlock);
61
53
  pool.add(async () => {
62
54
  const f = faucet.filters.WalletTopped();
63
- const events = await faucet
64
- .queryFilter(f, fromBlock, toBlock)
65
- .catch(e => {
66
- console.log("failed", { fromBlock, toBlock });
67
- return [];
68
- });
55
+ const events = await faucet.queryFilter(f, fromBlock, toBlock).catch(e => {
56
+ console.log("failed", { fromBlock, toBlock });
57
+ return [];
58
+ });
69
59
  events.forEach(e => {
70
60
  totalToppings += 1;
71
61
  totalAmount += Number(e.args.amount);
72
- toppingsByAddress[e.args.user] =
73
- (toppingsByAddress[e.args.user] || 0) + 1;
74
- toppingsByAmount[e.args.amount] =
75
- (toppingsByAmount[e.args.amount] || 0) + 1;
62
+ toppingsByAddress[e.args.user] = (toppingsByAddress[e.args.user] || 0) + 1;
63
+ toppingsByAmount[e.args.amount] = (toppingsByAmount[e.args.amount] || 0) + 1;
76
64
  });
77
65
  console.log("fetched events", {
78
66
  fromBlock,
@@ -1,5 +1,4 @@
1
1
  import { maxBy, range, sortBy, uniq, sum, flatten, countBy } from "lodash";
2
- import fetch from "node-fetch";
3
2
  import PromisePool from "async-promise-pool";
4
3
  import fs from "fs";
5
4
  import { ethers } from "hardhat";
@@ -39,10 +38,9 @@ const main = async () => {
39
38
  const incomingTxs = result
40
39
  .filter(
41
40
  _ =>
42
- [
43
- "0xca2f09c3ccfd7ad5cb9276918bd1868f2b922ea0",
44
- "0xd253a5203817225e9768c05e5996d642fb96ba86"
45
- ].includes(_.from) === false
41
+ ["0xca2f09c3ccfd7ad5cb9276918bd1868f2b922ea0", "0xd253a5203817225e9768c05e5996d642fb96ba86"].includes(
42
+ _.from
43
+ ) === false
46
44
  )
47
45
  .filter(_ => _.to === address.toLowerCase());
48
46
  const totalEarned = sum(incomingTxs.map(_ => Number(_.value))) / 100;
@@ -1,5 +1,4 @@
1
1
  import { last, range, sortBy } from "lodash";
2
- import fetch from "node-fetch";
3
2
  import PromisePool from "async-promise-pool";
4
3
  import fs from "fs";
5
4
  import { ethers } from "hardhat";
@@ -19,16 +18,13 @@ const main = async () => {
19
18
  }`;
20
19
  // console.log({ query });
21
20
  try {
22
- const { data = {}, errors } = await fetch(
23
- "https://api.thegraph.com/subgraphs/name/gooddollar/gooddollarfuse2",
24
- {
25
- method: "POST",
26
- headers: {
27
- "Content-Type": "application/json"
28
- },
29
- body: JSON.stringify({ query })
30
- }
31
- ).then(_ => _.json());
21
+ const { data = {}, errors } = await fetch("https://api.thegraph.com/subgraphs/name/gooddollar/gooddollarfuse2", {
22
+ method: "POST",
23
+ headers: {
24
+ "Content-Type": "application/json"
25
+ },
26
+ body: JSON.stringify({ query })
27
+ }).then(_ => _.json());
32
28
  errors && console.log({ errors });
33
29
  if (data?.goodBalances?.length === 1000) {
34
30
  const nextAddr = last(data?.goodBalances).id;
@@ -1,5 +1,4 @@
1
1
  import { maxBy, range, sortBy, flatten, uniq } from "lodash";
2
- import fetch from "node-fetch";
3
2
  import PromisePool from "async-promise-pool";
4
3
  import fs from "fs";
5
4
  import { Contract, Provider, setMulticallAddress } from "ethers-multicall";
@@ -487,9 +486,7 @@ const allProtocolAddresses: Array<string> = [
487
486
  ];
488
487
 
489
488
  setMulticallAddress(122, "0x3CE6158b7278Bf6792e014FA7B4f3c6c46fe9410");
490
- const fuseProvider = new ethers.providers.WebSocketProvider(
491
- "wss://rpc.gooddollar.org"
492
- );
489
+ const fuseProvider = new ethers.providers.WebSocketProvider("wss://rpc.gooddollar.org");
493
490
  const ethcallProvider = new Provider(fuseProvider, 122);
494
491
 
495
492
  const GD_FUSE = "0x495d133b938596c9984d462f007b676bdc57ecec";
@@ -534,31 +531,16 @@ const main = async () => {
534
531
  )
535
532
  );
536
533
 
537
- const checkWhitelisted = uniq(
538
- flatten(
539
- clean.map(_ => [_.args.from.toLowerCase(), _.args.to.toLowerCase()])
540
- )
541
- );
542
- const calls = checkWhitelisted.map(d =>
543
- identityContract.isWhitelisted(d)
544
- );
534
+ const checkWhitelisted = uniq(flatten(clean.map(_ => [_.args.from.toLowerCase(), _.args.to.toLowerCase()])));
535
+ const calls = checkWhitelisted.map(d => identityContract.isWhitelisted(d));
545
536
  const result = await ethcallProvider.all(calls);
546
537
  const whitelisted = checkWhitelisted.filter((v, i) => result[i]);
547
538
  const p2p = clean.filter(
548
- _ =>
549
- whitelisted.includes(_.args.to.toLowerCase()) ||
550
- whitelisted.includes(_.args.from.toLowerCase())
539
+ _ => whitelisted.includes(_.args.to.toLowerCase()) || whitelisted.includes(_.args.from.toLowerCase())
551
540
  );
552
541
  p2pTxs = p2pTxs.concat(p2p);
553
542
  uniques = uniques.concat(whitelisted);
554
- console.log(
555
- { fromBlock },
556
- results.length,
557
- clean.length,
558
- checkWhitelisted.length,
559
- whitelisted.length,
560
- p2p.length
561
- );
543
+ console.log({ fromBlock }, results.length, clean.length, checkWhitelisted.length, whitelisted.length, p2p.length);
562
544
  });
563
545
  });
564
546
 
@@ -1,5 +1,4 @@
1
1
  import { maxBy, range, sortBy } from "lodash";
2
- import fetch from "node-fetch";
3
2
  import PromisePool from "async-promise-pool";
4
3
  import fs from "fs";
5
4
  import { ethers } from "hardhat";
@@ -43,10 +42,7 @@ const main = async () => {
43
42
  ins.push(r);
44
43
  }
45
44
  });
46
- fs.writeFileSync(
47
- "tokenInOut.json",
48
- JSON.stringify({ incoming, outgoing, ins })
49
- );
45
+ fs.writeFileSync("tokenInOut.json", JSON.stringify({ incoming, outgoing, ins }));
50
46
  };
51
47
 
52
48
  main().catch(e => console.log(e));
@@ -1,15 +1,11 @@
1
1
  import { get, range, chunk, flatten, mergeWith, sortBy, uniq } from "lodash";
2
2
  import fs from "fs";
3
- import MerkleTree, {
4
- checkProof,
5
- checkProofOrdered
6
- } from "merkle-tree-solidity";
3
+ import MerkleTree, { checkProof, checkProofOrdered } from "merkle-tree-solidity";
7
4
  import coreContracts from "@gooddollar/goodcontracts/releases/deployment.json";
8
5
  import stakingContracts from "@gooddollar/goodcontracts/stakingModel/releases/deployment.json";
9
6
  import upgradablesContracts from "@gooddollar/goodcontracts/upgradables/releases/deployment.json";
10
7
  import SimpleDAIStaking from "@gooddollar/goodcontracts/stakingModel/build/contracts/SimpleDAIStaking.min.json";
11
8
  import { ethers as Ethers } from "hardhat";
12
- import fetch from "node-fetch";
13
9
  import { request, gql } from "graphql-request";
14
10
  import { Retrier } from "@jsier/retrier";
15
11
  import PromisePool from "async-promise-pool";
@@ -56,9 +52,7 @@ const otherContracts = [
56
52
 
57
53
  const systemContracts = {};
58
54
  const allContracts = flatten(
59
- [coreContracts, stakingContracts, upgradablesContracts].map(_ =>
60
- Object.values(_).map(_ => Object.values(_))
61
- )
55
+ [coreContracts, stakingContracts, upgradablesContracts].map(_ => Object.values(_).map(_ => Object.values(_)))
62
56
  );
63
57
  flatten(
64
58
  [].concat(
@@ -89,27 +83,17 @@ const quantile = (sorted, q) => {
89
83
  let FUSE_SNAPSHOT_BLOCK = 13175510; //September-29-2021 03:00:00 PM +3 UTC
90
84
  let ETH_SNAPSHOT_BLOCK = 13320531; //first blocka after 12pm Sep-29-2021 12:00:20 PM +UTC
91
85
 
92
- export const airdrop = (
93
- ethers: typeof Ethers,
94
- ethplorer_key,
95
- etherscan_key
96
- ) => {
86
+ export const airdrop = (ethers: typeof Ethers, ethplorer_key, etherscan_key) => {
97
87
  const fusePoktProvider = new ethers.providers.JsonRpcProvider({
98
88
  url: "https://fuse-mainnet.gateway.pokt.network/v1/lb/60ee374fc6318362996a1fb0",
99
89
  user: "",
100
90
  password: "d57939c260bdf0a6f22550e2350b4312" //end point will be removed, so its ok to keep clear text password
101
91
  });
102
92
 
103
- const fuseProvider = new ethers.providers.JsonRpcProvider(
104
- "https://rpc.fuse.io"
105
- );
93
+ const fuseProvider = new ethers.providers.JsonRpcProvider("https://rpc.fuse.io");
106
94
 
107
- const fuseGDProvider = new ethers.providers.JsonRpcProvider(
108
- "https://gooddollar-rpc.fuse.io"
109
- );
110
- const fuseArchiveProvider = new ethers.providers.JsonRpcBatchProvider(
111
- "https://explorer-node.fuse.io/"
112
- );
95
+ const fuseGDProvider = new ethers.providers.JsonRpcProvider("https://gooddollar-rpc.fuse.io");
96
+ const fuseArchiveProvider = new ethers.providers.JsonRpcBatchProvider("https://explorer-node.fuse.io/");
113
97
 
114
98
  const poktArchiveProvider = new ethers.providers.JsonRpcProvider({
115
99
  url: "https://eth-trace.gateway.pokt.network/v1/lb/6130bad2dc57c50036551041",
@@ -182,8 +166,7 @@ export const airdrop = (
182
166
  const nowBlock = ETH_SNAPSHOT_BLOCK; //await staking.provider.getBlockNumber();
183
167
  let toAggregate = events.map(_ => [
184
168
  _.args.staker.toLowerCase(),
185
- parseFloat(ethers.utils.formatEther(_.args.daiValue)) *
186
- (nowBlock - _.blockNumber), //value staked multiplied by time staked (there where no withdraws so far besides foundation account)
169
+ parseFloat(ethers.utils.formatEther(_.args.daiValue)) * (nowBlock - _.blockNumber), //value staked multiplied by time staked (there where no withdraws so far besides foundation account)
187
170
  parseFloat(ethers.utils.formatEther(_.args.daiValue))
188
171
  ]);
189
172
 
@@ -200,16 +183,12 @@ export const airdrop = (
200
183
  .filter(_ => !isSystemContract(_.args.from))
201
184
  .map(e => [
202
185
  e.args.from.toLowerCase(),
203
- parseFloat(ethers.utils.formatEther(e.args.value)) *
204
- (nowBlock - e.blockNumber),
186
+ parseFloat(ethers.utils.formatEther(e.args.value)) * (nowBlock - e.blockNumber),
205
187
  parseFloat(ethers.utils.formatEther(e.args.value))
206
188
  ]);
207
189
 
208
190
  //read eth donations and calculate period * $ value
209
- let provider = new ethers.providers.EtherscanProvider(
210
- "homestead",
211
- etherscan_key
212
- );
191
+ let provider = new ethers.providers.EtherscanProvider("homestead", etherscan_key);
213
192
 
214
193
  //use etherscan to read past eth transfers to the donation contract
215
194
  let historyPromises = (
@@ -222,9 +201,9 @@ export const airdrop = (
222
201
  .filter(_ => _.value.gt(ethers.constants.Zero))
223
202
  .map(async _ => {
224
203
  const data = await fetch(
225
- `https://poloniex.com/public?command=returnChartData&currencyPair=USDT_ETH&start=${
226
- _.timestamp
227
- }&end=${_.timestamp + 30000}&period=300`
204
+ `https://poloniex.com/public?command=returnChartData&currencyPair=USDT_ETH&start=${_.timestamp}&end=${
205
+ _.timestamp + 30000
206
+ }&period=300`
228
207
  ).then(_ => _.json());
229
208
  const price = data[0].weightedAverage || data[0].open;
230
209
  if (price == 0) console.error("error 0 price", { data });
@@ -234,18 +213,13 @@ export const airdrop = (
234
213
  timestamp: _.timestamp,
235
214
  price,
236
215
  usdvalue: price * parseFloat(ethers.utils.formatEther(_.value)),
237
- share:
238
- price *
239
- parseFloat(ethers.utils.formatEther(_.value)) *
240
- (nowBlock - _.blockNumber) //value staked multiplied by time staked
216
+ share: price * parseFloat(ethers.utils.formatEther(_.value)) * (nowBlock - _.blockNumber) //value staked multiplied by time staked
241
217
  };
242
218
  });
243
219
 
244
220
  let ethDonations = await Promise.all(historyPromises);
245
221
 
246
- let donationsToAggregate = daiDonationsToAggregate.concat(
247
- ethDonations.map(_ => [_.from, _.share, _.usdvalue])
248
- );
222
+ let donationsToAggregate = daiDonationsToAggregate.concat(ethDonations.map(_ => [_.from, _.share, _.usdvalue]));
249
223
 
250
224
  const stakerToTotal: { [key: string]: number } = {};
251
225
  toAggregate = toAggregate.concat(donationsToAggregate);
@@ -265,8 +239,7 @@ export const airdrop = (
265
239
  withdrawevents.forEach(
266
240
  _ =>
267
241
  (stakerToTotal[_.args.staker.toLowerCase()] -=
268
- parseFloat(ethers.utils.formatEther(_.args.daiValue)) *
269
- (nowBlock - _.blockNumber))
242
+ parseFloat(ethers.utils.formatEther(_.args.daiValue)) * (nowBlock - _.blockNumber))
270
243
  );
271
244
 
272
245
  //filter contracts + calculate total shares
@@ -323,10 +296,7 @@ export const airdrop = (
323
296
  liquidityPositions(
324
297
  orderDirection: desc
325
298
  orderBy: liquidityTokenBalance
326
- where: {
327
- pair: "0xa56a281cd8ba5c083af121193b2aaccaaac9850a"
328
- liquidityTokenBalance_gt: 0
329
- }
299
+ where: { pair: "0xa56a281cd8ba5c083af121193b2aaccaaac9850a", liquidityTokenBalance_gt: 0 }
330
300
  ) {
331
301
  id
332
302
  user {
@@ -341,10 +311,7 @@ export const airdrop = (
341
311
  }
342
312
  `;
343
313
 
344
- let pair = await ethers.getContractAt(
345
- "UniswapPair",
346
- "0xa56a281cd8ba5c083af121193b2aaccaaac9850a"
347
- );
314
+ let pair = await ethers.getContractAt("UniswapPair", "0xa56a281cd8ba5c083af121193b2aaccaaac9850a");
348
315
  pair = pair.connect(poktArchiveProvider);
349
316
 
350
317
  const pairTotalSupply = await pair
@@ -358,10 +325,7 @@ export const airdrop = (
358
325
  console.log("uniswap pair data:", { reserve0, pairTotalSupply });
359
326
 
360
327
  //TODO: read supplier balance at snapshot
361
- const { liquidityPositions } = await request(
362
- "https://api.thegraph.com/subgraphs/name/uniswap/uniswap-v2",
363
- query
364
- );
328
+ const { liquidityPositions } = await request("https://api.thegraph.com/subgraphs/name/uniswap/uniswap-v2", query);
365
329
 
366
330
  const gdHoldings = liquidityPositions.map(async pos => {
367
331
  const uAddress = pos.user.id.toLowerCase();
@@ -376,8 +340,7 @@ export const airdrop = (
376
340
  `${uAddress}.isNotContract`,
377
341
  (await gdMainnet.provider.getCode(uAddress).catch(e => "0x")) === "0x"
378
342
  );
379
- const newBalance =
380
- (get(addresses, `${uAddress}.balance`, 0) as number) + gdShare;
343
+ const newBalance = (get(addresses, `${uAddress}.balance`, 0) as number) + gdShare;
381
344
  console.log("uniswap position:", {
382
345
  pos,
383
346
  newBalance,
@@ -396,11 +359,7 @@ export const airdrop = (
396
359
  return addresses;
397
360
  };
398
361
 
399
- const getFuseSwapBalances = async (
400
- graphqlUrl,
401
- tokenId,
402
- addresses: Balances = {}
403
- ) => {
362
+ const getFuseSwapBalances = async (graphqlUrl, tokenId, addresses: Balances = {}) => {
404
363
  const _calcHoldings = async (pair, addresses: Balances = {}) => {
405
364
  const { liquidityPositions, reserve0: isReserve0, id } = pair;
406
365
  let pairContract = await ethers.getContractAt("UniswapPair", id);
@@ -443,8 +402,7 @@ export const airdrop = (
443
402
  reserve: reserve
444
403
  });
445
404
 
446
- const newBalance =
447
- (get(addresses, `${uAddress}.balance`, 0) as number) + gdShare;
405
+ const newBalance = (get(addresses, `${uAddress}.balance`, 0) as number) + gdShare;
448
406
 
449
407
  addresses[uAddress] = updateBalance(addresses[uAddress], {
450
408
  balance: newBalance
@@ -516,8 +474,7 @@ export const airdrop = (
516
474
  );
517
475
 
518
476
  const farmers = {};
519
- const yieldFarmingRep =
520
- addresses[usdcgdYieldFarming.address.toLowerCase()]?.balance || 0;
477
+ const yieldFarmingRep = addresses[usdcgdYieldFarming.address.toLowerCase()]?.balance || 0;
521
478
  if (yieldFarmingRep > 0) {
522
479
  const [totalStaked, ,] = await usdcgdYieldFarming.interestData({
523
480
  blockTag: FUSE_SNAPSHOT_BLOCK
@@ -525,19 +482,14 @@ export const airdrop = (
525
482
 
526
483
  await Promise.all(
527
484
  staked.map(async e => {
528
- const [balance] = await usdcgdYieldFarming.getStakerData(
529
- e.args.staker,
530
- { blockTag: FUSE_SNAPSHOT_BLOCK }
531
- );
485
+ const [balance] = await usdcgdYieldFarming.getStakerData(e.args.staker, { blockTag: FUSE_SNAPSHOT_BLOCK });
532
486
 
533
487
  if (balance > 0) {
534
488
  const share = balance.toNumber() / totalStaked.toNumber();
535
489
  const uAddress = e.args.staker;
536
490
  const repShare = parseInt((share * yieldFarmingRep).toFixed(0));
537
491
  farmers[uAddress] = [share, repShare];
538
- const newBalance =
539
- (get(addresses, `${uAddress}.balance`, 0) as number) +
540
- share * yieldFarmingRep;
492
+ const newBalance = (get(addresses, `${uAddress}.balance`, 0) as number) + share * yieldFarmingRep;
541
493
 
542
494
  addresses[uAddress] = updateBalance(addresses[uAddress], {
543
495
  balance: newBalance
@@ -563,16 +515,8 @@ export const airdrop = (
563
515
  return addresses;
564
516
  };
565
517
 
566
- const getFuseHolders = async (
567
- addresses: Balances = {},
568
- onlyBalances = false,
569
- onlyFailed = false
570
- ) => {
571
- console.log(
572
- "getFuseHolders",
573
- { onlyBalances, onlyFailed },
574
- Object.keys(addresses).length
575
- );
518
+ const getFuseHolders = async (addresses: Balances = {}, onlyBalances = false, onlyFailed = false) => {
519
+ console.log("getFuseHolders", { onlyBalances, onlyFailed }, Object.keys(addresses).length);
576
520
  const toFetch = {};
577
521
 
578
522
  const step = 1000;
@@ -596,11 +540,7 @@ export const airdrop = (
596
540
  const logs = await retrier.resolve(attempt => {
597
541
  console.log("fetching block transfer logs", { attempt, bc });
598
542
 
599
- return contracts[idx++ % contracts.length].queryFilter(
600
- filter,
601
- bc,
602
- Math.min(bc + step - 1, latestBlock)
603
- );
543
+ return contracts[idx++ % contracts.length].queryFilter(filter, bc, Math.min(bc + step - 1, latestBlock));
604
544
  });
605
545
 
606
546
  logs.forEach(l => (toFetch[l.args.to.toLowerCase()] = true));
@@ -652,14 +592,11 @@ export const airdrop = (
652
592
  for (let addrChunk of chunk(addrs, 50)) {
653
593
  balancesPool.add(async () => {
654
594
  const ps = addrChunk.map(async (uAddress: string) => {
655
- const curBalance = onlyFailed
656
- ? 0
657
- : get(addresses, `${uAddress}.balance`, 0);
595
+ const curBalance = onlyFailed ? 0 : get(addresses, `${uAddress}.balance`, 0);
658
596
  const isNotContract = get(
659
597
  addresses,
660
598
  `${uAddress}.isNotContract`,
661
- (await gdNonArchive.provider.getCode(uAddress).catch(e => "0x")) ===
662
- "0x"
599
+ (await gdNonArchive.provider.getCode(uAddress).catch(e => "0x")) === "0x"
663
600
  );
664
601
  const balance = await gd
665
602
  .balanceOf(uAddress)
@@ -682,8 +619,7 @@ export const airdrop = (
682
619
 
683
620
  await balancesPool.all();
684
621
  console.log("fuseHolders failed:", failed.length);
685
- if (!onlyFailed)
686
- fs.writeFileSync("airdrop/failed.tmp", JSON.stringify(failed));
622
+ if (!onlyFailed) fs.writeFileSync("airdrop/failed.tmp", JSON.stringify(failed));
687
623
  return addresses;
688
624
  };
689
625
 
@@ -706,8 +642,7 @@ export const airdrop = (
706
642
  const isNotContract = get(
707
643
  addresses,
708
644
  `${uAddress}.isNotContract`,
709
- (await gdNonArchive.provider.getCode(b[0]).catch(e => "0x")) ===
710
- "0x"
645
+ (await gdNonArchive.provider.getCode(b[0]).catch(e => "0x")) === "0x"
711
646
  );
712
647
  const cleanBalance = await gdNonArchive
713
648
  .balanceOf(uAddress, { blockTag: FUSE_SNAPSHOT_BLOCK })
@@ -738,9 +673,7 @@ export const airdrop = (
738
673
  }
739
674
 
740
675
  if (items && items.length) {
741
- const foundBalances = items.map(i =>
742
- i.match(/(0x\w{20,})|([0-9\.,]+ G\$)/g)
743
- );
676
+ const foundBalances = items.map(i => i.match(/(0x\w{20,})|([0-9\.,]+ G\$)/g));
744
677
  analyzedPages++;
745
678
  analyzedBalances += foundBalances.length;
746
679
  toFetch = toFetch.concat(foundBalances);
@@ -795,13 +728,11 @@ export const airdrop = (
795
728
  .then(_ => _.toNumber())
796
729
  .catch(e => failedAccounts.push(uAddress));
797
730
 
798
- const newBalance =
799
- get(addresses, `${uAddress}.balance`, 0) + cleanBalance;
731
+ const newBalance = get(addresses, `${uAddress}.balance`, 0) + cleanBalance;
800
732
  const isNotContract = get(
801
733
  addresses,
802
734
  `${uAddress}.isNotContract`,
803
- (await gdMainnet.provider.getCode(uAddress).catch(e => "0x")) ===
804
- "0x"
735
+ (await gdMainnet.provider.getCode(uAddress).catch(e => "0x")) === "0x"
805
736
  );
806
737
  addresses[uAddress] = updateBalance(addresses[uAddress], {
807
738
  balance: newBalance,
@@ -820,10 +751,7 @@ export const airdrop = (
820
751
  return addresses;
821
752
  };
822
753
 
823
- const getClaimsPerAddress = async (
824
- balances: Balances = {},
825
- ubiContract = ubi
826
- ) => {
754
+ const getClaimsPerAddress = async (balances: Balances = {}, ubiContract = ubi) => {
827
755
  const ubiFuse = ubiContract.connect(fuseProvider);
828
756
  const ubiPokt = ubiContract.connect(fusePoktProvider);
829
757
  const ubiGD = ubiContract.connect(fuseGDProvider);
@@ -831,11 +759,7 @@ export const airdrop = (
831
759
  const pool = new PromisePool({ concurrency: 50 });
832
760
  const step = 1000;
833
761
  const latestBlock = FUSE_SNAPSHOT_BLOCK; //await ubiContract.provider.getBlockNumber();
834
- const blocks = range(
835
- ubiContract === ubi ? 6276288 : 9376522,
836
- ubiContract === ubi ? 9497482 : latestBlock,
837
- step
838
- );
762
+ const blocks = range(ubiContract === ubi ? 6276288 : 9376522, ubiContract === ubi ? 9497482 : latestBlock, step);
839
763
  const filter = ubiContract.filters.UBIClaimed();
840
764
  const contracts = [ubiFuse, ubiGD];
841
765
  let idx = 0;
@@ -847,11 +771,7 @@ export const airdrop = (
847
771
  const logs = await retrier.resolve(attempt => {
848
772
  console.log("fetching block ubiclaimed logs", { attempt, bc });
849
773
 
850
- return contracts[idx++ % contracts.length].queryFilter(
851
- filter,
852
- bc,
853
- Math.min(bc + step - 1, latestBlock)
854
- );
774
+ return contracts[idx++ % contracts.length].queryFilter(filter, bc, Math.min(bc + step - 1, latestBlock));
855
775
  });
856
776
 
857
777
  console.log("found claim logs in block:", { bc }, logs.length);
@@ -870,20 +790,12 @@ export const airdrop = (
870
790
  };
871
791
 
872
792
  const calcRelativeRep = (balances: Balances) => {
873
- const totalSupply = Object.values(balances).reduce(
874
- (cur, data) => cur + data.balance,
875
- 0
876
- );
877
- const totalClaims = Object.values(balances).reduce(
878
- (cur, data) => cur + (data.claims || 0),
879
- 0
880
- );
793
+ const totalSupply = Object.values(balances).reduce((cur, data) => cur + data.balance, 0);
794
+ const totalClaims = Object.values(balances).reduce((cur, data) => cur + (data.claims || 0), 0);
881
795
 
882
796
  for (let addr in balances) {
883
- balances[addr].gdRepShare =
884
- totalSupply > 0 ? balances[addr].balance / totalSupply : 0;
885
- balances[addr].claimRepShare =
886
- totalClaims > 0 ? balances[addr].claims / totalClaims : 0;
797
+ balances[addr].gdRepShare = totalSupply > 0 ? balances[addr].balance / totalSupply : 0;
798
+ balances[addr].claimRepShare = totalClaims > 0 ? balances[addr].claims / totalClaims : 0;
887
799
  }
888
800
  return { totalSupply, totalClaims, balances };
889
801
  };
@@ -903,35 +815,26 @@ export const airdrop = (
903
815
 
904
816
  ps[0] = _timer(
905
817
  "getFuseSwapBalances",
906
- getFuseSwapBalances(
907
- "https://graph.fuse.io/subgraphs/name/fuseio/fuseswap",
908
- GD_FUSE
909
- ).then(r =>
818
+ getFuseSwapBalances("https://graph.fuse.io/subgraphs/name/fuseio/fuseswap", GD_FUSE).then(r =>
910
819
  fs.writeFileSync("airdrop/fuseswapBalances.json", JSON.stringify(r))
911
820
  )
912
821
  );
913
822
 
914
823
  ps[1] = _timer(
915
824
  "getUniswapBalances",
916
- getUniswapBalances().then(r =>
917
- fs.writeFileSync("airdrop/uniswapBalances.json", JSON.stringify(r))
918
- )
825
+ getUniswapBalances().then(r => fs.writeFileSync("airdrop/uniswapBalances.json", JSON.stringify(r)))
919
826
  );
920
827
 
921
828
  ps[2] = _timer(
922
829
  "getClaimsPerAddress",
923
830
  getClaimsPerAddress()
924
831
  .then(r => getClaimsPerAddress(r, ubinew))
925
- .then(r =>
926
- fs.writeFileSync("airdrop/claimBalances.json", JSON.stringify(r))
927
- )
832
+ .then(r => fs.writeFileSync("airdrop/claimBalances.json", JSON.stringify(r)))
928
833
  );
929
834
 
930
835
  ps[3] = _timer(
931
836
  "getEthPlorerHolders",
932
- getEthPlorerHolders().then(r =>
933
- fs.writeFileSync("airdrop/ethBalances.json", JSON.stringify(r))
934
- )
837
+ getEthPlorerHolders().then(r => fs.writeFileSync("airdrop/ethBalances.json", JSON.stringify(r)))
935
838
  );
936
839
 
937
840
  // ps[4] = _timer(
@@ -945,16 +848,12 @@ export const airdrop = (
945
848
  // );
946
849
  ps[4] = _timer(
947
850
  "getFuseHolders",
948
- getFuseHolders({}).then(r =>
949
- fs.writeFileSync("airdrop/fuseBalances.json", JSON.stringify(r))
950
- )
851
+ getFuseHolders({}).then(r => fs.writeFileSync("airdrop/fuseBalances.json", JSON.stringify(r)))
951
852
  );
952
853
 
953
854
  ps[5] = _timer(
954
855
  "getStakersBalance",
955
- getStakersBalance().then(r =>
956
- fs.writeFileSync("airdrop/stakersBalances.json", JSON.stringify(r))
957
- )
856
+ getStakersBalance().then(r => fs.writeFileSync("airdrop/stakersBalances.json", JSON.stringify(r)))
958
857
  );
959
858
 
960
859
  await Promise.all(ps);
@@ -980,13 +879,8 @@ export const airdrop = (
980
879
  obj1.claims = get(obj1, "claims", 0) + get(obj2, "claims", 0);
981
880
  obj1.balance = get(obj1, "balance", 0) + get(obj2, "balance", 0);
982
881
  obj1.stake = get(obj1, "stake", 0) + get(obj2, "stake", 0);
983
- obj1.stakeRepShare =
984
- get(obj1, "stakeRepShare") || get(obj2, "stakeRepShare", 0);
985
- obj1.isNotContract = get(
986
- obj1,
987
- "isNotContract",
988
- get(obj2, "isNotContract")
989
- );
882
+ obj1.stakeRepShare = get(obj1, "stakeRepShare") || get(obj2, "stakeRepShare", 0);
883
+ obj1.isNotContract = get(obj1, "isNotContract", get(obj2, "isNotContract"));
990
884
  return obj1;
991
885
  };
992
886
 
@@ -1003,14 +897,9 @@ export const airdrop = (
1003
897
  const HOLDER_REP_ALLOCATION = 24000000;
1004
898
  const STAKER_REP_ALLOCATION = 24000000;
1005
899
 
1006
- const ETORO = [
1007
- "0xf79b804bae955ae4cd8e8b0331c4bc437104804f",
1008
- "0x61ec01ad0937ebc10d448d259a2bbb1556b61e38"
1009
- ];
1010
- const EtoroOfficial =
1011
- "0x61ec01ad0937ebc10d448d259a2bbb1556b61e38".toLowerCase();
1012
- const FoundationOfficial =
1013
- "0x66582D24FEaD72555adaC681Cc621caCbB208324".toLowerCase();
900
+ const ETORO = ["0xf79b804bae955ae4cd8e8b0331c4bc437104804f", "0x61ec01ad0937ebc10d448d259a2bbb1556b61e38"];
901
+ const EtoroOfficial = "0x61ec01ad0937ebc10d448d259a2bbb1556b61e38".toLowerCase();
902
+ const FoundationOfficial = "0x66582D24FEaD72555adaC681Cc621caCbB208324".toLowerCase();
1014
903
 
1015
904
  const TEAM = [
1016
905
  "0x5AeE2397b39B479B72bcfbDA114512BD3329E5aC",
@@ -1045,24 +934,24 @@ export const airdrop = (
1045
934
 
1046
935
  ETORO.forEach(addr => delete balances[addr]);
1047
936
 
1048
- let toTree: Array<
1049
- [string, number, boolean, number, number, number, number]
1050
- > = Object.entries(balances).map(([addr, data]) => {
1051
- let rep =
1052
- data.claimRepShare * CLAIMER_REP_ALLOCATION +
1053
- data.gdRepShare * HOLDER_REP_ALLOCATION +
1054
- data.stakeRepShare * STAKER_REP_ALLOCATION;
1055
-
1056
- return [
1057
- addr,
1058
- rep,
1059
- !data.isNotContract,
1060
- data.claimRepShare * CLAIMER_REP_ALLOCATION,
1061
- data.gdRepShare * HOLDER_REP_ALLOCATION,
1062
- data.stakeRepShare * STAKER_REP_ALLOCATION,
1063
- 0
1064
- ];
1065
- });
937
+ let toTree: Array<[string, number, boolean, number, number, number, number]> = Object.entries(balances).map(
938
+ ([addr, data]) => {
939
+ let rep =
940
+ data.claimRepShare * CLAIMER_REP_ALLOCATION +
941
+ data.gdRepShare * HOLDER_REP_ALLOCATION +
942
+ data.stakeRepShare * STAKER_REP_ALLOCATION;
943
+
944
+ return [
945
+ addr,
946
+ rep,
947
+ !data.isNotContract,
948
+ data.claimRepShare * CLAIMER_REP_ALLOCATION,
949
+ data.gdRepShare * HOLDER_REP_ALLOCATION,
950
+ data.stakeRepShare * STAKER_REP_ALLOCATION,
951
+ 0
952
+ ];
953
+ }
954
+ );
1066
955
 
1067
956
  //split etoro's rep between team,etoro and foundation
1068
957
  const foundationEtoroRepShare = 8640000;
@@ -1072,15 +961,7 @@ export const airdrop = (
1072
961
  foundationRecord[6] = foundationEtoroRepShare;
1073
962
  console.log("Foundation updated record:", foundationRecord);
1074
963
 
1075
- const etoroRecord: [
1076
- string,
1077
- number,
1078
- boolean,
1079
- number,
1080
- number,
1081
- number,
1082
- number
1083
- ] = [
964
+ const etoroRecord: [string, number, boolean, number, number, number, number] = [
1084
965
  EtoroOfficial,
1085
966
  foundationEtoroRepShare,
1086
967
  false,
@@ -1128,11 +1009,7 @@ export const airdrop = (
1128
1009
  console.log({
1129
1010
  precentile: q * 100 + "%",
1130
1011
  addresses: (sorted.length * q).toFixed(0),
1131
- rep:
1132
- quantile(sorted, q) /
1133
- (CLAIMER_REP_ALLOCATION +
1134
- HOLDER_REP_ALLOCATION +
1135
- STAKER_REP_ALLOCATION)
1012
+ rep: quantile(sorted, q) / (CLAIMER_REP_ALLOCATION + HOLDER_REP_ALLOCATION + STAKER_REP_ALLOCATION)
1136
1013
  })
1137
1014
  );
1138
1015
 
@@ -1145,10 +1022,7 @@ export const airdrop = (
1145
1022
  })
1146
1023
  .split(".")[0];
1147
1024
  const hash = ethers.utils.keccak256(
1148
- ethers.utils.defaultAbiCoder.encode(
1149
- ["address", "uint256"],
1150
- [e[0], repInWei]
1151
- )
1025
+ ethers.utils.defaultAbiCoder.encode(["address", "uint256"], [e[0], repInWei])
1152
1026
  );
1153
1027
  treeData[e[0]] = {
1154
1028
  rep: repInWei,
@@ -1176,9 +1050,7 @@ export const airdrop = (
1176
1050
  1
1177
1051
  );
1178
1052
 
1179
- const lastProof = merkleTree
1180
- .getProof(elements[elements.length - 1])
1181
- .map(_ => _.toString("hex"));
1053
+ const lastProof = merkleTree.getProof(elements[elements.length - 1]).map(_ => _.toString("hex"));
1182
1054
  const lastValidProof = checkProofOrdered(
1183
1055
  lastProof.map(_ => Buffer.from(_, "hex")),
1184
1056
  merkleTree.getRoot(),
@@ -1230,10 +1102,7 @@ export const airdrop = (
1230
1102
  const proof = merkleTree.getProof(proofFor);
1231
1103
  const proofIndex = entries.findIndex(_ => _[1].hash === addrData.hash) + 1;
1232
1104
 
1233
- console.log(
1234
- "checkProof:",
1235
- checkProofOrdered(proof, merkleTree.getRoot(), proofFor, proofIndex)
1236
- );
1105
+ console.log("checkProof:", checkProofOrdered(proof, merkleTree.getRoot(), proofFor, proofIndex));
1237
1106
  const hexProof = proof.map(_ => "0x" + _.toString("hex"));
1238
1107
  console.log({ proofIndex, proof: hexProof, [addr]: addrData });
1239
1108
  };
@@ -9,7 +9,6 @@ import { MerkleTree } from "merkletreejs";
9
9
  import PromisePool from "async-promise-pool";
10
10
  import { ethers as Ethers } from "hardhat";
11
11
  import { BigNumber } from "ethers";
12
- import fetch from "node-fetch";
13
12
 
14
13
  const quantile = (sorted, q) => {
15
14
  const pos = (sorted.length - 1) * q;
@@ -22,18 +21,11 @@ const quantile = (sorted, q) => {
22
21
  };
23
22
 
24
23
  export const airdrop = (ethers: typeof Ethers) => {
25
- const fuseProvider = new ethers.providers.JsonRpcProvider(
26
- "https://rpc.fuse.io"
27
- );
28
-
29
- const zxfastProvider = new ethers.providers.JsonRpcProvider(
30
- "https://eth-eu.0xfast.com/rpc/free"
31
- );
32
-
33
- const cfProvider = new ethers.providers.InfuraProvider(
34
- 1,
35
- "143f9cf968fe4c3da0db77ff525e0da4"
36
- );
24
+ const fuseProvider = new ethers.providers.JsonRpcProvider("https://rpc.fuse.io");
25
+
26
+ const zxfastProvider = new ethers.providers.JsonRpcProvider("https://eth-eu.0xfast.com/rpc/free");
27
+
28
+ const cfProvider = new ethers.providers.InfuraProvider(1, "143f9cf968fe4c3da0db77ff525e0da4");
37
29
  const goodActiveVotes = async (network = "fuse") => {
38
30
  let balances = [];
39
31
 
@@ -45,9 +37,7 @@ export const airdrop = (ethers: typeof Ethers) => {
45
37
 
46
38
  const graphQuery = async (start, skip, step = EPOCH) => {
47
39
  const query = `{
48
- goodBalances(first: 1000 skip:${skip} where: { memberSince_gte: ${start} memberSince_lt:${
49
- start + step
50
- } }) {
40
+ goodBalances(first: 1000 skip:${skip} where: { memberSince_gte: ${start} memberSince_lt:${start + step} }) {
51
41
  id
52
42
  coreBalance
53
43
  totalVotes
@@ -64,16 +54,11 @@ export const airdrop = (ethers: typeof Ethers) => {
64
54
  body: JSON.stringify({ query })
65
55
  }).then(_ => _.json());
66
56
  errors && console.log({ errors });
67
- if (
68
- errors?.[0]?.message ===
69
- "The `skip` argument must be between 0 and 5000, but is 6000"
70
- ) {
57
+ if (errors?.[0]?.message === "The `skip` argument must be between 0 and 5000, but is 6000") {
71
58
  throw new Error("skip");
72
59
  }
73
60
  if (data?.goodBalances?.length === 1000) {
74
- return data.goodBalances.concat(
75
- await graphQuery(start, skip + 1000, step)
76
- );
61
+ return data.goodBalances.concat(await graphQuery(start, skip + 1000, step));
77
62
  }
78
63
  return data.goodBalances || [];
79
64
  } catch (error) {
@@ -111,11 +96,7 @@ export const airdrop = (ethers: typeof Ethers) => {
111
96
  await pool.all();
112
97
  console.log(`total ${network} GOOD Holders:`, balances.length, {
113
98
  uniques: uniq(balances.map(_ => _.id)).length,
114
- delegatees: uniq(
115
- balances
116
- .filter(_ => Number(_.coreBalance) < Number(_.totalVotes))
117
- .map(_ => _.id)
118
- ).length,
99
+ delegatees: uniq(balances.filter(_ => Number(_.coreBalance) < Number(_.totalVotes)).map(_ => _.id)).length,
119
100
  sample: balances.slice(0, 5)
120
101
  });
121
102
 
@@ -128,10 +109,7 @@ export const airdrop = (ethers: typeof Ethers) => {
128
109
  rep: record.activeVotes,
129
110
  hash: ethers.utils.keccak256(
130
111
  ethers.utils.keccak256(
131
- ethers.utils.defaultAbiCoder.encode(
132
- ["address", "uint256"],
133
- [record.id, record.activeVotes]
134
- )
112
+ ethers.utils.defaultAbiCoder.encode(["address", "uint256"], [record.id, record.activeVotes])
135
113
  )
136
114
  )
137
115
  };
@@ -140,9 +118,7 @@ export const airdrop = (ethers: typeof Ethers) => {
140
118
  `goodCheckpoints/goodCheckpoint_${network}.json`,
141
119
  JSON.stringify({ treeData, balances, until: Date.now() })
142
120
  );
143
- console.log(
144
- balances.filter(_ => Number(_.coreBalance) < Number(_.totalVotes))
145
- );
121
+ console.log(balances.filter(_ => Number(_.coreBalance) < Number(_.totalVotes)));
146
122
  };
147
123
 
148
124
  const collectAirdropData = async () => {
@@ -157,33 +133,15 @@ export const airdrop = (ethers: typeof Ethers) => {
157
133
  for (let blockChunk of chunk(blocks, 10)) {
158
134
  // Get the filter (the second null could be omitted)
159
135
  const ps = blockChunk.map(async (bc: number) => {
160
- const logs = await good
161
- .queryFilter(
162
- good.filters.Mint(),
163
- bc,
164
- Math.min(bc + step - 1, LAST_BLOCK)
165
- )
166
- .catch(e => {
167
- console.log("block transfer logs failed retrying...", bc);
168
- return good.queryFilter(
169
- good.filters.Mint(),
170
- bc,
171
- Math.min(bc + step - 1, LAST_BLOCK)
172
- );
173
- });
136
+ const logs = await good.queryFilter(good.filters.Mint(), bc, Math.min(bc + step - 1, LAST_BLOCK)).catch(e => {
137
+ console.log("block transfer logs failed retrying...", bc);
138
+ return good.queryFilter(good.filters.Mint(), bc, Math.min(bc + step - 1, LAST_BLOCK));
139
+ });
174
140
  const claimedLogs = await good
175
- .queryFilter(
176
- good.filters.StateHashProof(),
177
- bc,
178
- Math.min(bc + step - 1, LAST_BLOCK)
179
- )
141
+ .queryFilter(good.filters.StateHashProof(), bc, Math.min(bc + step - 1, LAST_BLOCK))
180
142
  .catch(e => {
181
143
  console.log("block transfer logs failed retrying...", bc);
182
- return good.queryFilter(
183
- good.filters.StateHashProof(),
184
- bc,
185
- Math.min(bc + step - 1, LAST_BLOCK)
186
- );
144
+ return good.queryFilter(good.filters.StateHashProof(), bc, Math.min(bc + step - 1, LAST_BLOCK));
187
145
  });
188
146
  console.log("found logs:", claimedLogs.length, logs.length, bc);
189
147
  return logs.concat(claimedLogs);
@@ -201,20 +159,14 @@ export const airdrop = (ethers: typeof Ethers) => {
201
159
  let totalMints = ethers.constants.Zero;
202
160
  logs.forEach(l => {
203
161
  if (l.event === "Mint") {
204
- mints[l.args._to.toLowerCase()] = (
205
- mints[l.args._to.toLowerCase()] || BigNumber.from("0")
206
- ).add(l.args._amount);
162
+ mints[l.args._to.toLowerCase()] = (mints[l.args._to.toLowerCase()] || BigNumber.from("0")).add(
163
+ l.args._amount
164
+ );
207
165
  totalMints = totalMints.add(l.args._amount);
208
166
  } else claims[l.args.user.toLowerCase()] = l.args.repBalance.toString();
209
167
  });
210
- Object.entries(mints).forEach(
211
- ([k, v]) =>
212
- (result[k] = { claim: "0", ...result[k], mint: v.toString() })
213
- );
214
- Object.entries(claims).forEach(
215
- ([k, v]) =>
216
- (result[k] = { mint: "0", ...result[k], claim: v.toString() })
217
- );
168
+ Object.entries(mints).forEach(([k, v]) => (result[k] = { claim: "0", ...result[k], mint: v.toString() }));
169
+ Object.entries(claims).forEach(([k, v]) => (result[k] = { mint: "0", ...result[k], claim: v.toString() }));
218
170
  console.log({ result, totalMints: totalMints.toString() });
219
171
  fs.writeFileSync("goodCheckpointMainnet.json", JSON.stringify(result));
220
172
  };
@@ -227,33 +179,21 @@ export const airdrop = (ethers: typeof Ethers) => {
227
179
  const buildMerkleTree = async () => {
228
180
  const buildTree = async (network = "fuse") => {
229
181
  const good = await ethers
230
- .getContractAt(
231
- "GReputation",
232
- "0x603B8C0F110E037b51A381CBCacAbb8d6c6E4543"
233
- )
182
+ .getContractAt("GReputation", "0x603B8C0F110E037b51A381CBCacAbb8d6c6E4543")
234
183
  .then(_ => _.connect(network === "fuse" ? fuseProvider : cfProvider));
235
184
 
236
- const checkpoint = JSON.parse(
237
- fs
238
- .readFileSync(`goodCheckpoints/goodCheckpoint_${network}.json`)
239
- .toString()
240
- );
185
+ const checkpoint = JSON.parse(fs.readFileSync(`goodCheckpoints/goodCheckpoint_${network}.json`).toString());
241
186
 
242
187
  const treeData = checkpoint.treeData;
243
188
 
244
- let toTree: Array<[string, BigNumber]> = Object.entries(treeData).map(
245
- ([k, v]) => {
246
- return [k, BigNumber.from((v as any).rep)];
247
- }
248
- );
189
+ let toTree: Array<[string, BigNumber]> = Object.entries(treeData).map(([k, v]) => {
190
+ return [k, BigNumber.from((v as any).rep)];
191
+ });
249
192
 
250
193
  toTree = toTree.sort((a, b) => (a[1].gte(b[1]) ? 1 : -1)).reverse();
251
194
  // console.log({ toTree });
252
195
  // const topContracts = toTree.filter(_ => _[2] === true);
253
- const totalReputation = toTree.reduce(
254
- (c, a) => c.add(a[1]),
255
- BigNumber.from(0)
256
- );
196
+ const totalReputation = toTree.reduce((c, a) => c.add(a[1]), BigNumber.from(0));
257
197
  const totalSupply = (await good.totalSupply()).toString();
258
198
  console.log({
259
199
  totalSupply,
@@ -271,9 +211,7 @@ export const airdrop = (ethers: typeof Ethers) => {
271
211
  precentile: q * 100 + "%",
272
212
  addresses: (sorted.length * q).toFixed(0),
273
213
  quantileRep,
274
- rep:
275
- Number(quantileRep.div(1e10).toString()) /
276
- Number(totalReputation.div(1e10).toString())
214
+ rep: Number(quantileRep.div(1e10).toString()) / Number(totalReputation.div(1e10).toString())
277
215
  });
278
216
  });
279
217
  const items = Object.values(treeData);
@@ -296,16 +234,10 @@ export const airdrop = (ethers: typeof Ethers) => {
296
234
  const validProof = merkleTree.verify(proof, elements[0], merkleRoot);
297
235
 
298
236
  const lastProof = merkleTree.getHexProof(elements[elements.length - 1]);
299
- const lastValidProof = merkleTree.verify(
300
- lastProof,
301
- elements[elements.length - 1],
302
- merkleRoot
303
- );
237
+ const lastValidProof = merkleTree.verify(lastProof, elements[elements.length - 1], merkleRoot);
304
238
 
305
239
  //check for possible address preimage
306
- const danger = (merkleTree.getHexLayers() as any).map(_ =>
307
- _.find(_ => _.startsWith("0x000000"))
308
- );
240
+ const danger = (merkleTree.getHexLayers() as any).map(_ => _.find(_ => _.startsWith("0x000000")));
309
241
 
310
242
  console.log({
311
243
  danger,
@@ -322,10 +254,7 @@ export const airdrop = (ethers: typeof Ethers) => {
322
254
 
323
255
  checkpoint.merkleRoot = merkleRoot;
324
256
  checkpoint.totalSupply = totalSupply;
325
- fs.writeFileSync(
326
- "goodCheckpoints/goodCheckpoint_fuse.json",
327
- JSON.stringify(checkpoint)
328
- );
257
+ fs.writeFileSync("goodCheckpoints/goodCheckpoint_fuse.json", JSON.stringify(checkpoint));
329
258
  };
330
259
 
331
260
  await buildTree();
@@ -333,9 +262,7 @@ export const airdrop = (ethers: typeof Ethers) => {
333
262
  };
334
263
 
335
264
  const getProof = addr => {
336
- const { treeData, merkleRoot } = JSON.parse(
337
- fs.readFileSync("airdrop/airdrop.json").toString()
338
- );
265
+ const { treeData, merkleRoot } = JSON.parse(fs.readFileSync("airdrop/airdrop.json").toString());
339
266
 
340
267
  let entries = Object.entries(treeData as Tree);
341
268
  let elements = entries.map(e => Buffer.from(e[1].hash.slice(2), "hex"));
@@ -355,14 +282,10 @@ export const airdrop = (ethers: typeof Ethers) => {
355
282
  const proofFor = Buffer.from(addrData.hash.slice(2), "hex");
356
283
 
357
284
  const proof = merkleTree.getHexProof(proofFor);
358
- const proofIndex =
359
- elements.findIndex(_ => "0x" + _.toString("hex") === addrData.hash) + 1;
285
+ const proofIndex = elements.findIndex(_ => "0x" + _.toString("hex") === addrData.hash) + 1;
360
286
 
361
287
  console.log({ proofIndex, proof, [addr]: addrData });
362
- console.log(
363
- "checkProof:",
364
- merkleTree.verify(proof, proofFor, calcMerkleRoot)
365
- );
288
+ console.log("checkProof:", merkleTree.verify(proof, proofFor, calcMerkleRoot));
366
289
  };
367
290
 
368
291
  return { buildMerkleTree, collectAirdropData, getProof };
@@ -1,18 +1,15 @@
1
1
  import { range, chunk } from "lodash";
2
2
  import { ethers as Ethers } from "hardhat";
3
- import fetch from "node-fetch";
4
3
 
5
4
  const ONE_DAY = 24 * 60 * 60;
6
5
 
7
6
  const main = async () => {
8
7
  const signer = (await Ethers.getSigners())[0];
9
8
  console.log("signer:", signer.address);
10
- const ubiScheme = new Ethers.Contract(
11
- "0xD7aC544F8A570C4d8764c3AAbCF6870CBD960D0D",
12
- ["function fishMulti(address[] tofish)"]
13
- ).connect(signer);
14
- const twoWeeksAgo =
15
- parseInt((Date.now() / 1000).toFixed(0)) - 24 * 60 * 60 * 14;
9
+ const ubiScheme = new Ethers.Contract("0xD7aC544F8A570C4d8764c3AAbCF6870CBD960D0D", [
10
+ "function fishMulti(address[] tofish)"
11
+ ]).connect(signer);
12
+ const twoWeeksAgo = parseInt((Date.now() / 1000).toFixed(0)) - 24 * 60 * 60 * 14;
16
13
 
17
14
  const daysAgo: number[] = range(0, 180, 1);
18
15
  let curDay = twoWeeksAgo;
@@ -27,19 +24,12 @@ const main = async () => {
27
24
  }
28
25
  `;
29
26
 
30
- console.log(
31
- "fetching inactive users since:",
32
- { curDay, day },
33
- JSON.stringify({ query })
34
- );
35
- const { walletStats } = await fetch(
36
- "https://api.thegraph.com/subgraphs/name/gooddollar/gooddollarfuse",
37
- {
38
- method: "post",
39
- body: JSON.stringify({ query }),
40
- headers: { "Content-Type": "application/json" }
41
- }
42
- ).then(_ => _.json());
27
+ console.log("fetching inactive users since:", { curDay, day }, JSON.stringify({ query }));
28
+ const { walletStats } = await fetch("https://api.thegraph.com/subgraphs/name/gooddollar/gooddollarfuse", {
29
+ method: "post",
30
+ body: JSON.stringify({ query }),
31
+ headers: { "Content-Type": "application/json" }
32
+ }).then(_ => _.json());
43
33
 
44
34
  console.log("got inactive wallets:", walletStats.length);
45
35
  const accounts = walletStats.map(_ => _.id);
@@ -1,5 +1,4 @@
1
1
  import { request, gql } from "graphql-request";
2
- import fetch from "node-fetch";
3
2
 
4
3
  let txCount = {};
5
4
  const fetchSwaps = async (to, url, pair) => {