| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143 | 
import { Interface } from "../abi/index.js";import { getCreateAddress } from "../address/index.js";import {    concat, defineProperties, getBytes, hexlify,    assert, assertArgument} from "../utils/index.js";import { BaseContract, copyOverrides, resolveArgs } from "./contract.js";import type { InterfaceAbi } from "../abi/index.js";import type { Addressable } from "../address/index.js";import type { ContractRunner } from "../providers/index.js";import type { BytesLike } from "../utils/index.js";import type {    ContractInterface, ContractMethodArgs, ContractDeployTransaction,} from "./types.js";import type { ContractTransactionResponse } from "./wrappers.js";// A = Arguments to the constructor// I = Interface of deployed contracts/** *  A **ContractFactory** is used to deploy a Contract to the blockchain. */export class ContractFactory<A extends Array<any> = Array<any>, I = BaseContract> {    /**     *  The Contract Interface.     */    readonly interface!: Interface;    /**     *  The Contract deployment bytecode. Often called the initcode.     */    readonly bytecode!: string;    /**     *  The ContractRunner to deploy the Contract as.     */    readonly runner!: null | ContractRunner;    /**     *  Create a new **ContractFactory** with %%abi%% and %%bytecode%%,     *  optionally connected to %%runner%%.     *     *  The %%bytecode%% may be the ``bytecode`` property within the     *  standard Solidity JSON output.     */    constructor(abi: Interface | InterfaceAbi, bytecode: BytesLike | { object: string }, runner?: null | ContractRunner) {        const iface = Interface.from(abi);        // Dereference Solidity bytecode objects and allow a missing `0x`-prefix        if (bytecode instanceof Uint8Array) {            bytecode = hexlify(getBytes(bytecode));        } else {            if (typeof(bytecode) === "object") { bytecode = bytecode.object; }            if (!bytecode.startsWith("0x")) { bytecode = "0x" + bytecode; }            bytecode = hexlify(getBytes(bytecode));        }        defineProperties<ContractFactory>(this, {            bytecode, interface: iface, runner: (runner || null)        });    }    attach(target: string | Addressable): BaseContract & Omit<I, keyof BaseContract> {        return new (<any>BaseContract)(target, this.interface, this.runner);    }    /**     *  Resolves to the transaction to deploy the contract, passing %%args%%     *  into the constructor.     */    async getDeployTransaction(...args: ContractMethodArgs<A>): Promise<ContractDeployTransaction> {        let overrides: Omit<ContractDeployTransaction, "data"> = { };        const fragment = this.interface.deploy;        if (fragment.inputs.length + 1 === args.length) {            overrides = await copyOverrides(args.pop());        }        if (fragment.inputs.length !== args.length) {            throw new Error("incorrect number of arguments to constructor");        }        const resolvedArgs = await resolveArgs(this.runner, fragment.inputs, args);        const data = concat([ this.bytecode, this.interface.encodeDeploy(resolvedArgs) ]);        return Object.assign({ }, overrides, { data });    }    /**     *  Resolves to the Contract deployed by passing %%args%% into the     *  constructor.     *     *  This will resolve to the Contract before it has been deployed to the     *  network, so the [[BaseContract-waitForDeployment]] should be used before     *  sending any transactions to it.     */    async deploy(...args: ContractMethodArgs<A>): Promise<BaseContract & { deploymentTransaction(): ContractTransactionResponse } & Omit<I, keyof BaseContract>> {        const tx = await this.getDeployTransaction(...args);        assert(this.runner && typeof(this.runner.sendTransaction) === "function",            "factory runner does not support sending transactions", "UNSUPPORTED_OPERATION", {            operation: "sendTransaction" });        const sentTx = await this.runner.sendTransaction(tx);        const address = getCreateAddress(sentTx);        return new (<any>BaseContract)(address, this.interface, this.runner, sentTx);    }    /**     *  Return a new **ContractFactory** with the same ABI and bytecode,     *  but connected to %%runner%%.     */    connect(runner: null | ContractRunner): ContractFactory<A, I> {        return new ContractFactory(this.interface, this.bytecode, runner);    }    /**     *  Create a new **ContractFactory** from the standard Solidity JSON output.     */    static fromSolidity<A extends Array<any> = Array<any>, I = ContractInterface>(output: any, runner?: ContractRunner): ContractFactory<A, I> {        assertArgument(output != null, "bad compiler output", "output", output);        if (typeof(output) === "string") { output = JSON.parse(output); }        const abi = output.abi;        let bytecode = "";        if (output.bytecode) {            bytecode = output.bytecode;        } else if (output.evm && output.evm.bytecode) {            bytecode = output.evm.bytecode;        }        return new this(abi, bytecode, runner);    }}
 |