Error: Returned error: sender account not recognized -- Reason given: Custom error (could not decode)

I am trying to run a test against my initializer. My test is below. But i get the above error message. I am synced with ganache (ports,network etc) and have my accounts set up in ganache.

My command is "npx truffle test --network development".

Why am i getting this error message?

These are the functions i am trying to test in my smart contract:

    function safeMint(address to, string memory uri) public onlyOwner {
        uint256 tokenId = _tokenIdCounter.current();
        _tokenIdCounter.increment();
        _safeMint(to, tokenId);
        _setTokenURI(tokenId, uri);
    }
    constructor() {
        _disableInitializers();
    }

    function initialize() initializer public {
        __ERC721_init("ComNFT", "CMT");
        __ERC721URIStorage_init();
        __Pausable_init();
        __Ownable_init();
    }
const assert = require('assert');
const { web3 } = require('@openzeppelin/test-environment');
const ComNFT = artifacts.require('ComNFT');
const { expect } = require('chai');

describe('ComNFT', () => {
  let accounts;
  let comNFT;


  beforeEach(async () => {
    accounts = await web3.eth.getAccounts();
    comNFT = await ComNFT.new({ from: accounts[0] });
    //done();
  });

  it('should be correctly initialized', async () => {
    const owner = await comNFT.owner();
    expect(owner).to.equal(accounts[0]);
    const name = await comNFT.name();
    expect(name).to.equal('ComNFT');
    const symbol = await comNFT.symbol();
    expect(symbol).to.equal('CMT');
    
  });
  

  it('should be able to mint a new token', async () => {
    await web3.eth.sendTransaction({
      from: accounts[0], // The owner account
      to: comNFT.address, // The contract address
      data: comNFT.methods.safeMint(accounts[1], 'token URI').encodeABI() // The function call and arguments, encoded as ABI
  
    });

    const tokenURI = await comNFT.tokenURI(1); // Assume the token ID is 1
    //expect(tokenURI).to.equal('token URI');
    assert.equal(tokenURI, 'token URI');
  });
});

Hey @Golanger,

This is related to this thread, which is already solved. However, I can't clearly see the reason behind it happening here.

Do you know in which test is throwing, or if it's throwing in the beforeEachHook?

It seems to be throwing in this section

  beforeEach(async () => {
    accounts = await web3.eth.getAccounts();
    comNFT = await ComNFT.new({ from: accounts[0] });
  });

Usually, the error happens when there's a transaction to be sent by an account that ganache hasn't previously loaded.

I'd look at the accounts in ganache and what this accounts array contains. Maybe the test environment is isolated from ganache or running a separate instance, which may be causing the sender not recognized error.

Can you take a look? If both differ, you'll need to make adjustments :sweat_smile:

Kind of makes sense, although i am able to do "npx truffle compile", even use commands in the console which take gas from my ganache account, but for some reason its not the same for running a test.

Where can i find out if the test env is isolated from ganache? or running a separate instance?

Compiling or opening the console does not send any transaction, thus, is expected to not throw this error.

Can you run these instructions in your truffle console?

const accounts = await web3.eth.getAccounts();
console.log(accounts);
const comNFT = await ComNFT.new({ from: accounts[0] });

The accounts logged should be the same as the ones you have in ganache and the error should also appear there.

You can notice if the environment is different in test by doing the same, the idea is that all should be consistent.

Here is my output

truffle(development)> const accounts = await web3.eth.getAccounts();
undefined
truffle(development)> console.log(accounts);
[
  '0x41F22fE138a93774B2Fb767DEF0d7dD34279798A',
  '0xE99919a7b5538791D5e0534A8c44885edec2b971',
  '0x19a4C2FD07b525057bdF76acA89BBb3e82737cf0',
  '0xB43D91eb2a985725A033589C0a000f96eC390736',
  '0x8F78e6771d4154FbbbdE4F4CcAf32a51FCD2f949',
  '0x87DD300815E54D7633D6B11e25C380Af428ADb89',
  '0xEb6ef71083DfCeAacE8Cc95DCb1BF51141d79Fd3',
  '0x7dC7b9eccF5d69a6C1f4fb54cfD6D61367fDBe45',
  '0xA58E0dc97e8650cD6F6279ab6bB8018918CD3982',
  '0x97a8A9B526C42b5E458C4268a509B068C1d729b5'
]
undefined
truffle(development)> const comNFT = await ComNFT.new({ from: accounts[0] });
undefined
truffle(development)>

Where abouts in my test file can i place this logic? to cross reference consistency?

Thanks

Seems like it's working correctly on your console, which is connecting properly to ganache.

If comNFT = await ComNFT.new({ from: accounts[0] }); is failing in your tests, I'd expect to see a different accounts variable if you console.log them.

Now that I see, it may be because you're importing web3 from @openzeppelin/test-environment in your tests, which have a different configuration.

I'd try following the truffle recommendation of using contract() instead of describe() to access the accounts or importing accounts from @openzeppelin/test-environment.

Your first 2 paragraphs make sense! So on that note, according to the configuration, would i need to replace "web3" with "truffle"?

And would i need to just replace "describe" with "contract" both as below?

const assert = require('assert');
const { truffle } = require('@openzeppelin/test-environment');
const ComNFT = artifacts.require('ComNFT');
const { expect } = require('chai');

contract('ComNFT', () => {
  let accounts;
  let comNFT;

I tried the method you recommended, and it seemed to throw 3 errors

  0 passing (3s)
  3 failing

  1) ComNFT
       should be correctly initialized:

      AssertionError: expected '0x00000000000000000000000000000000000…' to equal '0x41F22fE138a93774B2Fb767DEF0d7dD3427…'
      + expected - actual

      -0x0000000000000000000000000000000000000000
      +0x41F22fE138a93774B2Fb767DEF0d7dD34279798A

      at Context.<anonymous> (test/ComNFT.js:17:22)
      at processTicksAndRejections (node:internal/process/task_queues:96:5)

  2) ComNFT
       should fail when called by a non-owner account:

      AssertionError [ERR_ASSERTION]: Expected "onlyOwner" error message not found
      + expected - actual

      -false
      +true

      at Context.<anonymous> (test/ComNFT.js:33:7)
      at processTicksAndRejections (node:internal/process/task_queues:96:5)

  3) ComNFT
       should be able to mint a new token:
     TypeError: comNFT.methods.safeMint is not a function
      at Context.<anonymous> (test/ComNFT.js:41:28)
      at processTicksAndRejections (node:internal/process/task_queues:96:5)

Any tips here?

1 Like

I'm glad it finally worked :slight_smile:

Regarding your tests, I'd assume this is just an expected malfunction of your contract setup and the tests are working as expected (telling you something wrong).

I'm not sure why your tests are failing, but feel free to open a new topic with your question and detailed information about your smart contract.

OK i shall do thank you