Class: Yajl::HttpStream

Inherits:
Object
  • Object
show all
Defined in:
lib/yajl/http_stream.rb

Overview

This module is for making HTTP requests to which the response bodies (and possibly requests in the near future) are streamed directly into Yajl.

Defined Under Namespace

Classes: InvalidContentType

Constant Summary collapse

ALLOWED_MIME_TYPES =

The mime-type we expect the response to be. If it’s anything else, we can’t parse it and an InvalidContentType is raised.

["application/json", "text/plain"]

Class Method Summary collapse

Class Method Details

.get(uri, opts = {}, &block) ⇒ Object

Makes a basic HTTP GET request to the URI provided

  1. a raw socket is opened to the server/host provided

  2. the request is made using HTTP/1.0, Accept-encoding: gzip (deflate support coming soon, too)

  3. the response is read until the end of the headers

  4. the _socket itself_ is passed directly to Yajl, for direct parsing off the stream; As it’s being received over the wire!



24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
# File 'lib/yajl/http_stream.rb', line 24

def self.get(uri, opts = {}, &block)
  user_agent = opts.has_key?('User-Agent') ? opts.delete(['User-Agent']) : "Yajl::HttpStream #{Yajl::VERSION}"
  
  Thread.current[:yajl_socket] = socket = TCPSocket.new(uri.host, uri.port)
  request = "GET #{uri.path}#{uri.query ? "?"+uri.query : nil} HTTP/1.1\r\n"
  request << "Host: #{uri.host}\r\n"
  request << "Authorization: Basic #{[uri.userinfo].pack('m').chomp}\r\n" unless uri.userinfo.nil?
  request << "User-Agent: #{user_agent}\r\n"
  request << "Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8\r\n"
  request << "Connection: close\r\n"
  encodings = []
  encodings << "bzip2" if defined?(Yajl::Bzip2)
  encodings << "gzip" if defined?(Yajl::Gzip)
  encodings << "deflate" if defined?(Yajl::Deflate)
  request << "Accept-Encoding: #{encodings.join(',')}\r\n" if encodings.any?
  request << "Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7\r\n"
  request << "\r\n\r\n"
  socket.write(request)

  handle_response(socket, opts, &block)
end

.post(uri, body = {}, opts = {}, &block) ⇒ Object

Makes a basic HTTP POST request to the URI provided

  1. a raw socket is opened to the server/host provided

  2. the request is made using HTTP/1.0, Accept-encoding: gzip (deflate support coming soon, too)

  3. the response is read until the end of the headers

  4. the _socket itself_ is passed directly to Yajl, for direct parsing off the stream; As it’s being received over the wire!



51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
# File 'lib/yajl/http_stream.rb', line 51

def self.post(uri, body={}, opts = {}, &block)
  content = body.keys.collect {|param| "#{URI.escape(param.to_s)}=#{URI.escape(body[param].to_s)}"}.join('&')

  user_agent = opts.has_key?('User-Agent') ? opts.delete(['User-Agent']) : "Yajl::HttpStream #{Yajl::VERSION}"
  
  Thread.current[:yajl_socket] = socket = TCPSocket.new(uri.host, uri.port)
  request = "POST #{uri.path}#{uri.query ? "?"+uri.query : nil} HTTP/1.1\r\n"
  request << "Host: #{uri.host}\r\n"
  request << "Authorization: Basic #{[uri.userinfo].pack('m').chomp}\r\n" unless uri.userinfo.nil?
  request << "User-Agent: #{user_agent}\r\n"
  request << "Accept: */*\r\n"
  encodings = []
  encodings << "bzip2" if defined?(Yajl::Bzip2)
  encodings << "gzip" if defined?(Yajl::Gzip)
  encodings << "deflate" if defined?(Yajl::Deflate)
  request << "Accept-Encoding: #{encodings.join(',')}\r\n" if encodings.any?
  request << "Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7\r\n"
  request << "Content-Type: application/x-www-form-urlencoded\r\n"
  request << "Content-Length: #{content.length}"
  request << "\r\n\r\n"
  request << content
  socket.write(request)
  
  handle_response(socket, opts, &block)
end

.terminate(thread) ⇒ Object

Terminate a running HTTPStream instance given the thread it’s running in



78
79
80
81
# File 'lib/yajl/http_stream.rb', line 78

def self.terminate(thread)      
  thread[:yajl_intentional_termination] = true
  thread[:yajl_socket].close
end