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

to_stream and nonblocking sockets #723

Open
carlhoerberg opened this issue Nov 24, 2021 · 7 comments
Open

to_stream and nonblocking sockets #723

carlhoerberg opened this issue Nov 24, 2021 · 7 comments

Comments

@carlhoerberg
Copy link

carlhoerberg commented Nov 24, 2021

Since Ruby 3.0 sockets are by default nonblocking, which causes issues for Oj.to_stream here

require "oj"
require "socket"
require 'io/nonblock'
pid = spawn("nc -d 0.1 -l 5000", out: "/dev/null")
at_exit { Process.kill 9, pid }
sleep 0.1
s = Socket.tcp("localhost", 5000)
# s.nonblock = false
1_000_000.times do
  Oj.to_stream(s, { a: 1 })
end

output:

n.rb:10:in `to_stream': Write failed. [11:Resource temporarily unavailable] (IOError)
        from n.rb:10:in `block in <main>'
        from n.rb:9:in `times'
        from n.rb:9:in `<main>'

set s.nonblock = false and it works as expected..

Not sure if something should be done in Oj, but could be good for ppl to be aware.. It's not very ergonomic to catch the generic IOError and then trying to figure out if it's a EAGAIN error and manually do IO.select.

@carlhoerberg
Copy link
Author

Maybe use pwritev2 with the RWF_SYNC flag, but that's Linux only.. https://man7.org/linux/man-pages/man2/pwritev2.2.html

@ohler55
Copy link
Owner

ohler55 commented Dec 18, 2021

I'm hesitant to make that the default but it would be a nice option for Oj.to_stream. What do you think?

@ohler55
Copy link
Owner

ohler55 commented Dec 28, 2021

Looking at this again. I think I misunderstood the desired changes. I don't think Oj should set the stream to non blocking but I do think Oj could handle EAGAIN errors along with some timeout value. I'm looking into that now.

@ohler55
Copy link
Owner

ohler55 commented Jan 3, 2022

Please try branch "non-blocking". Test added as well although I found the issue is exposed more readily with a large single write instead of many smaller ones and the test reflects that.

@ohler55
Copy link
Owner

ohler55 commented Jan 4, 2022

I believe the non-blocking branch fixes the issue. I plan to release tomorrow barring feedback from you indicating it is not fixed.

@ohler55
Copy link
Owner

ohler55 commented Jan 22, 2022

Okay to close?

@Watson1978 Watson1978 pinned this issue Jan 23, 2022
@Watson1978 Watson1978 unpinned this issue Jan 23, 2022
@carlhoerberg
Copy link
Author

carlhoerberg commented Jan 26, 2022

is the patch included in oj 3.13.11? The example in the original issue still fails with it

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

No branches or pull requests

2 participants