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

Ink 4.4.0 doesn't wait for user input from stdin on second mount #625

Open
threepointone opened this issue Sep 8, 2023 · 15 comments
Open
Labels

Comments

@threepointone
Copy link

Hiya! Looks like this commit #616 broke something with input handling in 4.4.0. I managed to make a reproduction here https://github.com/threepointone/ink-repro. By running it, you'll see that hitting enter once will log the next message, but quit immediately after (with exit code 0).

With 4.3.1, it'll wait for 3 presses, as expected.

@vadimdemedes
Copy link
Owner

Thanks for the exemplary bug report, Sunil!

I traced the issue down to https://github.com/vadimdemedes/ink/pull/616/files#diff-86963609bec6fda3d34233676d5ae33f6aa4b9bbe2758a10cd4863b704b37093R178, which gets called during unmount(). The way I understand it, is it basically tells Node.js "I don't need data from process.stdin anymore, feel free to quit if there's no I/O happening".

I verified this by adding a process.stdin.ref() (the opposite of unref()) after the first waitForPress() in your reproduction → https://github.com/threepointone/ink-repro/blob/main/src/index.tsx#L27.

@matteodepalo Do we have to unref() the process.stdin in Ink? Can we remove it?

@vadimdemedes vadimdemedes changed the title bug: 4.4.0 exits early after input Ink 4.4.0 doesn't wait for user input from stdin on second mount Sep 9, 2023
@vadimdemedes
Copy link
Owner

@matteodepalo Just saw your PR (#622), thanks for the fix! Could you elaborate why we need to unref() in the first place? I'm wondering if it's going to have other side effects, in case other code outside of Ink depends on process.stdin data.

@vadimdemedes
Copy link
Owner

@threepointone Just published a 4.4.1 with @matteodepalo's fix while we're figuring this stuff out.

@threepointone
Copy link
Author

Amazing thank you! I’ll try this later when I’m at my laptop. Thanks for the quick turnaround!

@threepointone
Copy link
Author

4.4.1 appears to have fixed my specific issue, thank you!

@threepointone
Copy link
Author

Looks like it broke ink-testing-library tests for components that use useInput, I put up a PR with a fix vadimdemedes/ink-testing-library#23

@matteodepalo
Copy link
Contributor

matteodepalo commented Sep 11, 2023

Could you elaborate why we need to unref() in the first place? I'm wondering if it's going to have other side effects, in case other code outside of Ink depends on process.stdin data.

Basically, without unref() all the useInput tests would timeout because the node process wasn't allowed to exit. This is because adding any event listener will keep the process open, even if you call .off. This wasn't just in tests, our CLI commands wouldn't end "naturally" after everything was processed.

Before we had pause which would accomplish the same goal as unref, but had other issues, especially in Windows, and was outdated.

Thank you so much for merging!

@vadimdemedes
Copy link
Owner

I think #616 has actually been a breaking change and should've been released in a major version bump. It looks like it broke user-land code in several places, which shouldn't happen in a minor version bump (this issue, vadimdemedes/ink-testing-library#23, #627).

The best course of action seems to be to release a patch release with reverted readable change in #616 and then release a major version with that code included again.

What do you think?

@matteodepalo
Copy link
Contributor

To me that change isn't breaking code that uses the ink library itself because it changes the way an internal event is managed. The breaking change in ink-testing-library is because the Stdin class emits a data event manually, but I don't think that is part of the public API. If you stick to what is documented in the readme then you shouldn't get any breaking changes.

If you don't think that's enough then yes I agree that we should revert the change in a patch and ship the readable work as part of version 5.

@vadimdemedes
Copy link
Owner

That's a good point. Although I was thinking that useStdin users might see this as a breaking change, since stdin would emit data events.

@ohana54 submitted #627 too. @ohana54 could you clarify whether your own code started to break or just ink-testing-library?

@matteodepalo
Copy link
Contributor

Although I was thinking that useStdin users might see this as a breaking change, since stdin would emit data events.

Yeah I understand this. It mostly depends on what you consider to be public and private APIs. data events are not documented so I assumed it could be treated as private.

@matteodepalo
Copy link
Contributor

matteodepalo commented Sep 13, 2023

Also, according to the docs the data event will still be emitted when we call stream.read(), so anyone subscribing to that event won't have any breaking change. The problem in ink-testing-library was the other way around, we needed to trigger the useInput callback and the only way to do that is to emit the readable event.

@threepointone
Copy link
Author

Should I send a PR to ink-testing-lbrary that brings back emit('data',...?

@ohana54
Copy link

ohana54 commented Sep 13, 2023

It broke our tests when we tried to upgrade (we use the testing library for our low level components).
I went now and manually tested one of our product flows, user input works fine AFAICT.

@dmmulroy
Copy link

Any updates on this - anytime I try to use an Ink component that requires user input the app immediately closes

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

No branches or pull requests

5 participants