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

Add support for ledger #195

Merged
merged 19 commits into from
Oct 30, 2023
Merged

Add support for ledger #195

merged 19 commits into from
Oct 30, 2023

Conversation

moisses89
Copy link
Member

@moisses89 moisses89 commented Feb 11, 2023

Description

Closes #269

  • add load_ledger_cli_owners to add owner accounts from ledger
  • add ledger_manager to manage connection and communication with ledger using ledgereth library
  • ledger_manager also includes sign_eipt712 to sign domain_hash and message_hash without enable blind signature
  • add hw_exceptions to handle exceptions from signing devices
  • add ledger_manager tests

@coveralls
Copy link

coveralls commented Feb 11, 2023

Pull Request Test Coverage Report for Build 4153242346

  • 35 of 75 (46.67%) changed or added relevant lines in 3 files are covered.
  • No unchanged relevant lines lost coverage.
  • Overall coverage decreased (-0.4%) to 52.229%

Changes Missing Coverage Covered Lines Changed/Added Lines %
safe_cli/prompt_parser.py 4 5 80.0%
safe_cli/operators/hw_accounts/ledger_account.py 19 35 54.29%
safe_cli/operators/safe_operator.py 12 35 34.29%
Totals Coverage Status
Change from base Build 4046181829: -0.4%
Covered Lines: 738
Relevant Lines: 1413

💛 - Coveralls

@vzctl
Copy link

vzctl commented Mar 22, 2023

Hi! Thanks for this PR - amazing work!

We (in Aurora Labs) have tested load_ledger_cli_owners function but unfortunately it only loads one owner at a time (with multiple ledgers/owners connected simultaneously).

Is it a known limitation? Is there a possible workaround?

@moisses89
Copy link
Member Author

Hi! Thanks for this PR - amazing work!

We (in Aurora Labs) have tested load_ledger_cli_owners function but unfortunately it only loads one owner at a time (with multiple ledgers/owners connected simultaneously).

Is it a known limitation? Is there a possible workaround?

Good point, I should test it, for now I was only testing one ledger.
I think that could be some limitations related with "ledger driver" and SO integration, but it is something interesting to test.

@coveralls
Copy link

coveralls commented Oct 20, 2023

Coverage Status

coverage: 92.284% (+0.4%) from 91.927% when pulling 91a7a9d on add_ledger_owner into 09e8507 on master.

"signTransaction is deprecated in favor of sign_transaction",
category=DeprecationWarning,
)
pass
Copy link
Member

Choose a reason for hiding this comment

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

Suggested change
pass
return self.sign_transaction(transaction_dict)

* add tests
Refactor ledger sign_eip712 to be used in other places
@moisses89 moisses89 marked this pull request as ready for review October 26, 2023 13:45
@moisses89 moisses89 requested a review from Uxio0 October 26, 2023 13:50
@moisses89
Copy link
Member Author

Hi! Thanks for this PR - amazing work!

We (in Aurora Labs) have tested load_ledger_cli_owners function but unfortunately it only loads one owner at a time (with multiple ledgers/owners connected simultaneously).

Is it a known limitation? Is there a possible workaround?

@vzctl with this new approach you can load more than one owner from ledger but you can only connect one ledger device.

Copy link
Member

@Uxio0 Uxio0 left a comment

Choose a reason for hiding this comment

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

Really nice, some small suggestions

README.md Outdated Show resolved Hide resolved
requirements.txt Outdated Show resolved Hide resolved
safe_cli/operators/hw_accounts/hw_exceptions.py Outdated Show resolved Hide resolved
safe_cli/operators/hw_accounts/hw_exceptions.py Outdated Show resolved Hide resolved
safe_cli/operators/hw_accounts/ledger_manager.py Outdated Show resolved Hide resolved
@@ -325,6 +335,34 @@ def load_cli_owners(self, keys: List[str]):
except ValueError:
print_formatted_text(HTML(f"<ansired>Cannot load key={key}</ansired>"))

def load_ledger_cli_owners(self, legacy_account: bool = False):
Copy link
Member

Choose a reason for hiding this comment

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

Return type

Copy link
Member

Choose a reason for hiding this comment

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

Maybe for next iteration we should allow people to use a custom derivation path like:

> load_ledger_cli_owners DERIVATION_PATH

question: str, number_options: int, default_option: int = 0
) -> bool:
if "PYTEST_CURRENT_TEST" in os.environ:
return 0 # Ignore confirmations when running tests
Copy link
Member

Choose a reason for hiding this comment

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

Suggested change
return 0 # Ignore confirmations when running tests
return default_option # Ignore confirmations when running tests

if "PYTEST_CURRENT_TEST" in os.environ:
return 0 # Ignore confirmations when running tests
choices = f" [0-{number_options}] default {default_option}:"
reply = str(input(question + choices)).lower().strip() or str(default_option)
Copy link
Member

Choose a reason for hiding this comment

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

Use get_input so you can easily mock the function for testing. Please add a test for this function

return 0 # Ignore confirmations when running tests
choices = f" [0-{number_options}] default {default_option}:"
reply = str(input(question + choices)).lower().strip() or str(default_option)
option = int(reply)
Copy link
Member

Choose a reason for hiding this comment

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

What happens if reply cannot be converted to a number?

"tabulate>=0.8",
],
extras_require={"ledger": ["ledgereth==0.9.0"]},
Copy link
Member

Choose a reason for hiding this comment

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

Nice

moisses89 and others added 4 commits October 30, 2023 09:39
Co-authored-by: Uxío <Uxio0@users.noreply.github.com>
Co-authored-by: Uxío <Uxio0@users.noreply.github.com>
@@ -7,25 +7,25 @@
LedgerNotFound,
)

from safe_cli.operators.safe_operator import HwDeviceException
from safe_cli.operators.exceptions import HardwareWalletException
Copy link
Member

Choose a reason for hiding this comment

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

Nice, using a exception file we prevent a posible circular dependency

@moisses89 moisses89 merged commit 319991a into master Oct 30, 2023
13 checks passed
@moisses89 moisses89 deleted the add_ledger_owner branch October 30, 2023 10:03
@github-actions github-actions bot locked and limited conversation to collaborators Oct 30, 2023
@JagoFigueroa
Copy link

Hola team! Small detail, the command available on the readme for installing ledger support is not the correct one, should be:

pip install '.[ledger]'

Cheers!

@Uxio0
Copy link
Member

Uxio0 commented Oct 30, 2023

Hola team! Small detail, the command available on the readme for installing ledger support is not the correct one, should be:

pip install '.[ledger]'

Thanks, but that command is only for local development and using the last version. On the README we only have the command to use the last official release 😉

@JagoFigueroa
Copy link

Checking delegation! I see that in order to add or remove a delegate to a safe we need to be on tx-service mode and those commands look to be executed directly (something not possible to do from a ledger at this point).

tx-service > 0x6D04edC44F7C88faa670683036edC2F6FC10b86e > show_cli_owners
Account 0x454a478d2482C1d251F149424053d4485aDD3dC5 loaded
Not default sender set 
tx-service > 0x6D04edC44F7C88faa670683036edC2F6FC10b86e > add_delegate 0x357742b4799b3481dDbed8203CA06bFbe9Ca056E test 0x454
a478d2482C1d251F149424053d4485aDD3dC5
Account 0x454a478d2482C1d251F149424053d4485aDD3dC5 is not loaded
tx-service > 0x6D04edC44F7C88faa670683036edC2F6FC10b86e > 

Here is me trying to do so from a ladger. My guess is that it fails as expected but maybe it is worth it to create a separate improvement to change that owner not loaded message as that is not the case for something referencing that it is not possible to add / remove delegates from a ledger?

Account 0x454a478d2482C1d251F149424053d4485aDD3dC5 is not loaded

(or something more generic for when we implement trezor too).

Cheers!

@JagoFigueroa
Copy link

Other than that Ledger is working nicely for me on the CLI 😄

@moisses89
Copy link
Member Author

@JagoFigueroa thanks for your review :)
As the delegates issue that you mentioned is not something critical I created a separate task to implement it. #290

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.

Support Ledger for signing
5 participants