Skip to content
This repository has been archived by the owner on Dec 1, 2023. It is now read-only.

Replace subprocess #236

Merged
merged 92 commits into from
Nov 17, 2022
Merged

Conversation

andrew-fleming
Copy link
Contributor

@andrew-fleming andrew-fleming commented Oct 17, 2022

This PR supersedes #169 and resolves #161.

This PR proposes to include some notable changes that enable the removal of subprocess.

Account

  • Initializing the Account class requires Account to inherit the AsyncObject class.
    • Python does not allow asynchronous __init__s; therefore, this is a bit of a hacky workaround.
    • A cleaner solution could be to decouple Account initialization and deployment.

starknet_cli

  • Direct starknet_cli calls accept two parameters: args and command_args.
    1. args: a dictionary wrapped in SimpleNamespace.
    2. command_args: commands passed in an array as strings (similar to how Nile passed arguments to subprocess).
  • The new set_args function just requires the network and returns the necessary object to pass to starknet_cli.
  • command_args are appropriately created in the function itself.
  • The new capture_stdout captures the print statements from the starknet_cli calls. This is because those function calls do not return the values.

CLI

  • The CLI requires asyncclick.

NRE

  • Scripts must now be written with async/await.
    • async def run(nre):
    • balance = await nre.call(...)

Testing

  • Tests, of course, must use async/await when testing async functions.
  • For asynchronous mocks, AsyncMock should be used.

Copy link
Contributor

@martriay martriay left a comment

Choose a reason for hiding this comment

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

Looking good!

src/nile/core/account.py Outdated Show resolved Hide resolved
logging.info(output)

return output
return output
Copy link
Contributor

Choose a reason for hiding this comment

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

why not logging on query anymore?

Copy link
Contributor Author

Choose a reason for hiding this comment

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

It's still logging on query, the log command is before the query_flag and watch_mode conditional. The logic is just consolidated from how it was:

    if type != "call" and output:
        logging.info(output)
        if not query_flag and watch_mode:
            transaction_hash = _get_transaction_hash(output)
            return await status(normalize_number(transaction_hash), network, watch_mode)

contract_name=contract_name,
signature=signature,
signature=prepare_params(signature),
Copy link
Contributor

Choose a reason for hiding this comment

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

can/should prepare_params be called within execute_call?

Copy link
Contributor Author

Choose a reason for hiding this comment

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

They can and they were. The idea was to support set_command_args using a loop for most of the args (meaning less if statements and verbosity). That said, they probably should be called in execute_call. I'll throw them back in

Copy link
Member

Choose a reason for hiding this comment

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

I see prepare_params is used for signature inside execute_call already but hasn't been removed here right?

tests/commands/test_get_nonce.py Outdated Show resolved Hide resolved
tests/commands/test_get_nonce.py Outdated Show resolved Hide resolved
Comment on lines 44 to 45
# args = set_args("goerli")
command_args = {"contract_address": "0x4d2"}
Copy link
Contributor

Choose a reason for hiding this comment

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

Suggested change
# args = set_args("goerli")
command_args = {"contract_address": "0x4d2"}
command_args = {"contract_address": contract_address}

Copy link
Contributor Author

Choose a reason for hiding this comment

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

This test checks that non-0x addresses convert to hex (hence the hardcoded 0x4d2)



def _add_args(key, value):
return [f"--{key}", *value] if type(value) is list else [f"--{key}", value]
Copy link
Contributor

Choose a reason for hiding this comment

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

Suggested change
return [f"--{key}", *value] if type(value) is list else [f"--{key}", value]
return [f"--{key}", *value] if type(value) is list else [f"--{key}", value]

is it enough with *value or should we flatten if there's nested lists?

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Yeah, flattening seems correct

src/nile/starknet_cli.py Outdated Show resolved Hide resolved
Copy link
Member

@ericnordelo ericnordelo left a comment

Choose a reason for hiding this comment

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

Looking very good Andrew! I left a couple of comments.

@@ -2,7 +2,7 @@
"""Nile CLI entry point."""
import logging

import click
import asyncclick as click
Copy link
Member

Choose a reason for hiding this comment

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

Is asyncclick usage implying a requirement to update plugins accordingly?

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Great question! I'm honestly not sure. I'll try and test it to find out

src/nile/core/declare.py Outdated Show resolved Hide resolved
contract_name=contract_name,
signature=signature,
signature=prepare_params(signature),
Copy link
Member

Choose a reason for hiding this comment

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

I see prepare_params is used for signature inside execute_call already but hasn't been removed here right?

contract_name=contract_name,
inputs=prepare_params(arguments),
Copy link
Member

Choose a reason for hiding this comment

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

Aren't we calling prepare_params for inputs inside execute_call already?

ericnordelo
ericnordelo previously approved these changes Nov 15, 2022
Copy link
Member

@ericnordelo ericnordelo left a comment

Choose a reason for hiding this comment

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

Looking very good Andrew!

tests/test_starknet_cli.py Outdated Show resolved Hide resolved
ericnordelo
ericnordelo previously approved these changes Nov 15, 2022
Copy link
Member

@ericnordelo ericnordelo left a comment

Choose a reason for hiding this comment

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

LGTM!

martriay
martriay previously approved these changes Nov 16, 2022
Copy link
Contributor

@martriay martriay left a comment

Choose a reason for hiding this comment

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

🚀 🚀 🚀 🚀 🚀 🚀

src/nile/core/declare.py Outdated Show resolved Hide resolved
@martriay martriay dismissed stale reviews from ericnordelo and themself via f27558e November 16, 2022 23:55
@martriay martriay merged commit f74b568 into OpenZeppelin:main Nov 17, 2022
@andrew-fleming andrew-fleming deleted the replace-subprocess branch November 17, 2022 05:10
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Replace subprocess with direct python calls
3 participants