Skip to content

Commit

Permalink
support finding all best versions
Browse files Browse the repository at this point in the history
  • Loading branch information
taquangtrung committed Apr 27, 2023
1 parent 76212b7 commit 4dd636b
Show file tree
Hide file tree
Showing 4 changed files with 64 additions and 10 deletions.
2 changes: 1 addition & 1 deletion pyproject.toml
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
[project]
name = "solc_detect"
version = "0.0.7"
version = "0.0.8"
authors = [{name="Ta Quang Trung"},]
description = "A tool to detect Solidity compiler version required by smart contracts"
dynamic = ["dependencies"]
Expand Down
4 changes: 4 additions & 0 deletions solc_detect/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -16,3 +16,7 @@ def find_best_solc_version(input_file):
def find_best_solc_version_for_pragma(pragma_version):
"""Find the best version of Solc compiler for pragma."""
return solc_detect.find_best_solc_version_for_pragma(pragma_version)

def find_all_best_solc_versions_for_pragma(pragma_version):
"""Find all the best versions of Solc compiler for pragma."""
return solc_detect.find_all_best_solc_versions_for_pragma(pragma_version)
32 changes: 25 additions & 7 deletions solc_detect/__main__.py
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,16 @@ def configure_cli_arguments():
help="",
)

# Quiet mode, print only the best version.
arg_parser.add_argument(
"-a",
"--all-best-verions",
dest="all_best_versions",
action="store_true",
default=False,
help="Finding all best versions for each minor Solc version.",
)

# Help
arg_parser.add_argument(
"-h",
Expand Down Expand Up @@ -73,15 +83,23 @@ def main():
arg_parser.print_usage()
arg_parser.exit()

pragma_version = solc_detect.find_pragma_solc_version(input_file)
if not args.quiet:
print("Detected pragmas:", pragma_version)

best_version = solc_detect.find_best_solc_version_for_pragma(pragma_version)
pragmas = solc_detect.find_pragma_solc_version(input_file)
if not args.quiet:
print("Best version:", best_version)
print("Detected pragmas:", pragmas)

if args.all_best_versions:
best_version = solc_detect.find_all_best_solc_versions_for_pragma(pragmas)
if not args.quiet:
print("All best versions:", best_version)
else:
print(best_version)
return
else:
print(best_version)
best_version = solc_detect.find_best_solc_version_for_pragma(pragmas)
if not args.quiet:
print("Best version:", best_version)
else:
print(best_version)


if __name__ == "__main__":
Expand Down
36 changes: 34 additions & 2 deletions solc_detect/solc_detect.py
Original file line number Diff line number Diff line change
Expand Up @@ -51,20 +51,52 @@ def find_best_solc_version_for_pragma(pragma_versions) -> Optional[str]:
# First, use `semantic_version` module to find the best version
all_semvers = [semantic_version.Version(v) for v in group]
version_spec = semantic_version.NpmSpec(constraint)
if (best_version := version_spec.select(all_semvers)):
if best_version := version_spec.select(all_semvers):
return str(best_version)
except ValueError:
# If errors occur, then use `node_semver` module to find it
if (best_version := nodesemver.max_satisfying(group, constraint)):
if best_version := nodesemver.max_satisfying(group, constraint):
return str(best_version)

# Unable to find a suitable version
return None

def find_all_best_solc_versions_for_pragma(pragma_versions) -> List[str]:
"""Find multiple best versions of Solc compiler for a pragma version. These
versions are the latest patches of each version satisfying the required
pragmas.
"""
version_groups = enumerate_and_group_solc_version_by_minor_version()
constraint = " ".join(pragma_versions)

best_versions: List[str] = []
for group in version_groups:
try:
# First, use `semantic_version` module to find the best version
all_semvers = [semantic_version.Version(v) for v in group]
version_spec = semantic_version.NpmSpec(constraint)
if best_version := version_spec.select(all_semvers):
best_versions.append(str(best_version))
except ValueError:
# If errors occur, then use `node_semver` module to find it
if best_version := nodesemver.max_satisfying(group, constraint):
best_versions.append(str(best_version))

# Return all best versions
return best_versions

def find_best_solc_version(input_file) -> Optional[str]:
"""Find the best version of Solc compiler for a smart contract. This version
is the latest patch of the lowest minor version satisfying the required
pragmas."""
pragma_versions = find_pragma_solc_version(input_file)
return find_best_solc_version_for_pragma(pragma_versions)


def find_all_best_solc_versions(input_file) -> List[str]:
"""Find multiple best versions of Solc compiler for a smart contract. These
versions are the latest patches of each version satisfying the required
pragmas.
"""
pragma_versions = find_pragma_solc_version(input_file)
return find_all_best_solc_versions(pragma_versions)

0 comments on commit 4dd636b

Please sign in to comment.