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鈥檒l occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: extending with rustup components and external subcommands #31

Open
wants to merge 8 commits into
base: master
Choose a base branch
from

Conversation

somehowchris
Copy link

@somehowchris somehowchris commented Apr 16, 2022

Definitely not finished, but just wanna show my intent and get some feedback on the way.

Followup (16.4.2022):

It's kind of a big PR 馃槄 but it's not all new code.

General approaches:

  • Reduce endless referencing, copying and cloning using an OO approach
  • Use rayon for most iteration, where ever possible
  • Split the components into 2 parts as it should be from my point of view. The business logic aka "the backend" and the cli aka "the frontend"
  • Use serde to delegate anything about parsing (mentioned once in Support chunking聽#28 by @Manishearth)
  • Decouple validation from parsing using validator
  • Create a typed interface for Errors instead of dyn Error
  • Use clap for anything related to the cli interation aka frontend (mentioned once in Support chunking聽#28 by @Manishearth)

Specific changes:

Breaking changes

First of all the binary would be unified as cargo all-features .... but the old subcommands would just run with the old cli logic and a small warning.

The bigger breaking change would be the layout of the flags supplied to the subcommand vs the actual command being called by this crate. (almost like this mention #4 (comment))

cargo all-features build --chunk 1 --chunks 4 --dry-run -v --no-color --target-command cross -- --target aarch64-unknown-linux-gnu

# or as more generic

cargo all-features <command> <options> -- <options-forwarded>

As you can see there is a -- separating the two parts, this wasn't the case before but clap introduces best practises. If there would be the desicion to somehow circumvent such a syntax change this would mean it is much harder not only for this crates parting strategy but also cargo itself to tell them apart and in case of cross options like --target would be ignored.

The main business logic has not been touched, but I'm still testing in the wild.

Feedback to anything is very much welcome 馃

@somehowchris somehowchris marked this pull request as draft April 16, 2022 02:53
@frewsxcv
Copy link
Owner

How difficult would it be to make these changes without adding new dependencies? Most users of this project download and compile it in CI so it's important for it to be a small binary that compiles fast.

@somehowchris
Copy link
Author

serde and serde-json: go back to manual parsing via json

validator: just create an own error and leave the validation logic basically as is (as we only validate the package currently)

rayon: just go back to singe threaded things

yansi: go back to termcolor which will introduce some boilerplante code again which takes color formatting from 1 line to at least 4

clap: manual parsing all those flags can be hard, doing the same functionality without clap would be unnecessarily hard. I imagine somewhat like 2-300 LOCs at least

lazy_staic: the map could be hidden behind a function. This would mean every time it needed this function would collect the hashmap. Lazy static would initiate that once and rust simply return for all other times

which: it is not as easy as it seems to check for installed binaries cross platform. It would be really hard to check that and since there is a crate for that....

Im not the owner not maintainer if this crate, but here are my 2 cents.

All the crates used resemble a milestone in the evolution of a language. Parsing with serde, cli this with clap, parallelism with rayon and simple output coloring with yansi. They all have their purpose to exist so we can use their abstraction to take care of business value and do not have to maintain glue and boiler plate code. I would prefer a solution as cargo binstall: build binaries in ci, add them to github releases, let the user (also ci) download the binary. It is at least as safe as cargo install as all references to bineries are set by the publisher in the Cargo.toml. Much more efficient as downloading and compiling the crate too.

if you would like to see the added stuff for cargo-Binstall, I could have a go later this week on that

@Manishearth
Copy link
Collaborator

I feel like it would be good to depend on serde and an argument parser at the least, argh is a popularish alternate argument parser with minimal deps

@Manishearth
Copy link
Collaborator

Besides, at least on GHA you can cache these installs

@somehowchris
Copy link
Author

I get the case of "compatibility" and "ease of use", but at the same time. Things like docker or podman do not get compiled form source everytime someone uses them in their cicd pipeline. Why should you compile this subcommand in ci? Thats where cargo-binstall makes the process of installing binaries easy(-er)

@frewsxcv
Copy link
Owner

I get the case of "compatibility" and "ease of use", but at the same time. Things like docker or podman do not get compiled form source everytime someone uses them in their cicd pipeline. Why should you compile this subcommand in ci? Thats where cargo-binstall makes the process of installing binaries easy(-er)

I would bet most projects in the Rust ecosystem use cargo install and are not aware of cargo bininstall. Not to mention you need to download cargo binstall before you can even use it.

So before I review this, it would be helpful to know how much longer it takes to download + compile this branch on GitHub actions, compared to main.

@somehowchris
Copy link
Author

somehowchris commented Apr 28, 2022

Well cargo-binstall can actually be downloaded from binary releases and cargo-quickinstall already offers cargo-all-features as binaries.

Will do these benchmarks on Friday, @frewsxcv do you have a threshold?

@somehowchris
Copy link
Author

somehowchris commented Apr 29, 2022

So before committing to scripting I wanted to quickly check if the compile times are out of this world.

I used my gitpod instance for this, as I do not have a laptop or pc.

Build times:
frewsxcv:master: ~10 sec
somehowchris:master: ~30 sec
somehowchris:master without validator: ~20 sec

Yes, I quickly checked with cargo install --timings and validator and its subsequent dependencies needed about 10 secs to build. As said validator does bascially 0 with this setup besides a nice codegen, so I removed it.

Couldn't find much more optimizations to reduce build time. But I feel like the other depdencies are worth the 10 secs added considering all the stuff this crate doesn't have to fear about.

As said, this was just a quick check, these aren't github actions build times, will do them next

.collect();

println!(
"{}: the command `cargo {}` may be deprecated, please use `cargo all-features build`",
Copy link
Owner

Choose a reason for hiding this comment

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

Suggested change
"{}: the command `cargo {}` may be deprecated, please use `cargo all-features build`",
"{}: the command `cargo {}` is deprecated, please use `cargo all-features build`",

README.md Outdated
- name: Install cargo-all-features
uses: actions-rs/cargo@v1
with:
command: install cargo-all-features
Copy link
Owner

Choose a reason for hiding this comment

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

I wonder if we should suggest passing the argument that specifies a version to install. That could make it easier to introduce breaking changes in the future 馃

Copy link
Author

Choose a reason for hiding this comment

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

I'm a fan of the idea, but I do not really think many users will manually change the version inside the commands input as this would not be covered by something like dependabot.

One suggestion would be create a gh action for cargo-all-features itself, this could mean a 1:1 mapping between gh-action version and crate version which then could be updated using dependabot.

@somehowchris
Copy link
Author

im so so sorry, thought could do some stuff between final exams but they hit real hard. Will do things this comming weekend

@TimDiekmann
Copy link

This is great! Do you plan to also add clippy?

@somehowchris
Copy link
Author

somehowchris commented Jul 2, 2022

@TimDiekmann added it

@frewsxcv implemented your suggestions

Also, did some installs for all major platforms over at https://github.com/somehowchris/cargo-all-features-install-testing/actions/runs/2601011045

Results are similar for all platforms for gh actions, adding about 30-50 seconds

@somehowchris
Copy link
Author

somehowchris commented Jul 2, 2022

The last commit added cargo-binstall metadata and automated builds for gh release binaries.

IMO for ci usage, having binaries is a nice thing as to not having to rebuild it every time (cost and efficiency). Also the binaries are install procedure agnostic, so you could also curl and run them, cargo binstall is just a lovely cargo tooling

README.md Outdated
- [`cargo miri test`](https://github.com/rust-lang/miri) for testing using miri -> _rustup component `miri` is needed_
- Cargo plugins
- [`cargo udeps`](https://github.com/est31/cargo-udeps) to analyze for unused dependencies -> _cargo plugin `cargo-udeps` is needed_
- [`cargo tarpaulin`](https://github.com/xd009642/tarpaulin) to analyze for unused dependencies -> _cargo plugin `cargo-tarpaulin` is needed_
Copy link

Choose a reason for hiding this comment

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

tarpaulin is a code coverage reporting tool, and seems like not a unused dependencies analyzer:

Tarpaulin is a code coverage reporting tool for the Cargo build system, named for a waterproof cloth used to cover cargo on a ship. Currently, tarpaulin provides working line coverage and while fairly reliable may still contain minor inaccuracies in the results. A lot of work has been done to get it working on a wide range of projects, but often unique combinations of packages and build features can cause issues so please report anything you find that's wrong. Also, check out our roadmap for planned features.

Copy link
Author

Choose a reason for hiding this comment

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

Sry, yes totally missed that copy paste error, thanks

@pan93412
Copy link

pan93412 commented Aug 3, 2022

image

Besides, I can't pass chunks arguments even if the argument is valid 馃槩 Seems like this syntax is not supported by clap.

@somehowchris
Copy link
Author

somehowchris commented Aug 3, 2022

how about cargo all-features nextest --chunks 6 --chunk 1? Would make more sense as flags are set after the sub-command.

nvm, my bad. clap seems to get and compare what the possible values provided are and tries to compare them. wasn't like that when I originally rewrote that. just removed the possible values part

@frengor
Copy link

frengor commented Jul 29, 2023

What's the state of this? I'm really looking forward to using cargo-all-features with miri in CI.

@Manishearth
Copy link
Collaborator

Chunking and clap are in #47 and will get merged once I get a review.

I think what should be done here is splitting this into a lot of smaller changes, like all of the refactorings and some of the QoL improvements, and landing those first before adding tons to the CLI.

@rohel01
Copy link

rohel01 commented Aug 1, 2023

Also really interested in using clippy and nextest with this crate!

@somehowchris Do you need help?

@somehowchris
Copy link
Author

somehowchris commented Feb 5, 2024

didn't receive any words from @frewsxcv, saw some things being integrated but personally moved away from this as I didn't hear anything. is there a need to create a new PR with some of the this from this PR or should it be considered as failed and therefore closed?

I personally still believe that many of the issues would be fixed with the changes in this PR

@Manishearth
Copy link
Collaborator

It would be nice to split this into smaller things to make it more easily reviewed if possible.

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

7 participants