@taqueria/plugin-taquito
Version:
A taqueria plugin for originating smart contracts using Taquito
138 lines (125 loc) • 4.11 kB
text/typescript
import {
getAddressOfAlias,
getCurrentEnvironment,
getCurrentEnvironmentConfig,
getParameter,
RequestArgs,
sendAsyncErr,
sendJsonRes,
} from '@taqueria/node-sdk';
import { Environment } from '@taqueria/node-sdk/types';
import { Expr, Parser } from '@taquito/michel-codec';
import { TezosToolkit, WalletOperationBatch } from '@taquito/taquito';
import { BatchWalletOperation } from '@taquito/taquito/dist/types/wallet/batch-operation';
import {
configureToolKitForNetwork,
configureToolKitForSandbox,
doWithin,
getEnvTypeAndNodeConfig,
handleOpsError,
TransferOpts as Opts,
} from './common';
export type ContractInfo = {
contractAlias: string;
contractAddress: string;
parameter: string;
entrypoint: string;
mutezTransfer: number;
};
type TableRow = {
contractAlias: string;
contractAddress: string;
parameter: string;
entrypoint: string;
mutezTransfer: string;
destination: string;
};
const isContractAddress = (contract: string): boolean =>
contract.startsWith('tz1') || contract.startsWith('tz2') || contract.startsWith('tz3') || contract.startsWith('KT1');
const getContractInfo = async (parsedArgs: Opts, env: Environment.t): Promise<ContractInfo> => {
const contract = parsedArgs.contract;
const protocolArgs = RequestArgs.create(parsedArgs);
return {
contractAlias: isContractAddress(contract) ? 'N/A' : contract,
contractAddress: isContractAddress(contract) ? contract : await getAddressOfAlias(env, contract),
parameter: parsedArgs.param ? await getParameter(protocolArgs, parsedArgs.param) : 'Unit',
entrypoint: parsedArgs.entrypoint ?? 'default',
mutezTransfer: parseInt(parsedArgs.mutez ?? '0'),
};
};
const createBatchForTransfer = (
tezos: TezosToolkit,
contractsInfo: ContractInfo[],
gasLimit?: number,
storageLimit?: number,
fee?: number,
): WalletOperationBatch =>
contractsInfo.reduce((acc, contractInfo) =>
acc.withTransfer({
fee,
gasLimit,
storageLimit,
to: contractInfo.contractAddress,
amount: contractInfo.mutezTransfer,
parameter: {
entrypoint: contractInfo.entrypoint,
value: new Parser().parseMichelineExpression(contractInfo.parameter) as Expr,
},
mutez: true,
}), tezos.wallet.batch());
export const performTransferOps = async (
tezos: TezosToolkit,
env: string,
contractsInfo: ContractInfo[],
maxTimeout: number,
gasLimit?: number,
storageLimit?: number,
fee?: number,
): Promise<BatchWalletOperation> => {
const batch = createBatchForTransfer(tezos, contractsInfo, gasLimit, storageLimit, fee);
try {
return await doWithin<BatchWalletOperation>(maxTimeout, async () => {
const op = await batch.send();
await op.confirmation();
return op;
});
} catch (err) {
return handleOpsError(err, env);
}
};
const prepContractInfoForDisplay = (tezos: TezosToolkit, contractInfo: ContractInfo): TableRow => {
return {
contractAlias: contractInfo.contractAlias,
contractAddress: contractInfo.contractAddress,
parameter: contractInfo.parameter,
entrypoint: contractInfo.entrypoint,
mutezTransfer: contractInfo.mutezTransfer.toString(),
destination: tezos.rpc.getRpcUrl(),
};
};
const transfer = async (opts: Opts): Promise<void> => {
const protocolArgs = RequestArgs.create(opts);
const env = getCurrentEnvironmentConfig(protocolArgs);
if (!env) return sendAsyncErr(`There is no environment called ${protocolArgs.env} in your config.json`);
try {
const [envType, nodeConfig] = await getEnvTypeAndNodeConfig(protocolArgs, env);
const tezos = await (envType === 'Network'
? configureToolKitForNetwork(protocolArgs, nodeConfig, opts.sender)
: configureToolKitForSandbox(nodeConfig, opts.sender));
const contractInfo = await getContractInfo(opts, env);
await performTransferOps(
tezos,
getCurrentEnvironment(protocolArgs),
[contractInfo],
opts.timeout,
opts.gasLimit,
opts.storageLimit,
opts.fee,
);
const contractInfoForDisplay = prepContractInfoForDisplay(tezos, contractInfo);
return sendJsonRes([contractInfoForDisplay]);
} catch {
return sendAsyncErr('No operations performed');
}
};
export default transfer;