0

I'm trying to compile a "FundMe.sol" contract: the issue is that when I try to compile it I keep getting the following Compiler Error:

Brownie v1.19.2 - Python development framework for Ethereum

New compatible solc version available: 0.8.0
Compiling contracts...
  Solc version: 0.8.0
  Optimizer: Enabled  Runs: 200
  EVM Version: Istanbul
CompilerError: solc returned the following errors:

ParserError: Source "@chainlink/contracts/src/v0.8/interfaces/AggregatorV3Interface.sol" not found: File outside of allowed directories.
  --> contracts/FundMe.sol:15:1:
   |
15 | import "@chainlink/contracts/src/v0.8/interfaces/AggregatorV3Interface.sol";
   | ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^

The contract is included inside of the "contracts" folder (initted by brownie), moreover I have created the "brownie-config.yaml" file which should remap @chainlink - I feel as it might have contain some kind of error aswell.

I'm including all the mentioned files down below:

Project Folder: brownie_fund_me

FundMe.sol:

//SPDX-License-Identifier: MIT
//Last update: 25/12/2022

/* ***** ABI = Application Binary Interface *****
 * Interfaces compile down to an ABI. 
 *
 * ABI tells Solidity and other coding languages
 * how it can interact with other contracts. 
 *
 * Anytime you want to interact with another
 * deployed contract, you will need that contracts' ABI.
 */

pragma solidity >=0.6.0 <0.9.0;

// ***** Imports *****
import "@chainlink/contracts/src/v0.8/interfaces/AggregatorV3Interface.sol";   //The following library is shown below
/*
 *
 *      interface AggregatorV3Interface 
 *      {
 *       function decimals() external view returns (uint8);
 *
 *       function description() external view returns (string memory);
 *
 *       function version() external view returns (uint256);    <-------------- Version
 *
 *       function getRoundData(uint80 _roundId) external view returns 
 *       (
 *           uint80 roundId,
 *           int256 answer,          
 *           uint256 startedAt,
 *           uint256 updatedAt,
 *           uint80 answeredInRound
 *       );
 *
 *       function latestRoundData() external view returns 
 *       (
 *           uint80 roundId,
 *           int256 answer,             <---------- Value in USD
 *           uint256 startedAt,
 *           uint256 updatedAt,
 *           uint80 answeredInRound
 *       );
 *      }
 *
 */

// ***** FundMe *****
// The following contract allows the end users to send a minimum amount
// of ETH without being able to retrive it.
// This contract is a good example of crowd funding.
contract FundMe{
    
    // ***** AddressToAmountFunded *****
    // The following mapping allows the user to access the amount funded
    // by somebody, provided the address.
    mapping (address => uint256) public AddressToAmountFunded;

    // Array of addresses where the address of each funder will be stored in a temporary way
    // Every time the owner calls the withdraw function, the array is being reset
    address[] public funders;

    // Owners' address: this will be the only address being able to withdraw
    address public owner;

    // Constructor is called automatically and istantly when the contract is being deployed
    // Such thing allows the deployer of the contract to be the owner
    constructor() public
    {
        owner = msg.sender;     // msg.sender is who calls a function, in the constructor case, who deploys the contract
    }

    // ***** onlyOwner *****
    // The following modifier is used in the declaration of functions, such as withdraw, 
    // in order to allow the function, to be called only by the owner.
    modifier onlyOwner
    {
        require(msg.sender == owner);      // Whoever calls the function (msg.sender) must be the owner
        _;                                 // The "_;" means that we call the instruction after we check that the address of the caller is equal to owner
    }

    // ***** fund *****
    // The following function allows the users to fund the contract with a minimum amount of money "minimumUSD"
    // to this date (25/12/2022) 50$ = 0,041ETH = 41000000000000000Wei = (41 * 10^15)Wei - to update the value, check the USD/ETH change and convert to Wei here https://eth-converter.com/
    // If the amount funded is <= minimumUSD the transaction will not go through and will lead to an inversion of the
    // transaction
    // ! ! ! ! ! Please notice that the amount funded cannot be retrived in any way ! ! ! ! !
    function fund() public payable
    {
        uint256 minimumUSD = 41 * 10 ** 15;                                                                                        // Minimum amount transferable
        require(msg.value >= minimumUSD, "The amount of ETH you sent is less then 50$ - Transaction is being inverted");           // "msg.value" is a keyword that stays for the amount of Wei sent

        AddressToAmountFunded[msg.sender] += msg.value;             // Given an address, the mapping will return the amount funded by such account - Note that these values will be reset every time withdraw is called
        funders.push(msg.sender);                                   // The funders' address will be added to the funders array - Note that these values will be reset every time withdraw is called
    }

    // ***** getVersion *****
    // The following function is contained inside of the imported library AggregatorV3Interface
    // When called, the function will return the current version of the contract/library AggregatorV3Interface
    // ! ! ! ! ! This function will only work if the ENVIROMENT used is local (METAMASK) - JVMs will not return any value and will lead to a possible error ! ! ! ! !
    function getVersion() public view returns(uint256)
    {      
        return AggregatorV3Interface(0xD4a33860578De61DBAbDc8BFdb98FD742fA7028e).version();     // .version method is contained inside of AggregatorV3Interface, the address can be find here
        //                                                                                                                                                                                 |
        // The function works also if written like this:                                                                                                                                   |
        // AggregatorV3Interface priceFeed = AggregatorV3Interface(0xD4a33860578De61DBAbDc8BFdb98FD742fA7028e);  <--- Address                                                              |
        // return priceFeed.version();                                                                           <--- ABI                                                                 /
        // You can find the Addresses for AggregatorV3Interface here ---> https://docs.chain.link/data-feeds/price-feeds/addresses/ <----------------------------------------------------
    }

    // ***** getPrice *****
    // The following function is contained inside of the imported library AggregatorV3Interface
    // When called, the function will return the current value of 1ETH in USD, please note that you will get an apporximate value 
    // ! ! ! ! ! This function will only work if the ENVIROMENT used is local (METAMASK) - JVMs will not return any value and will lead to a possible error ! ! ! ! !
    function getPrice() public view returns(uint256)
    {
        AggregatorV3Interface priceFeed = AggregatorV3Interface(0xD4a33860578De61DBAbDc8BFdb98FD742fA7028e);    // .latestRoundData method is contained inside of AggregatorV3Interface, the address can be found above
        (,int256 answer,,,) = priceFeed.latestRoundData();                                                      // The method returns 5 different values, we exclude all of them but answer, for further understanding check at AggregatorV3Interface under imports
        return uint256(answer / 10 ** 8);                                                                       // Answer is divided by 10^8 so that the value in USD has no decimals and is easier to read
        
        // Historical:
        // 23/12/2022 - 1,226.67395017
        // 25/12/2022 - 1,220.00000000
    }

    // ***** getConvertionRate *****
    // The following function could be considered an extension of getPrice : given
    // the amount of ETH, the function will return the current value of such amount of ETH
    // in USD
    // ! ! ! ! ! This function will only work if the ENVIROMENT used is local (METAMASK) - JVMs will not return any value and will lead to a possible error ! ! ! ! !
    function getConvertionRate(uint256 ETH_Amount) public view returns(uint256)
    {
        uint256 ETH_Price = getPrice();                         // Calls getPrice function
        uint256 ETH_AmountInUSD = ETH_Price * ETH_Amount;       // Current ETH pirce * ETH amount
        return ETH_AmountInUSD;                                 // Returns the value of amount ETH in USD
    }

    // ***** withdraw *****
    // The following function allows the deployer of the contract (owner) to withdraw
    // the amount of ETH funded to the contract, moreover when the function is called,
    // the funders array will be reset
    function withdraw() payable onlyOwner public                // Check for onlyOwner modifier description at line 77
    {
        payable(msg.sender).transfer(address(this).balance);    // This line of code allows the withdrawal, this refers to the contract

        for(uint256 funderIndex = 0; funderIndex < funders.length; funderIndex++)   // The following cycle allows the reset of the money
        {                                                                           // value sent by the funders, accessible through mapping
            address funder = funders[funderIndex];
            AddressToAmountFunded[funder] = 0;
        }

        funders = new address[] (0);                            // funders array gets reset, so that it's able to store new values starting from 0
    }
}

brownie-config.yaml:

dependencies:
  # - <organization/repo@version>
  - smartcontractkit/[email protected]
  
compiler:
  solc:
    remappings:
      - '@chainlink = smartcontractkit/[email protected]' 

I'm quiet new to "python-solidity" coding, but so far I had managed to overcome all the issues that were popping up. I have spent over 2 days tring to find a solution to this problem - it's becoming really frustrating. I'm really thankful to whoever - at least - tries helping me!

Solutions I tried:

-Changing versions of pragma solidity, imports and repo;

-Adding a .vscode folder --> setting.json containing a path to solidity remappings;

-Updating solc and brownie

1 Answer 1

0

You can try with an older version, this one worked for me : @1.1.1

So re run the following commande:

brownie pm install smartcontractkit/[email protected]

and then in brownie-config.yaml :

dependencies:
  # - <organization/repo>@<version>
  - smartcontractkit/[email protected]
compiler:
  solc:
    remappings:
      - '@chainlink=smartcontractkit/[email protected]'

FundMe.sol :

// SPDX-License-Identifier: MIT

pragma solidity ^0.6.6;

import "@chainlink/contracts/src/v0.6/interfaces/AggregatorV3Interface.sol";

This worked for me, i hope the same for you

7
  • hey, thanks for the answer - it's telling me that the package is already installed which seems quiet wiered Jan 6, 2023 at 13:58
  • @waterlilyjack i updated the answer, hope it will help
    – noro meb
    Jan 6, 2023 at 14:14
  • I have tried again and I found out by typing brownie pm list that I not only had smartcontractkit/[email protected] but also @0.2.1 and @0.5.1 - such thing was maybe causing not detected "NameCollision error". Unfortunately, after i got rid of them, it still doesn't work, I'm currently getting crazy trying to find an answer in two other discussion and in Juan Blanco's remapping documentation. I have also re introduced the setting.json file that - of course - isn't helping. Jan 6, 2023 at 15:03
  • The discussions are the following one: discussion_one Jan 6, 2023 at 15:04
  • discussion_2 Jan 6, 2023 at 15:05

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

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