1

I'm trying to make a simple test in Truffle using Ganache where I call a function from a smart contract instance. This component will create a Vault and return me its address.

My truffle test does the following:

const VaultFactory = artifacts.require("./VaultFactory");
const Vault = artifacts.require("./Vault");

contract('VaultFactory', async () => {
    it("Should create a new Vault", async () => {
        let VaultFactoryInstance = await VaultFactory.deploy();
        let VaultAddress = await VaultFactoryInstance.CreateVaultContract.call();
        let VaultInstance = await Vault.at(VaultAddress);
    });
});

The VaultFactory.sol code that creates the Vault does the following (the Vault's constructor is empty):

function CreateVaultContract ()
    public
    returns(address)
{
    Vault newVault = new Vault();
    emit VaultCreation(msg.sender, newVault, VaultState.Created);
    return address(newVault);
}

The VaultAdress that I get is not empty, however, when I try to get the VaultInstance, it gives me the following error:

Uncaught Error: Cannot create instance of Vault; no code at address 0xed41bb9a56dad9b9d0901400f0a8de72d3cf1854

I tried doing a web3.eth.getCode(VaultAddress); to see if I had any code, but it returns me 0x0.

So, my VaultFactory contract seems to be deployed and looks like it created a Vault. But for some reason, I can't manage to get its instance. Any idea why?

  • 1
    Try to replace await VaultFactory.deploy() with await VaultFactory.new(). – goodvibration Jun 15 '18 at 15:33
  • 1
    Also, the CreateVaultContract function is not constant (i.e., it changes the state), so you cannot call it and get the return-value directly (you need to send it as a transaction, and get the return-value from the event that this function emits). – goodvibration Jun 15 '18 at 15:35
1

let VaultAddress = await VaultFactoryInstance.CreateVaultContract.call();

should be:

let VaultAddress = await VaultFactoryInstance.CreateVaultContract();

0

I finally managed to get a working solution (even though I'm not sure it's the best one).

const VaultFactory = artifacts.require("./VaultFactory");
const Vault = artifacts.require("./Vault");

contract('VaultFactory', async () => {
    it("Should create a new Vault", async () => {
        let VaultFactoryInstance = await VaultFactory.deploy();
        let VaultReceipt = await VaultFactoryInstance.CreateVaultContract();

        //This returns the address of the newly created Vault
        let VaultAddress = VaultReceipt.logs[0].address;

        let VaultInstance = await Vault.at(VaultAddress);
    });
});

This way, I can get my Vault address and can get the instance of it. I then tried to call a function and it works perfectly!

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.