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

Feature/init option #243

Merged
merged 6 commits into from
Sep 8, 2017
Merged

Feature/init option #243

merged 6 commits into from
Sep 8, 2017

Conversation

rigelrozanski
Copy link
Contributor

Closes #241
The approach was to parse the option flag right into the genesis file as it gets created, the rest of the process train is still the same. Multiple --option flags can be used consecutively and it will work. The one problem that seemed to be a huge headache to resolve is to add more complex options that require JSON (such as the existing value to the option coin/issuer) This has to do with some the annoying ways which glide likes to parse information, I tried to come up with a solution but it seemed like to much effort for what it's worth... so for the time being this these options only accept non-json strings for the option value.

var optionsStr string
sep := ",\n "
optionsRaw := viper.GetStringSlice(FlagOption)
if len(optionsRaw) > 0 {
Copy link
Contributor

Choose a reason for hiding this comment

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

How about pulling out the logic into its own function so that we can write a unit test against it. This applies to L70 - L85.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Originally, I had thought to unit test the way which you have described, but I kind of figured it should be tested like the rest of our commands as a part of the bash testing... (which has been done checkout init-server.sh). Additionally, the results are more relevant in the context of the genesis file as opposed to just a lone string to add in... Anyways, we can do it, not sure if it makes sense since we have bash test

Copy link
Contributor

Choose a reason for hiding this comment

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

I agree with Rigel, this cli parsing stuff is covered by the bash tests. Ugly but there is not really a better way.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

okay leaving

sep := ",\n "
optionsRaw := viper.GetStringSlice(FlagOption)
if len(optionsRaw) > 0 {
optionsStr = sep
Copy link
Contributor

Choose a reason for hiding this comment

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

Do we need this assignment?

How about:

sed += strings.Join(option[:], sed)

Maybe we should rename sed then :-)

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Are you referring to L75? yes we need that because only if options are set to we want to include a (comma and new line) seperator

Copy link
Contributor

@ethanfrey ethanfrey left a comment

Choose a reason for hiding this comment

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

Look good, some minor additions, but the biggest issue is not being able to enter json as you mentioned:

 basecoin init $ADDR --option mod/key/val --option 'coin/dings/{"name": "joe"}'
ERROR: invalid argument "coin/dings/{\"name\": \"joe\"}" for "--option" flag: line 1, column 12: bare " in non-quoted-field

Either we need to fix that, or we need to find a way to parse stuff out, so I could use the role:xyz format and the init function would convert it into a json represention of a basecoin actor (which requires init to understand all the formats), or we change the SetInitState() methods to accept non-json data. (eg. the text represenation of basecoin actor or coins or whatever).

var optionsStr string
sep := ",\n "
optionsRaw := viper.GetStringSlice(FlagOption)
if len(optionsRaw) > 0 {
Copy link
Contributor

Choose a reason for hiding this comment

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

I agree with Rigel, this cli parsing stuff is covered by the bash tests. Ugly but there is not really a better way.

options = append(options, option)
}
}
optionsStr += strings.Join(options[:], sep)
Copy link
Contributor

Choose a reason for hiding this comment

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

s/+=/=/ since it just defaults to the empty string above and put this into the if statement

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Moved to the if statement, replaced += ... with = sep + ...

@@ -64,7 +67,24 @@ func initCmd(cmd *cobra.Command, args []string) error {
return errors.New("Address must be 20-bytes in hex")
}

genesis := GetGenesisJSON(viper.GetString(FlagChainID), userAddr)
var options []string
Copy link
Contributor

Choose a reason for hiding this comment

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

options and sep can be moved into the if statement as we only need them if options flags are provided.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

👍 addressed

CLIENT_EXE=basecli
SERVER_EXE=basecoin

test01initOption() {
Copy link
Contributor

Choose a reason for hiding this comment

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

nice test that it writes the values. however, it would be good to make sure it started up and could parse this file.
i guess at least using jq to check the genesis file ensures it is proper json, but still, maybe just start the basecoin server and make sure it doesn't return an error.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

added

@ethanfrey
Copy link
Contributor

Looking into the parse error. It comes from this code in pflag:

func readAsCSV(val string) ([]string, error) {
        if val == "" {
                return []string{}, nil
        }
        stringReader := strings.NewReader(val)
        csvReader := csv.NewReader(stringReader)
        return csvReader.Read()
}

Which is based on the csv lib:

https://golang.org/src/encoding/csv/reader.go#L397

Not sure how to fake the csv data properly...

@ethanfrey
Copy link
Contributor

Okay, reading through the csv parsing code, I determined that if want quotes inside, then the whole field needs to be in quotes, and you must use two consequtive quotes to denote one quote inside...

basecoin init $ADDR --option mod/key/val --option '"coin/dings/{""name"": ""joe""}"'

produces:

   "plugin_options": [
      "coin/issuer", {"app": "sigs", "addr": "1234567890deadbeefaa1234567890deadbeefaa"},
      "mod/key", "val",
      "coin/dings", "{"name": "joe"}"
    ]

which is almost what we want, even if the cli is a bit ugly. one important issue is we note the json is surrounded by quotes on the last line (false), while there are no quotes on the top line (correct).

Want to take another stab at this @rigelrozanski ?
I don't mind having to deal with quotes like that in the cli if it is documented. But maybe others do. And in any case, the output must be cleaner.

One option is to implement our own flag type that does this better than string slice, look at:

https://github.com/spf13/pflag/blob/master/string_slice.go#L122
https://github.com/spf13/pflag/blob/master/string_slice.go#L10-L63

@zramsay
Copy link
Contributor

zramsay commented Sep 4, 2017

I don't mind having to deal with quotes like that in the cli if it is documented. But maybe others do.

Yeah, I'm not a fan. Even if documented, there's a cognitive overheard of having to do that parsing...reducing simplicity. Can we use a simple config file instead of multiple --option flags?

@rigelrozanski
Copy link
Contributor Author

@zramsay you can already just modify the genesis config file... This is really just an added bonus for extra app functionality at startup. The main intention was to be able to use the SDK library functionality without needing to write your own genesis specifications if you didn't want too, which I don't haha. BUT yes, ultimately one can also program a custom init function which takes custom app-specific flags which are parsed specifically for your apps requirements. App-options as far as I can see are pretty much always optional anyways on top of that.

Copy link
Contributor

@ethanfrey ethanfrey left a comment

Choose a reason for hiding this comment

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

Okay, seems a fair fix.

Can you add a test case in bash for this?
With and without json.

@rigelrozanski
Copy link
Contributor Author

All changes addressed. Let me know if anything else needs updating

Copy link
Contributor

@ethanfrey ethanfrey left a comment

Choose a reason for hiding this comment

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

LGTM. Let's see how they work in practice, and maybe revisit this options idea later if we want to change the format. Only experience will tell.

@ethanfrey ethanfrey merged commit 83c460a into develop Sep 8, 2017
@ethanfrey ethanfrey deleted the feature/init-option branch September 8, 2017 18:45
sosedoff referenced this pull request in figment-networks/cosmos-sdk Jun 4, 2022
Closes: #XXX

## What is the purpose of the change

Backporting and expanding on: cosmos#11182

This is an attempt to fix app version bug related to state-sync and tendermit. More context is in the linked-above PR.

Upon backporting all relevant commits from the linked-above PR, it was discovered that some integration and simulation tests were failing. With the original design, it was difficult to find the source of the problem due to storing the protocol version in 2 database locations. Therefore, the original work was significantly redesigned to only keep the protocol version in param store.

Additionally, the protocol version was assumed to have already been set. Since we are creating a new entry in the database, it is now possible that the protocol version is non-existent at the start. As a result, mechanisms for detecting a missing protocol version were added:
- `baseapp.init(...)`
   * This is called on every restart. Here, we check if the protocol version is already in db. If not, set it to 0
- `baseapp.InitChain(...)`
   * This is called once at genesis. Here, we always set protocol version to 0

Then, on every upgrade the version gets incremented by 1

## Brief Changelog

- cherry-picked all relevant commits from cosmos#11182
- fixed some issues
- addressed some style comments from code review in cosmos#11182
- redesigned to only store protocol version in params store and removed logic for storing it in the upgrade keeper
- added logic for detecting missing protocol version and, if missing, setting it to 0
- unit and integration tested
- fixed all tests

## Testing and Verifying

This change is a trivial rework / code cleanup without any test coverage.

This change is already covered by existing tests, such as *(please describe tests)*.

TODO: This change needs to be manually tested

## Documentation and Release Note

  - Does this pull request introduce a new feature or user-facing behavior changes? yes
  - Is a relevant changelog entry added to the `Unreleased` section in `CHANGELOG.md`? no
  - How is the feature or change documented? not applicable

(cherry picked from commit a68d28e)

Co-authored-by: Roman <[email protected]>
rootulp referenced this pull request in rootulp/cosmos-sdk Aug 15, 2022
…lease

chore: create a v0.46.0 release branch with celestia specific changes
yihuang added a commit to yihuang/cosmos-sdk that referenced this pull request Apr 1, 2024
* Support RunAtomic API

* add unit test
dudong2 pushed a commit to b-harvest/cosmos-sdk that referenced this pull request Oct 17, 2024
dudong2 pushed a commit to b-harvest/cosmos-sdk that referenced this pull request Oct 17, 2024
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.

Genesis options flag for init
4 participants