El contrato inteligente se está implementando pero la llamada no devuelve la dirección del contrato después de la implementación

Entonces, he estado tratando de implementar un contrato inteligente usando nodejs, pero cuando llamo a la función para implementar, no obtengo una dirección de contrato en mi consola. Es como si la función send() nunca completara su ejecución. Y es por eso que la siguiente instrucción nunca comienza a ejecutarse, aunque sé que el contrato aún se está implementando en mi red blockchain local (lo sé porque puedo ver en el indicador de cmd dónde se está ejecutando mi ganache-cli. Estoy tratando de obtener la dirección del contrato implementado, dígame cómo hacer lo mismo.

Comportamiento esperado La llamada await contract.deploy({..}).send({..}) debería devolver una respuesta, y después de eso, la dirección del contrato debería imprimirse en la consola.

Comportamiento real En cambio, no se imprime ningún resultado en la consola después de esto: 'Función de implementación llamada, a punto de implementar'.

la salida del símbolo del sistema se detiene después de:

D:/Usuario/proyecto>nodo src/implementar

¿Sin web3? ¡Deberías considerar probar MetaMask!

[AsyncFunction: deployment] ingresado, a punto de implementarse

Aunque sé que el contrato se ha implementado porque mi ganache-cli muestra este resultado:

Transacción: 0x12345

Contrato creado: 0x12345

Consumo de gasolina: 1605526

Número de bloque: 6

Block Time: se muestra la fecha y la hora de la implementación

Aquí está el código que estoy tratando de ejecutar: (deploy.js)

var Web3 = require('web3');

// abibytecode[0] has abi, abibytecode[1] has bytecode
const abibytecode = require('../src/compile');
var web3;

if (typeof web3 !== 'undefined') {
    web3 = new Web3(web3.currentProvider);
} else {
    // set the provider you want from Web3.providers
    console.log('No web3? You should consider trying MetaMask!');
    web3 = new Web3('ws://localhost:8545');
}

let account = 'my account address is here';

const contract = new web3.eth.Contract(abibytecode[0]);

const deploy = async () => {
    console.log('Deploy function called, about to deploy');
    const response = await contract.deploy({data: abibytecode[1]}).send({
      from: account,
      gas: '3000000'
    });
    console.log('Contract deployed to:', response.address);
    console.log('Contract deployed to:', response.options.address);

    return response;
};
console.log(deploy);
deploy((res)=>{console.log(res)});

Versiones:

  • web3.js: 1.0.0-beta.55

  • nodejs: v10.16.0

  • navegador: Ninguno, ejecutando el script desde el comando

  • nodo ethereum: ganache-cli

Además, esta es mi primera publicación en stackexchange, así que si me perdí alguna información, házmelo saber y llenaré los vacíos.

¿ Estás seguro de que abibytecode[0]es un objeto y no una cadena? ¿ Estás seguro de que abibytecode[1]es una cadena que comienza con 0x?
Puede consultar mi sugerencia para la implementación de contratos en ethereum.stackexchange.com/a/71580/16043 . Es posible que desee probar eso en su lugar (aunque tenga en cuenta que se basa en web3.js 1.0.0-beta.34).
> ¿Estás seguro de que abibytecode[0] es un objeto y no una cadena? ¿Estás seguro de que abibytecode[1] es una cadena que comienza con 0x? typeof abibytecode[0] devuelve 'objeto' y typeof abibytecode[1] devuelve 'cadena' El bytecode, sin embargo, no comienza con 0x. Y no creo que se suponga que lo sea, porque cuando escribo el contrato inteligente en Remix IDE, me da el mismo código de bytes (el que no comienza con 0x)
Lo siento, en realidad estoy escribiendo un comentario sobre stackexchange por primera vez.
He tenido problemas con él antes, y tal vez lo hayan solucionado en versiones posteriores de web3.js, pero por si acaso, sugiero que lo use data: '0x' + abibytecode[1]en su lugar. Además, si el constructor de su contrato toma argumentos de entrada, debe agregarlos arguments: [your argument values]cuando llame a contract.deploy.
Intenté hacer eso. No funcionó, la salida aún no se muestra. Tenga en cuenta que el contrato inteligente se está implementando y la dirección del contrato está impresa en ganache-cli.
No tengo constructor en mi contrato :P
Estoy atrapado en esta situación desde hace casi un día. Si alguien puede ayudar, estaré agradecido.
También probé una alternativa para implementar el contrato, pero eso parece darme los mismos resultados. Ver aquí: pastebin.com/jAY5kef4
¿Has probado mi sugerencia (segundo comentario desde arriba)?

Respuestas (1)

Para implementar un contrato se requiere un firmante. El uso de web3 requiere que la clave privada de la dirección esté presente en el nodo. Asegúrese de que la clave privada de la cuenta esté presente en el nodo de prueba local. Una forma es comenzar constantemente ganache-clicon un conjunto de claves privadas.

Hay un problema en la forma en que se invoca la función de implementación asíncrona, debería ser

deploy().then(function(response){ console.log(response)})

También puede cambiar a ethers.js, es más amigable para los desarrolladores

const { ContractFactory, Wallet, providers } = require('ethers')
const provider = new providers.JsonRpcProvider('http://localhost:8545')
const wallet = new Wallet(privateKey, provider)
async function deployContracts() {
    let token = new ContractFactory(tokenabi, tokenbytecode, wallet)
    // this deploys the contract
    token = await token.deploy()
    // we must wait until it is mined
    token = await token.deployed()
    return token
}