Skip to content

Commit

Permalink
add POL support + deprecate MATIC (#118)
Browse files Browse the repository at this point in the history
  • Loading branch information
nooxx authored Sep 5, 2024
1 parent 5eec788 commit 1bdd798
Show file tree
Hide file tree
Showing 5 changed files with 269 additions and 2 deletions.
3 changes: 2 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -17,10 +17,11 @@ Check out the [full documentation](https://docs.kiln.fi/v1/connect/overview).
- INJ (mainnet)
- KAVA (mainnet)
- KSM (mainnet)
- MATIC (mainnet and sepolia)
- MATIC (deprecated, use POL instead) (mainnet and sepolia)
- NEAR (mainnet and testnet)
- NOBLE (mainnet)
- OSMO (mainnet)
- POL (mainnet and sepolia)
- SOL (mainnet and testnet)
- TIA (mainnet)
- TON (mainnet and testnet)
Expand Down
2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "@kilnfi/sdk",
"version": "2.21.2",
"version": "2.22.0",
"autor": "Kiln <[email protected]> (https://kiln.fi)",
"license": "BUSL-1.1",
"description": "JavaScript sdk for Kiln API",
Expand Down
12 changes: 12 additions & 0 deletions src/services/matic.ts
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ export class MaticService extends Service {
}

/**
* @deprecated Please use POL functions instead
* Craft an approve transaction to the MATIC token contract allowing the contract given to spend the amount given
* If no amount is provided, an infinite amount will be approved
* @param walletAddress wallet address signing the transaction
Expand All @@ -32,6 +33,7 @@ export class MaticService extends Service {
}

/**
* @deprecated Please use POL functions instead
* Craft a buyVoucher transaction to a ValidatorShare proxy contract
* It also links the stake to the account id given
* @param accountId id of the kiln account to use for the stake transaction
Expand All @@ -55,6 +57,7 @@ export class MaticService extends Service {
}

/**
* @deprecated Please use POL functions instead
* Craft a sellVoucher transaction to a ValidatorShare proxy contract
* Note there that your tokens will be unbonding and locked for 21 days after this transaction
* @param walletAddress address delegating
Expand All @@ -75,6 +78,7 @@ export class MaticService extends Service {
}

/**
* @deprecated Please use POL functions instead
* Craft an unstakeClaimTokens transaction to a ValidatorShare proxy contract
* Note that your tokens must be unbonded before you can claim them
* @param walletAddress address delegating
Expand All @@ -89,6 +93,7 @@ export class MaticService extends Service {
}

/**
* @deprecated Please use POL functions instead
* Craft an withdrawRewards transaction to a ValidatorShare proxy contract
* All rewards earned are transferred to the delegator's wallet
* @param walletAddress address delegating
Expand All @@ -103,6 +108,7 @@ export class MaticService extends Service {
}

/**
* @deprecated Please use POL functions instead
* Craft an withdrawRewards transaction to a ValidatorShare proxy contract
* All rewards earned are then re-delegated
* @param walletAddress address delegating
Expand All @@ -117,6 +123,7 @@ export class MaticService extends Service {
}

/**
* @deprecated Please use POL functions instead
* Sign transaction with given integration
* @param integration custody solution to sign with
* @param tx raw transaction
Expand Down Expand Up @@ -151,6 +158,7 @@ export class MaticService extends Service {
}

/**
* @deprecated Please use POL functions instead
* Sign transaction with given integration
* @param integration custody solution to sign with
* @param tx raw transaction
Expand Down Expand Up @@ -179,6 +187,7 @@ export class MaticService extends Service {
}

/**
* @deprecated Please use POL functions instead
* Broadcast transaction to the network
* @param signedTx
*/
Expand All @@ -190,6 +199,7 @@ export class MaticService extends Service {
}

/**
* @deprecated Please use POL functions instead
* Get transaction status
* @param txHash transaction hash
*/
Expand All @@ -199,6 +209,7 @@ export class MaticService extends Service {
}

/**
* @deprecated Please use POL functions instead
* Decode transaction
* @param txSerialized transaction serialized
*/
Expand All @@ -208,6 +219,7 @@ export class MaticService extends Service {
}

/**
* @deprecated Please use POL functions instead
* Convert MATIC to WEI
* @param matic
*/
Expand Down
213 changes: 213 additions & 0 deletions src/services/pol.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,213 @@
import api from "../api";
import { Service } from "./service";
import { utils } from "ethers";
import { ServiceProps } from "../types/service";
import { PolDecodedTx, PolSignedTx, PolTx, PolTxHash, PolTxStatus } from "../types/pol";
import { Integration } from "../types/integrations";
import { TransactionResponse } from "fireblocks-sdk";

export class PolService extends Service {
constructor({ testnet }: ServiceProps) {
super({ testnet });
}

/**
* Craft an approve transaction to the POL token contract allowing the contract given to spend the amount given
* If no amount is provided, an infinite amount will be approved
* @param walletAddress wallet address signing the transaction
* @param contractAddressToApprove contract address that you allow to spend the token
* @param amountPol how many tokens to approve the spending, if not specified an infinite amount will be approved
*/
async craftApproveTx(walletAddress: string, contractAddressToApprove: string, amountPol?: number): Promise<PolTx> {
const { data } = await api.post<PolTx>(`/v1/pol/transaction/approve`, {
wallet: walletAddress,
contract: contractAddressToApprove,
amount_wei: amountPol ? this.polToWei(amountPol.toString()) : undefined,
});
return data;
}

/**
* Craft a buyVoucher transaction to a ValidatorShare proxy contract
* It also links the stake to the account id given
* @param accountId id of the kiln account to use for the stake transaction
* @param walletAddress withdrawal creds /!\ losing it => losing the ability to withdraw
* @param validatorShareProxyAddress ValidatorShare proxy contract address of the validator
* @param amountPol how many tokens to stake in POL
*/
async craftBuyVoucherTx(
accountId: string,
walletAddress: string,
validatorShareProxyAddress: string,
amountPol: number,
): Promise<PolTx> {
const { data } = await api.post<PolTx>(`/v1/pol/transaction/buy-voucher`, {
account_id: accountId,
wallet: walletAddress,
amount_wei: this.polToWei(amountPol.toString()),
validator_share_proxy_address: validatorShareProxyAddress,
});
return data;
}

/**
* Craft a sellVoucher transaction to a ValidatorShare proxy contract
* Note there that your tokens will be unbonding and locked for 21 days after this transaction
* @param walletAddress address delegating
* @param validatorShareProxyAddress ValidatorShare proxy contract address of the validator
* @param amountPol how many tokens to unbond in POL
*/
async craftSellVoucherTx(
walletAddress: string,
validatorShareProxyAddress: string,
amountPol: number,
): Promise<PolTx> {
const { data } = await api.post<PolTx>(`/v1/pol/transaction/sell-voucher`, {
wallet: walletAddress,
amount_wei: this.polToWei(amountPol.toString()),
validator_share_proxy_address: validatorShareProxyAddress,
});
return data;
}

/**
* Craft an unstakeClaimTokens transaction to a ValidatorShare proxy contract
* Note that your tokens must be unbonded before you can claim them
* @param walletAddress address delegating
* @param validatorShareProxyAddress ValidatorShare proxy contract address of the validator
*/
async craftUnstakeClaimTokensTx(walletAddress: string, validatorShareProxyAddress: string): Promise<PolTx> {
const { data } = await api.post<PolTx>(`/v1/pol/transaction/unstake-claim-tokens`, {
wallet: walletAddress,
validator_share_proxy_address: validatorShareProxyAddress,
});
return data;
}

/**
* Craft an withdrawRewards transaction to a ValidatorShare proxy contract
* All rewards earned are transferred to the delegator's wallet
* @param walletAddress address delegating
* @param validatorShareProxyAddress ValidatorShare proxy contract address of the validator
*/
async craftWithdrawRewardsTx(walletAddress: string, validatorShareProxyAddress: string): Promise<PolTx> {
const { data } = await api.post<PolTx>(`/v1/pol/transaction/withdraw-rewards`, {
wallet: walletAddress,
validator_share_proxy_address: validatorShareProxyAddress,
});
return data;
}

/**
* Craft an withdrawRewards transaction to a ValidatorShare proxy contract
* All rewards earned are then re-delegated
* @param walletAddress address delegating
* @param validatorShareProxyAddress ValidatorShare proxy contract address of the validator
*/
async craftRestakeRewardsTx(walletAddress: string, validatorShareProxyAddress: string): Promise<PolTx> {
const { data } = await api.post<PolTx>(`/v1/pol/transaction/restake-rewards`, {
wallet: walletAddress,
validator_share_proxy_address: validatorShareProxyAddress,
});
return data;
}

/**
* Sign transaction with given integration
* @param integration custody solution to sign with
* @param tx raw transaction
* @param note note to identify the transaction in your custody solution
*/
async sign(integration: Integration, tx: PolTx, note?: string): Promise<PolSignedTx> {
const payload = {
rawMessageData: {
messages: [
{
content: tx.data.unsigned_tx_hash,
preHash: {
content: tx.data.unsigned_tx_serialized,
hashAlgorithm: "KECCAK256",
},
},
],
},
};

const fbSigner = this.getFbSigner(integration);
const fbNote = note ? note : "POL tx from @kilnfi/sdk";
const fbTx = await fbSigner.sign(payload, this.testnet ? "ETH_TEST5" : "ETH", fbNote);
const { data } = await api.post<PolSignedTx>(`/v1/pol/transaction/prepare`, {
unsigned_tx_serialized: tx.data.unsigned_tx_serialized,
r: `0x${fbTx?.signedMessages?.[0].signature.r}`,
s: `0x${fbTx?.signedMessages?.[0].signature.s}`,
v: fbTx?.signedMessages?.[0].signature.v ?? 0,
});
data.data.fireblocks_tx = fbTx;
return data;
}

/**
* Sign transaction with given integration
* @param integration custody solution to sign with
* @param tx raw transaction
* @param note note to identify the transaction in your custody solution
*/
async signAndBroadcast(integration: Integration, tx: PolTx, note?: string): Promise<TransactionResponse> {
if (!integration.fireblocksDestinationId) {
throw new Error("Fireblocks destination id is missing in integration");
}

const payload = {
contractCallData: tx.data.contract_call_data,
};

const fbSigner = this.getFbSigner(integration);
const fbNote = note ? note : "POL tx from @kilnfi/sdk";
const assetId = this.testnet ? "ETH_TEST5" : "ETH";
return await fbSigner.signAndBroadcastWith(
payload,
assetId,
tx,
integration.fireblocksDestinationId,
false,
fbNote,
);
}

/**
* Broadcast transaction to the network
* @param signedTx
*/
async broadcast(signedTx: PolSignedTx): Promise<PolTxHash> {
const { data } = await api.post<PolTxHash>(`/v1/pol/transaction/broadcast`, {
tx_serialized: signedTx.data.signed_tx_serialized,
});
return data;
}

/**
* Get transaction status
* @param txHash transaction hash
*/
async getTxStatus(txHash: string): Promise<PolTxStatus> {
const { data } = await api.get<PolTxStatus>(`/v1/pol/transaction/status?tx_hash=${txHash}`);
return data;
}

/**
* Decode transaction
* @param txSerialized transaction serialized
*/
async decodeTx(txSerialized: string): Promise<PolDecodedTx> {
const { data } = await api.get<PolDecodedTx>(`/v1/pol/transaction/decode?tx_serialized=${txSerialized}`);
return data;
}

/**
* Convert POL to WEI
* @param pol
*/
polToWei(pol: string): string {
return utils.parseEther(pol).toString();
}
}
41 changes: 41 additions & 0 deletions src/types/pol.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,41 @@
import { TransactionResponse } from "fireblocks-sdk";
import { TransactionSerializableLegacy, TransactionReceipt } from "viem";

export type PolTx = {
data: {
unsigned_tx_hash: string;
unsigned_tx_serialized: string;
to: string;
contract_call_data: string;
amount_wei?: string;
nonce: number;
gas_limit: number;
max_priority_fee_per_gas_wei: string;
max_fee_per_gas_wei: string;
chain_id: number;
};
};

export type PolTxHash = {
data: {
tx_hash: string;
};
};

export type PolTxStatus = {
data: {
status: "success" | "error" | "pending_confirmation";
receipt: TransactionReceipt | null;
};
};
export type PolSignedTx = {
data: {
fireblocks_tx: TransactionResponse;
signed_tx_serialized: string;
};
};

export type PolDecodedTx = TransactionSerializableLegacy & {
functionName?: string;
args?: any[];
};

0 comments on commit 1bdd798

Please sign in to comment.