allo-monad-ray
Version:
Monad version of Allo v2 SDK
312 lines (311 loc) • 10.1 kB
JavaScript
import { encodeAbiParameters, encodeFunctionData, extractChain, getContract, parseAbiParameters, } from "viem";
import { Allo } from "../../Allo/Allo";
import { abi as alloAbi } from "../../Allo/allo.config";
import { create } from "../../Client/Client";
import { ZERO_ADDRESS, } from "../../Common/types";
import { supportedChains } from "../../chains.config";
import { NATIVE } from "../../types";
import { abi, bytecode as bytecode } from "./directGrantsLite.config";
export class DirectGrantsLiteStrategy {
constructor({ chain, rpc, address, poolId }) {
const usedChain = extractChain({
chains: supportedChains,
id: chain,
});
this.client = create(usedChain, rpc);
this.allo = new Allo({ chain, rpc }); // to call allocate
if (address) {
this.contract = getContract({
address: address,
abi,
client: {
public: this.client,
}
});
this.strategy = address;
}
this.poolId = poolId || BigInt(-1);
}
async getAllo() {
return this.allo;
}
async setPoolId(poolId) {
this.poolId = poolId;
const strategyAddress = await this.allo.getStrategy(poolId);
this.setContract(strategyAddress);
}
setContract(address) {
this.contract = getContract({
address: address,
abi,
client: {
public: this.client,
}
});
this.strategy = address;
}
// Validation functions
checkPoolId() {
if (this.poolId === BigInt(-1))
throw new Error("DirectGrantsLiteStrategy: No poolId provided. Please call `setPoolId` first.");
}
checkStrategy() {
if (!this.strategy)
throw new Error("DirectGrantsLiteStrategy: No strategy address provided. Please call `setContract` first.");
}
/* Read Functions */
async getNative() {
this.checkStrategy();
const native = await this.contract.read.NATIVE();
return native;
}
/* Public Storage Variables */
async useRegistryAnchor() {
this.checkStrategy();
const anchor = await this.contract.read.useRegistryAnchor();
return anchor;
}
async metadataRequired() {
this.checkStrategy();
const required = await this.contract.read.metadataRequired();
return required;
}
async registrationStartTime() {
this.checkStrategy();
const startTime = await this.contract.read.registrationStartTime();
return startTime;
}
async registrationEndTime() {
this.checkStrategy();
const endTime = await this.contract.read.registrationEndTime();
return endTime;
}
async recipientsCounter() {
this.checkStrategy();
const counter = await this.contract.read.recipientsCounter();
return counter;
}
async statusesBitMap(index) {
this.checkStrategy();
const bitMap = await this.contract.read.statusesBitMap([index]);
return bitMap;
}
async recipientToStatusIndexes(recipient) {
this.checkStrategy();
const indexes = await this.contract.read.recipientToStatusIndexes([
recipient,
]);
return indexes;
}
async getPoolAmount() {
this.checkStrategy();
const amount = await this.contract.read.getPoolAmount();
return amount;
}
async getPoolId() {
this.checkStrategy();
const id = await this.contract.read.getPoolId();
return id;
}
async getRecipient(recipientId) {
this.checkStrategy();
const recipient = await this.contract.read.getRecipient([recipientId]);
return recipient;
}
async getRecipientStatus(recipientId) {
this.checkStrategy();
const status = await this.contract.read.getRecipientStatus([recipientId]);
return status;
}
async getStrategyId() {
this.checkStrategy();
const id = await this.contract.read.getStrategyId();
return id;
}
async isPoolActive() {
this.checkStrategy();
const active = await this.contract.read.isPoolActive();
return active;
}
async isValidAllocator(allocator) {
this.checkStrategy();
const valid = await this.contract.read.isValidAllocator([allocator]);
return valid;
}
/**
* Write functions
*/
/**
*
* @returns DeployParams {abi, bytecode}
*/
getDeployParams() {
const version = "DirectGrantsLiteStrategy1.0";
const constructorArgs = encodeAbiParameters(parseAbiParameters("address, string"), [this.allo.address(), version]);
const constructorArgsNo0x = constructorArgs.slice(2);
return {
abi,
bytecode: (bytecode + constructorArgsNo0x),
};
}
async getInitializeData(data) {
const encodedData = encodeAbiParameters(parseAbiParameters("(bool, bool, uint64, uint64)"), [
[
data.useRegistryAnchor,
data.metadataRequired,
data.registrationStartTime,
data.registrationEndTime,
],
]);
return encodedData;
}
/**
*
* @param data - Allocation: (address,(((address,uint256),uint256,uint256),bytes))
* @returns `0x${string}`
*/
getEncodedAllocation(data) {
const encoded = encodeAbiParameters(parseAbiParameters("address, address, uint256"), [data.token, data.recipientId, data.amount]);
return encoded;
}
/**
*
* @param allocation - Allocation[]: [{token: `0x${string}`, recipientId: `0x${string}`, amount: bigint}]
* @returns TransactionData: {to: `0x${string}`, data: `0x${string}`, value: string}
*/
getAllocateData(allocations) {
this.checkPoolId();
let totalNativeAmount = BigInt(0);
for (const allocation of allocations) {
if (allocation.token.toLowerCase() === NATIVE.toLowerCase())
totalNativeAmount += allocation.amount;
}
const encoded = encodeAbiParameters(parseAbiParameters("(address token, address recipientId, uint256 amount)[]"), [allocations]);
const encodedData = encodeFunctionData({
abi: alloAbi,
functionName: "allocate",
args: [this.poolId, encoded],
});
return {
to: this.allo.address(),
data: encodedData,
value: totalNativeAmount.toString(),
};
}
/**
*
* @param data - (address, address, Metadata)
* @returns
*/
getRegisterRecipientData(data) {
this.checkPoolId();
const encoded = encodeAbiParameters(parseAbiParameters("address, address, (uint256, string)"), [
data.registryAnchor || ZERO_ADDRESS,
data.recipientAddress,
[data.metadata.protocol, data.metadata.pointer],
]);
const encodedData = encodeFunctionData({
abi: alloAbi,
functionName: "registerRecipient",
args: [this.poolId, encoded],
});
return {
to: this.allo.address(),
data: encodedData,
value: "0",
};
}
/**
* Batch register recipients
*
* @param data - Array of RegisterDataDirectGrantsLiteVoting
*
* @returns TransactionData
*/
getBatchRegisterRecipientData(data) {
this.checkPoolId();
const encodedParams = [];
data.forEach((registerData) => {
const encoded = encodeAbiParameters(parseAbiParameters("address, address, (uint256, string)"), [
registerData.registryAnchor || ZERO_ADDRESS,
registerData.recipientAddress,
[registerData.metadata.protocol, registerData.metadata.pointer],
]);
encodedParams.push(encoded);
});
const poolIds = Array(encodedParams.length).fill(this.poolId);
const encodedData = encodeFunctionData({
abi: alloAbi,
functionName: "batchRegisterRecipient",
args: [poolIds, encodedParams],
});
return {
to: this.allo.address(),
data: encodedData,
value: "0",
};
}
/**
* Provides a function to batch together multiple calls in a single external call
*
* @param data - Array of encoded data
*
* @returns - Encoded transaction data
*/
multicall(data) {
this.checkPoolId();
const encodedData = encodeFunctionData({
abi,
functionName: "multicall",
args: [data],
});
return {
to: this.strategy,
data: encodedData,
value: "0",
};
}
/**
* Review recipients
*
* @param statuses - Array of status indexes and statusRows
*
* @returns TransactionData
*/
reviewRecipients(statuses, refRecipientsCounter) {
const data = encodeFunctionData({
abi,
functionName: "reviewRecipients",
args: [statuses, refRecipientsCounter],
});
return {
to: this.strategy,
data: data,
value: "0",
};
}
updatePoolTimestamps(registrationStartTime, registrationEndTime) {
const data = encodeFunctionData({
abi,
functionName: "updatePoolTimestamps",
args: [registrationStartTime, registrationEndTime],
});
return {
to: this.strategy,
data: data,
value: "0",
};
}
withdraw(address) {
const data = encodeFunctionData({
abi,
functionName: "withdraw",
args: [address],
});
return {
to: this.strategy,
data: data,
value: "0",
};
}
}