DeclarationError: Identifier already declared

I got error in my smart contract,

/Pool.sol:10:1: DeclarationError: Identifier already declared. import './ERC20.sol'; ^------------------------------^ Token.sol:10:1: The previous declaration is here: contract ERC20 { ^ (Relevant source part starts here and spans across multiple lines).

Token.sol is using ERC20 contract inline and not importing it, while Pool.sol is importing Token.sol, ERC20.sol

I tried changing name of ERC20 to ERC20-new throughout the Token.sol file only so it could fix the conflict still faced some issues


// SPDX-License-Identifier: MIT

pragma solidity >=0.6.12;
pragma experimental ABIEncoderV2;

import './Token.sol';
import './Initializable.sol';
import './SafeMath.sol';
import './interfaces/IERC20.sol';
import './interfaces/ERC20.sol';
import './interfaces/IFactory.sol';
import './interfaces/IPool.sol';
import './interfaces/ISettlement.sol';
import './interfaces/IOracle.sol';

contract Pool is Initializable {
    using SafeMath for uint;

    bytes4 private constant SELECTOR = bytes4(keccak256(bytes('transfer(address,uint256)')));

    address public factory;
    address public baseToken;
    uint public baseTokenDecimals;
    address public oracle;
    uint public oracleDecimals;

    uint public baseTokenTargetAmount;
    uint public baseTokenBalance;

    uint public liquidityParameter;

    bool public tradeEnabled;
    bool public depositEnabled;
    bool public withdrawEnabled;


pragma solidity >=0.7.5;

import './SafeMath.sol';

interface tokenRecipient {
    function receiveApproval(address _from, uint256 _value, address _token, bytes calldata _extraData) external;

contract ERC20 {
    mapping (address => uint256) public balanceOf;
    mapping (address => mapping (address => uint256)) public allowance;
    event Transfer(address indexed from, address indexed to, uint256 value);
    event Approval(address indexed _owner, address indexed _spender, uint256 _value);
    function _transfer(address _from, address _to, uint _value) internal {
        require(_to != address(0x0));
        require(balanceOf[_from] >= _value);
        require(balanceOf[_to] + _value >= balanceOf[_to]);
        uint previousBalances = balanceOf[_from] + balanceOf[_to];
        balanceOf[_from] -= _value;
        balanceOf[_to] += _value;
        emit Transfer(_from, _to, _value);
        assert(balanceOf[_from] + balanceOf[_to] == previousBalances);

    function transfer(address _to, uint256 _value) public returns (bool success) {
        _transfer(msg.sender, _to, _value);
        return true;

    function transferFrom(address _from, address _to, uint256 _value) public returns (bool success) {
        require(_value <= allowance[_from][msg.sender]);     // Check allowance
        allowance[_from][msg.sender] -= _value;
        _transfer(_from, _to, _value);
        return true;

    function approve(address _spender, uint256 _value) public
        returns (bool success) {
        allowance[msg.sender][_spender] = _value;
        emit Approval(msg.sender, _spender, _value);
        return true;

    function approveAndCall(address _spender, uint256 _value, bytes memory _extraData)
        returns (bool success) {
        tokenRecipient spender = tokenRecipient(_spender);
        if (approve(_spender, _value)) {
            spender.receiveApproval(msg.sender, _value, address(this), _extraData);
            return true;

Hi, welcome! :wave:

I am not sure, maybe you should share your source code.

Hi there,
I have added the code for reference

Emmm, have you pasted all code in the Pool?

Partly since pool has error in line > import ‘./interfaces/ERC20.sol’;
Which throws duplicate declaration error in Token.sol line 10 > contract ERC20 {

Maybe you can rename this contract:

import './interfaces/ERC20.sol';

to import './interfaces/IERC20.sol'; and change the contract name in the interfaces/ERC20.sol

@rsv did this work. How did you resolve this issue?

Hello, apologies for bumping an old thread but I had the same error message with a different cause. In my case I was using Remix and I imported all but one file as per npm, for example:

import "@openzeppelin/contracts/governance/Governor.sol";

But one of the files was imported through a URL:

import "";

This created conflicts, and using exclusively npm type imports worked.

No, I don't think that's the issue here. Although I haven't got the hold of the issue yet but surely remix don't complain while importing the file either way.

Have anybody else got the solution for this problem?

I think this might help -->

Hey everyone, did someone happen to resolve this issue?
I'm facing a smilar issue.
Any help is appreciated.