-
Notifications
You must be signed in to change notification settings - Fork 995
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
Yargs async #1453
Yargs async #1453
Conversation
@mleguen I'm excited about this work ... it represents a big change to yargs that I didn't expect to have the time to really ever dig into and take on. It's my goal to set aside a few hours to open-source on Saturday this week, to really dive in and understand this work and your underlying proposal. One thought, it might be interesting to make an effort to update |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@mleguen this is incredible work; I especially appreciate how in #1452 you document the entire effected API surface.
This API is most likely the future of yargs ... but, I think it might be too disruptive for the next few major versions. Especially since, I think we're in a position where we could use a few stability releases with the parser.
Here's an idea I have, what if we modularize yargs a little bit more, so that there's a ton of shared code, and release a library called yargsa
(yargs 'eh). This library would:
- expose the async API surface you've drafted in this PR.
- be more restrictive with the version of Node.js it supports:
- top-level await is landing soon, and this would make the async yargs API surface much more elegant, I think we should pin to the first Node.js version to introduce this.
- I'd like us to switch to my c8 project for coverage, which becomes much more stable in Node 12+.
- It would let us start growing a sub-community of folks playing and testing the async API surface (allowing us to address bugs).
We could link to the async version in the yargs README, and as the community gradually grows, eventually merge the two projects?
What do you think?
@bcoe Don't worry: updating docs is in my TODO list, and may be in my mind the most important part of this work... |
@bcoe Regarding your suggestion of yargsa:
|
@bcoe I do not see however how we could benefit from top level await, as we have no dynamic initializing in Yargs. We would export an async API, but we would export it statically, so there would be no need for us to use top level await. EDIT: could you detail a use case for top level await in some of yargs module? |
@bcoe about c8: If I understand well, this is a replacement for nyc, using builtin node functionality? This looks exciting! However, the drawback would be the need for node v12, meaning we would have to support both yargs and yargsa at least for 18 months (until node v10 is out of maintenance). Would we have enough time for that? EDIT: I see that your already switched yargs to c8, testing only coverage for node v13, which makes sense as we do not need to test coverage for all versions we support (this is only a dev indicator). So ignore my "drawback" above). |
@mleguen I'm empathetic to the drawbacks of having an async version of yargs in conjunction with a sync version, however, some of the biggest users of yargs require that its behavior is sync ( And I think that the disruption to the existing community is (at this time) not worth the benefit we'd get from an async API. As you've mentioned yourself, the async features we have are a bit odd, and not super compelling:
However, as we Node.js/JavaScript continues to evolve, and we get top-level await, async-iterators, and other delightful abstractions for async code, I think that there will start to be a reasonable case for yargs being async. I don't think it would be worth making this jump for the next few majors though, and we'd provide more value to the community continuing to address some of the backlog of bugs, oddities, etc. This makes me think if we'd like to start experimenting with an async API, it would at least be worth considering floating two versions of yargs at once. |
57af615
to
a039f20
Compare
@mleguen I've created https://github.com/yargs/yargsa, which you are a maintainer of, I've also published https://www.npmjs.com/package/yargsa (as a placeholder for our work). I'd like to advocate that we pull together an async version of yargs in this repo, I think it would be a great opportunity to play with:
Let's use this as a playground to flesh out the version of yargs we'd like to see in the future. |
@bcoe Thank you! And Wow! for your hard work of the two past weeks on yargs!
Why not switching to typescript?
At the moment, Yargs is the only project I am still developping in plain JS |
4 broken tests are skipped, to be fixed in following commits
…s async Allows 3 of the 4 broken tests to be OK back
The last broken test in completion is back online
1 skipped broken test, to be fixed in following commits
Bring the broken test in middeware back online
25 broken tests, to be fixed in following commits
Fix 25 broken tests expecting parse() to return a result after calling process.exit, which was only a side effect of old checkUsage() not to occur in real life
It is more readable to explicitely write that a rejection is expected instead of ignoring the rejection when it occurs. Moreover, the corresponding tests now fail when there is no rejection, which is what is expected.
To keep the current behavior (not calling parseFn when _parseArgs throws)
done() is called before should.be.rejected (and not sould) is evaluated. Moreover, it should not be rejected as there is no rejection when there is a fail callback
2 broken tests, to be fixed in following commits
Fix 1 broken test expecting parse() to return a result after calling process.exit, which was only a side effect of old checkUsage() not to occur in real life
expect.fail() should not be used in a test using a done callback: - if it covers a path which should not be reached, done(err) should be used instead - it has no use if called after done(): not calling done is enough for the test not to be successful Bring the last broken test for validation back online.
2 broken tests, to be fixed in following commits
No longer needed.
to align its async behavior with completion function
The test did not really tested the handler was called, as the promise was already created beforeHand. Moreover, now also tests the handler completes before await parse() returns.
bbcbbb4
to
f837e57
Compare
To align its async behavior with completion and builder functions.
f837e57
to
43122d0
Compare
To align its async behavior with other async allowed callbacks.
I also aligned the async behavior of all async allowed callbacks (command builder and handlers, middlewares and completion function). They can now all be:
|
@bcoe @cspotcode, @petrgrishin, @Goodluckhf ready for review |
@cspotcode @mleguen I'm open to TypeScript. |
All async callbacks (command builders and handlers, middlewares and completion functions) can now either return a promise or call a standard js (err, value) callback. Corresponding tests reviewed and added when missing.
f05b123
to
155a5d9
Compare
1 test is broken as a global middleware failure leads to fail being called if the middleware runs after validation, not before, which is incoherent and should be fixed
@cspotcode @mleguen would you be open to closing this PR, and moving the pertinent conversation we've had to a conversation on yargsa? |
Yeah, works for me.
…On Fri, Nov 15, 2019, 3:14 PM Benjamin E. Coe ***@***.***> wrote:
@cspotcode <https://github.com/cspotcode> @mleguen
<https://github.com/mleguen> would you be open to closing this PR, and
moving the pertinent conversation we've had to a conversation on yargsa?
—
You are receiving this because you were mentioned.
Reply to this email directly, view it on GitHub
<#1453?email_source=notifications&email_token=AAC35ODKBJTQU4HMLU2527DQT37IZA5CNFSM4JBNJN22YY3PNVWWK3TUL52HS4DFVREXG43VMVBW63LNMVXHJKTDN5WW2ZLOORPWSZGOEEGSWZI#issuecomment-554511205>,
or unsubscribe
<https://github.com/notifications/unsubscribe-auth/AAC35ODF3CUQCVEDA4ZB7HDQT37IZANCNFSM4JBNJN2Q>
.
|
Conversation moved here: https://github.com/yargs/yargsa/issues/4 @mleguen do you think you'd be open to making an attempt at PR on if you, @cspotcode, and others have the will and the cycles, we could also try an approach that's slightly more from the ground up. |
yargs/yargsa repository does not seem to be public, Github returns 404 for me. |
Did anything else happen with yargsa? |
If I recall correctly, nothing much happened with yargsa. If I recall correctly, there was disagreement on the name of a function in the API surface, and the code being JS instead of TS was making it unnecessarily time-consuming to reason about any refactors. Someone was working on porting yargs to TS, which seems to be mostly complete. They said they no longer have time to lead that effort. I'm not sure what still remains to be done. |
Do you know if that PR or branch still exists somewhere? I'd be happy to contribute to it Edit: Ah, I'm guessing this is probably the one: #1586 |
Yeah, I guess that's it. Seems like steps 5-9 are pretty straightforward. @types/yargs should already have tests which can be used to verify the bundled declarations. Contributions to @types get merged within a week, so that can happen quickly. I don't know if any work has been done converting yargs-parser to TS. I wonder what ts-migrate would do with it? |
See yargs/yargsa#4