mirror of
				https://github.com/ethereum/solidity
				synced 2023-10-03 13:03:40 +00:00 
			
		
		
		
	
		
			
				
	
	
		
			111 lines
		
	
	
		
			3.6 KiB
		
	
	
	
		
			Python
		
	
	
	
	
	
			
		
		
	
	
			111 lines
		
	
	
		
			3.6 KiB
		
	
	
	
		
			Python
		
	
	
	
	
	
| #!/usr/bin/env python3
 | |
| 
 | |
| # ------------------------------------------------------------------------------
 | |
| # This file is part of solidity.
 | |
| #
 | |
| # solidity is free software: you can redistribute it and/or modify
 | |
| # it under the terms of the GNU General Public License as published by
 | |
| # the Free Software Foundation, either version 3 of the License, or
 | |
| # (at your option) any later version.
 | |
| #
 | |
| # solidity is distributed in the hope that it will be useful,
 | |
| # but WITHOUT ANY WARRANTY; without even the implied warranty of
 | |
| # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 | |
| # GNU General Public License for more details.
 | |
| #
 | |
| # You should have received a copy of the GNU General Public License
 | |
| # along with solidity.  If not, see <http://www.gnu.org/licenses/>
 | |
| #
 | |
| # (c) 2023 solidity contributors.
 | |
| # ------------------------------------------------------------------------------
 | |
| 
 | |
| import os
 | |
| import re
 | |
| import subprocess
 | |
| from shutil import which
 | |
| from textwrap import dedent
 | |
| from typing import Optional
 | |
| 
 | |
| from runners.base import BaseRunner
 | |
| from test_helpers import SettingsPreset
 | |
| from test_helpers import settings_from_preset
 | |
| 
 | |
| def run_forge_command(command: str, env: Optional[dict] = None):
 | |
|     subprocess.run(
 | |
|         command.split(),
 | |
|         env=env if env is not None else os.environ.copy(),
 | |
|         check=True
 | |
|     )
 | |
| 
 | |
| 
 | |
| class FoundryRunner(BaseRunner):
 | |
|     """Configure and run Foundry-based projects"""
 | |
| 
 | |
|     FOUNDRY_CONFIG_FILE = "foundry.toml"
 | |
| 
 | |
|     def setup_environment(self):
 | |
|         super().setup_environment()
 | |
|         if which("forge") is None:
 | |
|             raise RuntimeError("Forge not found.")
 | |
| 
 | |
|     @staticmethod
 | |
|     def profile_name(preset: SettingsPreset):
 | |
|         """Returns foundry profile name"""
 | |
|         # Replace - or + by underscore to avoid invalid toml syntax
 | |
|         return re.sub(r"(\-|\+)+", "_", preset.value)
 | |
| 
 | |
|     @staticmethod
 | |
|     def profile_section(profile_fields: dict) -> str:
 | |
|         return dedent("""\
 | |
|             [profile.{name}]
 | |
|             gas_reports = ["*"]
 | |
|             auto_detect_solc = false
 | |
|             solc = "{solc}"
 | |
|             evm_version = "{evm_version}"
 | |
|             optimizer = {optimizer}
 | |
|             via_ir = {via_ir}
 | |
| 
 | |
|             [profile.{name}.optimizer_details]
 | |
|             yul = {yul}
 | |
|         """).format(**profile_fields)
 | |
| 
 | |
|     @BaseRunner.enter_test_dir
 | |
|     def configure(self):
 | |
|         """Configure forge tests profiles"""
 | |
| 
 | |
|         profiles = []
 | |
|         for preset in self.presets:
 | |
|             settings = settings_from_preset(preset, self.config.evm_version)
 | |
|             profiles.append(self.profile_section({
 | |
|                 "name": self.profile_name(preset),
 | |
|                 "solc": self.solc_binary_path,
 | |
|                 "evm_version": self.config.evm_version,
 | |
|                 "optimizer": str(settings["optimizer"]["enabled"]).lower(),
 | |
|                 "via_ir": str(settings["viaIR"]).lower(),
 | |
|                 "yul": str(settings["optimizer"]["details"]["yul"]).lower(),
 | |
|             }))
 | |
| 
 | |
|         with open(
 | |
|             file=self.test_dir / self.FOUNDRY_CONFIG_FILE,
 | |
|             mode="a",
 | |
|             encoding="utf-8",
 | |
|         ) as f:
 | |
|             for profile in profiles:
 | |
|                 f.write(profile)
 | |
| 
 | |
|         run_forge_command("forge install", self.env)
 | |
| 
 | |
|     @BaseRunner.enter_test_dir
 | |
|     def compile(self, preset: SettingsPreset):
 | |
|         """Compile project"""
 | |
| 
 | |
|         # Set the Foundry profile environment variable
 | |
|         self.env.update({"FOUNDRY_PROFILE": self.profile_name(preset)})
 | |
|         run_forge_command("forge build", self.env)
 | |
| 
 | |
|     @BaseRunner.enter_test_dir
 | |
|     def run_test(self):
 | |
|         """Run project tests"""
 | |
| 
 | |
|         run_forge_command("forge test --gas-report", self.env)
 |