/**
 * Sends an Ethereum transaction executing this method with the supplied parameters. This is a read/write
 * Ethereum operation and will cost gas.
 {{> params_docstring inputs=inputs docstrings=devdoc.params}}
 * @param txData Additional data for transaction
 * @returns The hash of the transaction
 */
async sendTransactionAsync(
{{> typed_params inputs=inputs}}
txData?: Partial<TxData> | undefined,
): Promise<string> {
    {{#each inputs}}
    {{#assertionType name type}}{{/assertionType}}
    {{/each}}
    const self = this as any as {{contractName}}Contract;
    const encodedData = self._strictEncodeArguments('{{this.functionSignature}}', [{{> normalized_params inputs=inputs}}]);
    const txDataWithDefaults = await BaseContract._applyDefaultsToTxDataAsync(
        {
            to: self.address,
            ...txData,
            data: encodedData,
        },
        self._web3Wrapper.getContractDefaults(),
    );
    if (txDataWithDefaults.from !== undefined) {
        txDataWithDefaults.from = txDataWithDefaults.from.toLowerCase();
    }

    const txHash = await self._web3Wrapper.sendTransactionAsync(txDataWithDefaults);
    return txHash;
},
/**
 * Sends an Ethereum transaction and waits until the transaction has been successfully mined without reverting.
 * If the transaction was mined, but reverted, an error is thrown.
 {{> params_docstring inputs=inputs docstrings=devdoc.params}}
 * @param txData Additional data for transaction
 * @param pollingIntervalMs Interval at which to poll for success
 * @returns A promise that resolves when the transaction is successful
 */
awaitTransactionSuccessAsync(
{{> typed_params inputs=inputs}}
    txData?: Partial<TxData>,
    pollingIntervalMs?: number,
    timeoutMs?: number,
): PromiseWithTransactionHash<TransactionReceiptWithDecodedLogs> {
    {{#each inputs}}
    {{#assertionType name type}}{{/assertionType}}
    {{/each}}
    const self = this as any as {{contractName}}Contract;
    {{#if inputs}}
    const txHashPromise = self.{{languageSpecificName}}.sendTransactionAsync({{> normalized_params input=inputs}}, txData);
    {{else}}
    const txHashPromise = self.{{languageSpecificName}}.sendTransactionAsync(txData);
    {{/if}}
    return new PromiseWithTransactionHash<TransactionReceiptWithDecodedLogs>(
        txHashPromise,
        (async (): Promise<TransactionReceiptWithDecodedLogs> => {
            // When the transaction hash resolves, wait for it to be mined.
            return self._web3Wrapper.awaitTransactionSuccessAsync(
                await txHashPromise,
                pollingIntervalMs,
                timeoutMs,
            );
        })(),
    );
},
/**
 * Estimates the gas cost of sending an Ethereum transaction calling this method with these arguments.
 {{> params_docstring inputs=inputs docstrings=devdoc.params}}
 * @param txData Additional data for transaction
 * @returns The hash of the transaction
 */
async estimateGasAsync(
{{> typed_params inputs=inputs}}
    txData?: Partial<TxData> | undefined,
): Promise<number> {
    {{#each inputs}}
    {{#assertionType name type}}{{/assertionType}}
    {{/each}}
    const self = this as any as {{contractName}}Contract;
    const encodedData = self._strictEncodeArguments('{{this.functionSignature}}', [{{> normalized_params inputs=inputs}}]);
    const txDataWithDefaults = await BaseContract._applyDefaultsToTxDataAsync(
        {
            to: self.address,
            ...txData,
            data: encodedData,
        },
        self._web3Wrapper.getContractDefaults(),
    );
    if (txDataWithDefaults.from !== undefined) {
        txDataWithDefaults.from = txDataWithDefaults.from.toLowerCase();
    }

    const gas = await self._web3Wrapper.estimateGasAsync(txDataWithDefaults);
    return gas;
},
async validateAndSendTransactionAsync(
    {{> typed_params inputs=inputs}}
    txData?: Partial<TxData> | undefined,
    ): Promise<string> {
    await (this as any).{{languageSpecificName}}.callAsync(
    {{#each inputs~}}
        {{name}},
    {{/each~}}
        txData,
    );
    const txHash =  await (this as any).{{languageSpecificName}}.sendTransactionAsync(
    {{#each inputs~}}
        {{name}},
    {{/each~}}
        txData,
    ); 
    return txHash;
},
