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 foundation & initial implementation for a full-blown wallet CLI #133

Merged
merged 7 commits into from
Apr 3, 2019

Conversation

jonathanknowles
Copy link
Member

Experimental!

Issue Number

#96

Overview

Add beginnings of a docopt-based CLI for the Wallet.


Usage:
cardano-wallet address list --wallet-id=UUID
cardano-wallet wallet create --name=STRING --mnemonic-sentence=STRING --passphrase=STRING [--address-pool-gap=INT] [--mnemonic-second-factor=STRING]
Copy link
Member

Choose a reason for hiding this comment

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

The mnemonics will have to be prompted 😶 These are sensitive pieces of info we do not want in the bash history 😅

Copy link
Member Author

Choose a reason for hiding this comment

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

The mnemonics will have to be prompted no_mouth These are sensitive pieces of info we do not want in the bash history sweat_smile

That's a really good point. I'm happy to add this. Is there any particular approach you would prefer for reading the mnemonics in?

Copy link
Member

@KtorZ KtorZ Mar 29, 2019

Choose a reason for hiding this comment

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

Just a plain shell prompt, doesn't necessarily have to be hidden (because it may become very tricky to type-in 24 words if you can see shit 😂 )
But clearing the prompt once done.

$ Please enter your 12-to-24-word mnemonics: ...

|
|
v

$ Please enter your 12-to-24-word mnemonics: patate patate patate patate

|
|
v

hits enter

|
|
v

Please enter your 12-to-24 word mnemonics: ****
Thank you, now we've got all your ADA in a safe place

Copy link
Member Author

@jonathanknowles jonathanknowles Apr 3, 2019

Choose a reason for hiding this comment

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

The mnemonics will have to be prompted 😶
These are sensitive pieces of info we do not want in the bash history 😅
But clearing the prompt once done.

@KtorZ I've now implemented a basic version of the above. It's still a bit rough at the edges (in particular, with the reporting of errors), but clearing the prompt does work.

One issue that I ran into when clearing data from a terminal screen is that it's not always possible to determine the original position of the cursor. If we're not careful, we run the risk of not clearing all the sensitive data from the display.

Therefore, if the system on which the CLI is running is not able to provide this info, I've opted to clear the entire screen after the user has finished entering their data.

{-# LANGUAGE DuplicateRecordFields #-}
{-# LANGUAGE QuasiQuotes #-}

module Main where
Copy link
Member

Choose a reason for hiding this comment

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

Side-note but this cli and cardano-wallet-server are one and one thing. We do want to have them merged together in the end, so that there's one CLI to spawn the server, and the same one to interact with it 👍

Copy link
Member Author

Choose a reason for hiding this comment

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

Side-note but this cli and cardano-wallet-server are one and one thing. We do want to have them merged together in the end, so that there's one CLI to spawn the server, and the same one to interact with it +1

Understood! In that case, are you expecting something like this:

cardano-wallet server start ...
cardano-wallet wallet create --name wibble ...
cardano-wallet wallet list

Copy link
Member

Choose a reason for hiding this comment

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

Sounds reasonable to me :)


-- | Indicates an error that occurred while decoding from text.
newtype TextDecodingError = TextDecodingError
{ getTextDecodingError :: String }
Copy link
Member

Choose a reason for hiding this comment

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

Not sure what's the value of the newtype here. I'd simply go for a string to be honest. It adds value when we have multiple ones, one per actual type (albeit having a raw string isn't really the best option). But since it has now become a common abstraction, a String has pretty much the same value as the newtype here.

Copy link
Member Author

Choose a reason for hiding this comment

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

I think there is some value in having a newtype here.

  1. The descriptive name of the type TextDecodingError is self-commenting. When I see this type in the wild somewhere, I don't need to think very hard to know that it's an error relating to the decoding of text, and not some random string that happens to have been inserted into the left-hand-side of an Either.

  2. If I see TextDecodingError in the wild, in a place outside of the Api.Types module, then I have a direct way to look up its definition, at which point I can see the extended comment.

  3. If I were to try refactor TextDecodingError in some way, then I might get better compiler feedback than if it were just a naked String.

What do you think? Of course, if you think the arguments I've presented have no basis, then we can remove it.

(Note that I've now created a separate PR for the textual encoding work: #142.)

, encodeApiWalletName
, ToText (..)
, FromText (..)
, TextDecodingError (..)
Copy link
Member

Choose a reason for hiding this comment

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

The overall looks clean and re-usable. Nice work!
(one reserve about the TextDecodingError)

Copy link
Member Author

Choose a reason for hiding this comment

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

Thanks! I've moved the textual encoding work into a separate PR: #142.

I'll keep this PR for the docopt CLI-specific work.

Copy link
Member

@KtorZ KtorZ left a comment

Choose a reason for hiding this comment

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

Reviewed & Wrapped up.
I'll add a few more tests and merge it.

@KtorZ KtorZ marked this pull request as ready for review April 3, 2019 16:49
@KtorZ KtorZ force-pushed the jonathanknowles/cli-docopt branch from 8114af7 to 8b8dbfe Compare April 3, 2019 16:59
@KtorZ KtorZ changed the title [wip] Add beginnings of docopt-based CLI for the Wallet. Add foundation & initial implementation for a full-blown wallet CLI Apr 3, 2019
@KtorZ KtorZ merged commit efde04f into master Apr 3, 2019
@KtorZ KtorZ deleted the jonathanknowles/cli-docopt branch April 3, 2019 17:23
-- The terminal lines containing the data are also cleared if the application
-- exits abnormally, before the user has finished entering data.
--
getLineWithSensitiveData :: IO Text
Copy link
Contributor

Choose a reason for hiding this comment

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

alternitavelly we could even hide user input from the screen (similar like sudo does).

The cons of hiding the user input is that user is unable to check/verify/easily-correct entered mnemonic or password.

Some CLI application approach the problem of requesting the same input data to be done twice in order to confirm that user didn't make a mistake:

Passphrase: ********
Retype passphrase: ********

user experience is lower with this model but users are now able to enter their their mnemonics or passphrases in public spaces.

Mnemonics are pretty long (15+ words) and passphrase as well (10+ chars) so there is a high chance of mistake. That's also the case not to implement what I am proposing.

I guess CLI will most likely be used by someone already more technically advanced - so there is a higher chance that person already is aware that mnemonic and passphrase is something he should hide and not reveal (ie, type in public place).

Conclusion is that I think this is ok solution but maybe we should keep in mind and research alternatives.

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.

None yet

3 participants