EOFError: ถึงจุดสิ้นสุดของไฟล์ถึงปัญหากับ Net :: HTTP


158

ฉันใช้ ruby-1.8.7-p302 / Rails 2.3.11 ฉันกำลังพยายามใช้ FQL (Facebook API) เพื่อรับสถิติสำหรับลิงก์ นี่คือรหัสของฉัน:

def stats(fb_post_url)
  url = BASE_URI + "?query=#{URI.encode("select like_count from link_stat where url=\"#{fb_post_url}\"")}"
  parsed_url = URI.parse(url)
  http = Net::HTTP.new(parsed_url.host, parsed_url.port)
  request = Net::HTTP::Get.new(parsed_url.request_uri)

  response = http.request(request)
  response.inspect
end

และนี่คือข้อผิดพลาด:

EOFError: end of file reached
from /home/rahul/.rvm/rubies/ruby-1.8.7-p302/lib/ruby/1.8/net/protocol.rb:135:in `sysread'
from /home/rahul/.rvm/rubies/ruby-1.8.7-p302/lib/ruby/1.8/net/protocol.rb:135:in `rbuf_fill'
from /home/rahul/.rvm/rubies/ruby-1.8.7-p302/lib/ruby/1.8/timeout.rb:67:in `timeout'
from /home/rahul/.rvm/rubies/ruby-1.8.7-p302/lib/ruby/1.8/timeout.rb:101:in `timeout'
from /home/rahul/.rvm/rubies/ruby-1.8.7-p302/lib/ruby/1.8/net/protocol.rb:134:in `rbuf_fill'
from /home/rahul/.rvm/rubies/ruby-1.8.7-p302/lib/ruby/1.8/net/protocol.rb:116:in `readuntil'
from /home/rahul/.rvm/rubies/ruby-1.8.7-p302/lib/ruby/1.8/net/protocol.rb:126:in `readline'
from /home/rahul/.rvm/rubies/ruby-1.8.7-p302/lib/ruby/1.8/net/http.rb:2028:in `read_status_line'
from /home/rahul/.rvm/rubies/ruby-1.8.7-p302/lib/ruby/1.8/net/http.rb:2017:in `read_new'
from /home/rahul/.rvm/rubies/ruby-1.8.7-p302/lib/ruby/1.8/net/http.rb:1051:in `request'
from /home/rahul/.rvm/rubies/ruby-1.8.7-p302/lib/ruby/1.8/net/http.rb:1037:in `request'
from /home/rahul/.rvm/rubies/ruby-1.8.7-p302/lib/ruby/1.8/net/http.rb:543:in `start'
from /home/rahul/.rvm/rubies/ruby-1.8.7-p302/lib/ruby/1.8/net/http.rb:1035:in `request'
from /home/rahul/Work/Radr/lib/fb_stats.rb:13:in `stats'
from (irb):10

สิ่งนี้ดูเหมือนว่าจะเกิดขึ้นเฉพาะในกรณีของ Facebook API นอกจากนี้ฉันเห็นมันแนะนำในโพสต์นี้อาจเป็นข้อผิดพลาดใน Net :: HTTP


3
คุณพบทางออกสำหรับสิ่งนี้หรือไม่? ฉันกำลังประสบปัญหาที่คล้ายกันใน SFDC API
Nilesh

คำตอบ:


281

หาก URL ใช้ https แทน http คุณต้องเพิ่มบรรทัดต่อไปนี้:

parsed_url = URI.parse(url)
http = Net::HTTP.new(parsed_url.host, parsed_url.port)
http.use_ssl = true

http.use_ssl = trueหมายเหตุเพิ่มเติม

และรหัสที่เหมาะสมยิ่งขึ้นซึ่งจะจัดการทั้ง http และ https จะคล้ายกับรหัสต่อไปนี้

url = URI.parse(domain)
req = Net::HTTP::Post.new(url.request_uri)
req.set_form_data({'name'=>'Sur Max', 'email'=>'some@email.com'})
http = Net::HTTP.new(url.host, url.port)
http.use_ssl = (url.scheme == "https")
response = http.request(req)

ดูข้อมูลเพิ่มเติมในบล็อกของฉัน: EOFError: จุดสิ้นสุดของแฟ้มถึงปัญหาเมื่อโพสต์รูปแบบกับสุทธิ


ขอบคุณนี้ช่วยให้ฉันเข้าใจความแตกต่างระหว่างและhttp req
guptron

6
การเชื่อมโยงโพสต์บล็อกเสีย แต่ลองนี้web.archive.org/web/20150429191916/http://expressica.com/2012/...
เฮนริก N

ถ้ามันไม่ใช่ https ล่ะ?
Jwan622

5

ฉันมีปัญหาคล้ายกันกับการร้องขอไปยังบริการที่ไม่ใช่ SSL

บล็อกนี้แนะนำให้ลองใช้การเข้ารหัส URI ที่ส่งผ่านไปที่ 'รับ': http://www.loudthinking.org/2010/02/ruby-eoferror-end-of-file-reached.html

ฉันถ่ายภาพตามความสิ้นหวังและในการทดสอบที่ จำกัด ของฉันดูเหมือนว่าจะแก้ไขให้ฉันแล้ว รหัสใหม่ของฉันคือ:

@http = Net::HTTP.new('domain.com')  
@http = @http.start    
url = 'http://domain.com/requested_url?blah=blah&etc=1'
req = Net::HTTP::Get.new(URI.encode(url))
req.basic_auth USERNAME, API_KEY
res = @http.request(req) 

โปรดทราบว่าฉันใช้ @ http.start ตามที่ฉันต้องการบำรุงรักษาเซสชัน HTTP ผ่านการร้องขอหลายรายการ นอกเหนือจากนั้นคุณอาจต้องการลองส่วนที่เกี่ยวข้องมากที่สุดซึ่งก็คือ: URI.encode (url)ภายในการรับสาย


2
ฉันแค่ต้องการให้ข้อเสนอแนะเพิ่มเติมเกี่ยวกับเรื่องนี้เนื่องจากมันยังคงมีประโยชน์ ฉันใช้ URI ที่เข้ารหัสนี้บนเซิร์ฟเวอร์ที่ใช้งานจริงเป็นเวลา 4 เดือนและฉันสามารถยืนยันได้ว่าได้แก้ปัญหาแล้ว
Phil

3

ฉันพบว่าฉันพบปัญหา Net :: HTTP และ Net :: FTP เช่นนี้เป็นระยะและเมื่อฉันโดยรอบการโทรด้วยการหมดเวลา () ทำให้ปัญหาเหล่านั้นหายไป ดังนั้นสิ่งนี้จะแขวนเป็นเวลา 3 นาทีหรือมากกว่านั้นและยก EOFError:

res = Net::HTTP.post_form(uri, args)

วิธีนี้แก้ไขได้เสมอสำหรับฉัน:

res = timeout(120) { Net::HTTP.post_form(uri, args) }

3

ฉันมีปัญหาเดียวกัน ruby-1.8.7-p357 และลองใช้สิ่งต่าง ๆ อย่างเปล่าประโยชน์ ...

ในที่สุดฉันก็รู้ว่ามันจะเกิดขึ้นเฉพาะกับการโทรหลายสายโดยใช้ XMLRPC :: อินสแตนซ์ของลูกค้า!

ดังนั้นตอนนี้ฉันกำลังสร้างอินสแตนซ์ใหม่ให้กับลูกค้าของฉันในการโทรแต่ละครั้งและใช้งานได้: |


1

หลังจากทำวิจัยบางคนนี้กำลังจะเกิดขึ้นในรูบีของXMLRPC::Clientห้องสมุด - NET::HTTPซึ่งการใช้งาน ไคลเอนต์ใช้start()วิธีการNET::HTTPที่ทำให้การเชื่อมต่อเปิดสำหรับการร้องขอในอนาคต

สิ่งนี้เกิดขึ้นอย่างแม่นยำใน 30 วินาทีหลังจากการร้องขอครั้งสุดท้ายดังนั้นข้อสันนิษฐานของฉันที่นี่คือเซิร์ฟเวอร์ที่กำลังกดปุ่มเป็นการปิดการร้องขอหลังจากนั้น ฉันไม่แน่ใจว่าสิ่งที่เป็นค่าเริ่มต้นคือNET::HTTPเพื่อให้คำขอเปิด - แต่ฉันจะทดสอบกับ 60 วินาทีเพื่อดูว่าแก้ปัญหา


1
ผลลัพธ์คืออะไร
Peter Mortensen

1

ฉันวิ่งเข้าไปในนี้เมื่อเร็ว ๆ นี้และในที่สุดก็พบว่าสิ่งนี้เกิดจากการหมดเวลาเครือข่ายจากจุดสิ้นสุดที่เรากำลังกดปุ่ม โชคดีสำหรับเราเราสามารถเพิ่มระยะเวลาการหมดเวลาได้

เพื่อตรวจสอบว่านี่เป็นปัญหาของเรา (และที่จริงแล้วไม่ใช่ปัญหากับ net http) ฉันได้ทำคำขอเดียวกันกับ curl และยืนยันว่าคำขอนั้นถูกยกเลิก


-1

ใน Ruby on Rails ฉันใช้รหัสนี้และทำงานได้อย่างสมบูรณ์:

req_profilepic = ActiveSupport::JSON.decode(open(URI.encode("https://graph.facebook.com/me/?fields=picture&type=large&access_token=#{fb_access_token}")))

profilepic_url = req_profilepic['picture']
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.