Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: Support Vyper 0.3.10 #97

Merged
merged 16 commits into from
Oct 26, 2023
Merged

feat: Support Vyper 0.3.10 #97

merged 16 commits into from
Oct 26, 2023

Conversation

z80dev
Copy link
Contributor

@z80dev z80dev commented Oct 24, 2023

What I did

fixes: #96 APE-1462

How I did it

Compile each set of contracts separately according to specified optimization level in pragmas.

If no optimization level is there, we fall back to "True" as before.

also, for version pragmas, we support the new format now, looks like #pragma version 0.3.10

How to verify it

Compile any contract with #pragma optimize codesize

Checklist

  • Passes all linting checks (pre-commit and CI jobs)
  • New test cases have been added and are passing
  • Documentation has been updated
  • PR title follows Conventional Commit standard (will be automatically included in the changelog)

@z80dev z80dev requested review from fubuloubu and antazoey October 24, 2023 04:00
@z80dev z80dev changed the title Feat: New pragmas support feat: New pragmas support Oct 24, 2023
@z80dev z80dev changed the title feat: New pragmas support feat: Support Vyper 0.3.10 Oct 24, 2023
ape_vyper/compiler.py Outdated Show resolved Hide resolved
ape_vyper/compiler.py Outdated Show resolved Hide resolved
@antazoey
Copy link
Member

hey to fix the mypy issue (temporarily) just pin pydantic <2 in the lint dependencies with a comment saying it's needed, i did it on core ape and some other repos too

antazoey
antazoey previously approved these changes Oct 24, 2023
ape_vyper/compiler.py Show resolved Hide resolved
fubuloubu
fubuloubu previously approved these changes Oct 25, 2023
Comment on lines 82 to 89
pragma_match = next(re.finditer(r"(?:\n|^)\s*#\s*@version\s*([^\n]*)", source_str), None)
if pragma_match is None:
return None # Try compiling with latest
# support new pragma syntax
pragma_match = next(
re.finditer(r"(?:\n|^)\s*#\s*pragma\s+version\s*([^\n]*)", source_str), None
)
if pragma_match is None:
return None # Try compiling with latest
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This might work a little nicer

    if not (pragma_match := next(
        itertools.chain(
            re.finditer(r"(?:\n|^)\s*#\s*@version\s*([^\n]*)", source_str),
            re.finditer(r"(?:\n|^)\s*#\s*pragma\s+version\s*([^\n]*)", source_str),
            None,
        )
    ):
        return None  # Try compiling with latest

Copy link
Contributor Author

@z80dev z80dev Oct 25, 2023

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

had to make a few tweaks to this:

  • we want to do something with the match if we have it, so I had to invert the condition here by removing the not
  • all the args to itertools.chain must be iterators, so None caused an exception, I had to wrap it as [None] which accomplishes what we want, but looks a bit weird. Do you have an idea for making it more readable?
def get_version_pragma_spec(source: Union[str, Path]) -> Optional[SpecifierSet]:
    """
    Extracts version pragma information from Vyper source code.

    Args:
        source (str): Vyper source code

    Returns:
        ``packaging.specifiers.SpecifierSet``, or None if no valid pragma is found.
    """
    source_str = source if isinstance(source, str) else source.read_text()
    if pragma_match := next(
        itertools.chain(
            re.finditer(r"(?:\n|^)\s*#\s*@version\s*([^\n]*)", source_str),
            re.finditer(r"(?:\n|^)\s*#\s*pragma\s+version\s*([^\n]*)", source_str),
            [None],
        )
    ):
        raw_pragma = pragma_match.groups()[0]
        pragma_str = " ".join(raw_pragma.split()).replace("^", "~=")
        if pragma_str and pragma_str[0].isnumeric():
            pragma_str = f"=={pragma_str}"

        try:
            return SpecifierSet(pragma_str)
        except InvalidSpecifier:
            logger.warning(f"Invalid pragma spec: '{raw_pragma}'. Trying latest.")
            return None
    else:
        return None

Copy link
Contributor Author

@z80dev z80dev Oct 25, 2023

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

ended up with this:

def get_version_pragma_spec(source: Union[str, Path]) -> Optional[SpecifierSet]:
    """
    Extracts version pragma information from Vyper source code.

    Args:
        source (str): Vyper source code

    Returns:
        ``packaging.specifiers.SpecifierSet``, or None if no valid pragma is found.
    """
    version_pragma_patterns = [
        r"(?:\n|^)\s*#\s*@version\s*([^\n]*)",
        r"(?:\n|^)\s*#\s*pragma\s+version\s*([^\n]*)",
    ]

    source_str = source if isinstance(source, str) else source.read_text()
    for pattern in version_pragma_patterns:
        for match in re.finditer(pattern, source_str):
            raw_pragma = match.groups()[0]
            pragma_str = " ".join(raw_pragma.split()).replace("^", "~=")
            if pragma_str and pragma_str[0].isnumeric():
                pragma_str = f"=={pragma_str}"

            try:
                return SpecifierSet(pragma_str)
            except InvalidSpecifier:
                logger.warning(f"Invalid pragma spec: '{raw_pragma}'. Trying latest.")
                return None
    return None

ape_vyper/compiler.py Outdated Show resolved Hide resolved
ape_vyper/compiler.py Outdated Show resolved Hide resolved
ape_vyper/compiler.py Show resolved Hide resolved
ape_vyper/compiler.py Outdated Show resolved Hide resolved
Copy link
Member

@antazoey antazoey left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM!

@z80dev z80dev merged commit 888ab4c into main Oct 26, 2023
21 of 22 checks passed
@z80dev z80dev deleted the new-pragmas-support branch October 26, 2023 18:46
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

support vyper 0.3.10 [APE-1462]
3 participants