tilia-http 4.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (63) hide show
  1. checksums.yaml +7 -0
  2. data/.gitignore +19 -0
  3. data/.rspec +1 -0
  4. data/.rubocop.yml +35 -0
  5. data/.simplecov +4 -0
  6. data/.travis.yml +3 -0
  7. data/CHANGELOG.sabre.md +235 -0
  8. data/CONTRIBUTING.md +25 -0
  9. data/Gemfile +18 -0
  10. data/Gemfile.lock +69 -0
  11. data/LICENSE +27 -0
  12. data/LICENSE.sabre +27 -0
  13. data/README.md +68 -0
  14. data/Rakefile +17 -0
  15. data/examples/asyncclient.rb +45 -0
  16. data/examples/basicauth.rb +39 -0
  17. data/examples/client.rb +20 -0
  18. data/examples/reverseproxy.rb +39 -0
  19. data/examples/stringify.rb +37 -0
  20. data/lib/tilia/http/auth/abstract_auth.rb +51 -0
  21. data/lib/tilia/http/auth/aws.rb +191 -0
  22. data/lib/tilia/http/auth/basic.rb +43 -0
  23. data/lib/tilia/http/auth/bearer.rb +37 -0
  24. data/lib/tilia/http/auth/digest.rb +187 -0
  25. data/lib/tilia/http/auth.rb +12 -0
  26. data/lib/tilia/http/client.rb +452 -0
  27. data/lib/tilia/http/client_exception.rb +15 -0
  28. data/lib/tilia/http/client_http_exception.rb +37 -0
  29. data/lib/tilia/http/http_exception.rb +21 -0
  30. data/lib/tilia/http/message.rb +241 -0
  31. data/lib/tilia/http/message_decorator_trait.rb +183 -0
  32. data/lib/tilia/http/message_interface.rb +154 -0
  33. data/lib/tilia/http/request.rb +235 -0
  34. data/lib/tilia/http/request_decorator.rb +160 -0
  35. data/lib/tilia/http/request_interface.rb +126 -0
  36. data/lib/tilia/http/response.rb +164 -0
  37. data/lib/tilia/http/response_decorator.rb +58 -0
  38. data/lib/tilia/http/response_interface.rb +36 -0
  39. data/lib/tilia/http/sapi.rb +165 -0
  40. data/lib/tilia/http/url_util.rb +70 -0
  41. data/lib/tilia/http/util.rb +51 -0
  42. data/lib/tilia/http/version.rb +9 -0
  43. data/lib/tilia/http.rb +416 -0
  44. data/test/http/auth/aws_test.rb +189 -0
  45. data/test/http/auth/basic_test.rb +60 -0
  46. data/test/http/auth/bearer_test.rb +47 -0
  47. data/test/http/auth/digest_test.rb +141 -0
  48. data/test/http/client_mock.rb +101 -0
  49. data/test/http/client_test.rb +331 -0
  50. data/test/http/message_decorator_test.rb +67 -0
  51. data/test/http/message_test.rb +163 -0
  52. data/test/http/request_decorator_test.rb +87 -0
  53. data/test/http/request_test.rb +132 -0
  54. data/test/http/response_decorator_test.rb +28 -0
  55. data/test/http/response_test.rb +38 -0
  56. data/test/http/sapi_mock.rb +12 -0
  57. data/test/http/sapi_test.rb +133 -0
  58. data/test/http/url_util_test.rb +155 -0
  59. data/test/http/util_test.rb +186 -0
  60. data/test/http_test.rb +102 -0
  61. data/test/test_helper.rb +6 -0
  62. data/tilia-http.gemspec +18 -0
  63. metadata +192 -0
@@ -0,0 +1,58 @@
1
+ module Tilia
2
+ module Http
3
+ # Response Decorator
4
+ #
5
+ # This helper class allows you to easily create decorators for the Response
6
+ # object.
7
+ class ResponseDecorator
8
+ include Tilia::Http::ResponseInterface
9
+ include Tilia::Http::MessageDecoratorTrait
10
+
11
+ # Constructor.
12
+ #
13
+ # @param ResponseInterface inner
14
+ def initialize(inner)
15
+ @inner = inner
16
+ end
17
+
18
+ # Returns the current HTTP status code.
19
+ #
20
+ # @return int
21
+ def status
22
+ @inner.status
23
+ end
24
+
25
+ # Returns the human-readable status string.
26
+ #
27
+ # In the case of a 200, this may for example be 'OK'.
28
+ #
29
+ # @return [String]
30
+ def status_text
31
+ @inner.status_text
32
+ end
33
+
34
+ # Sets the HTTP status code.
35
+ #
36
+ # This can be either the full HTTP status code with human readable string,
37
+ # for example: "403 I can't let you do that, Dave".
38
+ #
39
+ # Or just the code, in which case the appropriate default message will be
40
+ # added.
41
+ #
42
+ # @param [String, Fixnum] status
43
+ # @return [void]
44
+ def status=(status)
45
+ @inner.status = status
46
+ end
47
+
48
+ # Serializes the request object as a string.
49
+ #
50
+ # This is useful for debugging purposes.
51
+ #
52
+ # @return [String]
53
+ def to_s
54
+ @inner.to_s
55
+ end
56
+ end
57
+ end
58
+ end
@@ -0,0 +1,36 @@
1
+ module Tilia
2
+ module Http
3
+ # This interface represents a HTTP response.
4
+ module ResponseInterface
5
+ include Tilia::Http::MessageInterface
6
+
7
+ # Returns the current HTTP status code.
8
+ #
9
+ # @return int
10
+ def status
11
+ end
12
+
13
+ # Returns the human-readable status string.
14
+ #
15
+ # In the case of a 200, this may for example be 'OK'.
16
+ #
17
+ # @return [String]
18
+ def status_text
19
+ end
20
+
21
+ # Sets the HTTP status code.
22
+ #
23
+ # This can be either the full HTTP status code with human readable string,
24
+ # for example: "403 I can't let you do that, Dave".
25
+ #
26
+ # Or just the code, in which case the appropriate default message will be
27
+ # added.
28
+ #
29
+ # @param [String, Fixnum] status
30
+ # @throws \InvalidArgumentExeption
31
+ # @return [void]
32
+ def status=(_status)
33
+ end
34
+ end
35
+ end
36
+ end
@@ -0,0 +1,165 @@
1
+ require 'stringio'
2
+ require 'base64'
3
+ module Tilia
4
+ module Http
5
+ # PHP SAPI
6
+ #
7
+ # This object is responsible for:
8
+ # 1. Constructing a Request object based on the current HTTP request sent to
9
+ # the PHP process.
10
+ # 2. Sending the Response object back to the client.
11
+ #
12
+ # It could be said that this class provides a mapping between the Request and
13
+ # Response objects, and php's:
14
+ #
15
+ # * $_SERVER
16
+ # * $_POST
17
+ # * $_FILES
18
+ # * php://input
19
+ # * echo
20
+ # * header
21
+ # * php://output
22
+ #
23
+ # You can choose to either call all these methods statically, but you can also
24
+ # instantiate this as an object to allow for polymorhpism.
25
+ class Sapi
26
+ # This static method will create a new Request object, based on the
27
+ # current PHP request.
28
+ #
29
+ # @return Request
30
+ def self.request
31
+ fail NotImplementedError, 'This object method now is an instance method'
32
+ end
33
+
34
+ # Sends the HTTP response back to a HTTP client.
35
+ #
36
+ # This calls php's header function and streams the body to php://output.
37
+ #
38
+ # @param ResponseInterface response
39
+ # @return [void]
40
+ def self.send_response(response)
41
+ # RUBY: Rack does not support HTTP Version (?)
42
+ # header("HTTP/#{response.http_version} #{response.status} #{response.status_text}")
43
+
44
+ status = response.status
45
+ headers = {}
46
+ response.headers.each do |key, value|
47
+ headers[key] = value.join("\n")
48
+ end
49
+
50
+ body = response.body_as_stream
51
+ content_length = response.header('Content-Length')
52
+ if content_length
53
+ output = StringIO.new
54
+ output.write body.read(content_length.to_i)
55
+ output.rewind
56
+ body = output
57
+ end
58
+
59
+ [status, headers, body]
60
+ end
61
+
62
+ # This static method will create a new Request object, based on a PHP
63
+ # $_SERVER array.
64
+ #
65
+ # @param array server_array
66
+ # @return Request
67
+ def self.create_from_server_array(server_array)
68
+ headers = {}
69
+ method = nil
70
+ url = nil
71
+ http_version = '1.1'
72
+
73
+ protocol = 'http'
74
+ host_name = 'localhost'
75
+
76
+ server_array.each do |key, value|
77
+ case key
78
+ when 'SERVER_PROTOCOL'
79
+ http_version = '1.0' if value == 'HTTP/1.0'
80
+ when 'REQUEST_METHOD'
81
+ method = value
82
+ when 'REQUEST_URI'
83
+ url = value
84
+
85
+ # These sometimes should up without a HTTP_ prefix
86
+ when 'CONTENT_TYPE'
87
+ headers['Content-Type'] = value
88
+ when 'CONTENT_LENGTH'
89
+ headers['Content-Length'] = value
90
+
91
+ # mod_php on apache will put credentials in these variables.
92
+ # (fast)cgi does not usually do this, however.
93
+ when 'PHP_AUTH_USER'
94
+ if server_array.key? 'PHP_AUTH_PW'
95
+ headers['Authorization'] = "Basic #{Base64.strict_encode64 "#{value}:#{server_array['PHP_AUTH_PW']}"}"
96
+ end
97
+ when 'PHP_AUTH_DIGEST'
98
+ headers['Authorization'] = "Digest #{value}"
99
+
100
+ # Apache may prefix the HTTP_AUTHORIZATION header with
101
+ # REDIRECT_, if mod_rewrite was used.
102
+ when 'REDIRECT_HTTP_AUTHORIZATION'
103
+ headers['Authorization'] = value
104
+
105
+ when 'HTTP_HOST'
106
+ host_name = value
107
+ headers['Host'] = value
108
+
109
+ when 'HTTPS'
110
+ protocol = 'https' if value && value != 'off'
111
+
112
+ # RUBY
113
+ when 'rack.url_scheme'
114
+ protocol = value
115
+
116
+ else
117
+ if key.index('HTTP_') == 0
118
+ # It's a HTTP header
119
+
120
+ # Normalizing it to be prettier
121
+ header = key[5..-1].downcase
122
+
123
+ # Transforming dashes into spaces, and uppercasing
124
+ # every first letter.
125
+ # Turning spaces into dashes.
126
+ header = header.split(/_/).map(&:capitalize).join('-')
127
+
128
+ headers[header] = value
129
+ end
130
+ end
131
+ end
132
+
133
+ r = Tilia::Http::Request.new(method, url, headers)
134
+ r.http_version = http_version
135
+ r.raw_server_data = server_array
136
+ r.absolute_url = "#{protocol}://#{host_name}#{url}"
137
+ r
138
+ end
139
+
140
+ # TODO: document
141
+ def initialize(env)
142
+ @env = env
143
+ @rack_request = Rack::Request.new(env)
144
+ end
145
+
146
+ # TODO: document
147
+ def request
148
+ r = create_from_server_array(@env)
149
+ r.body = StringIO.new
150
+ r.post_data = @rack_request.POST
151
+ r
152
+ end
153
+
154
+ # TODO: document
155
+ def send_response(response)
156
+ self.class.send_response(response)
157
+ end
158
+
159
+ # TODO: document
160
+ def create_from_server_array(server_array)
161
+ self.class.create_from_server_array(server_array)
162
+ end
163
+ end
164
+ end
165
+ end
@@ -0,0 +1,70 @@
1
+ module Tilia
2
+ module Http
3
+ # URL utility class
4
+ #
5
+ # Note: this class is deprecated. All its functionality moved to functions.php
6
+ # or sabre\uri.
7
+ #
8
+ # @deprectated
9
+ module UrlUtil
10
+ # Encodes the path of a url.
11
+ #
12
+ # slashes (/) are treated as path-separators.
13
+ #
14
+ # @deprecated use \Sabre\HTTP\encode_path
15
+ # @param [String] path
16
+ # @return [String]
17
+ def self.encode_path(path)
18
+ Tilia::Http.encode_path(path)
19
+ end
20
+
21
+ # Encodes a 1 segment of a path
22
+ #
23
+ # Slashes are considered part of the name, and are encoded as %2f
24
+ #
25
+ # @deprecated use \Sabre\HTTP\encode_path_segment
26
+ # @param [String] path_segment
27
+ # @return [String]
28
+ def self.encode_path_segment(path_segment)
29
+ Tilia::Http.encode_path_segment(path_segment)
30
+ end
31
+
32
+ # Decodes a url-encoded path
33
+ #
34
+ # @deprecated use \Sabre\HTTP\decodePath
35
+ # @param [String] path
36
+ # @return [String]
37
+ def self.decode_path(path)
38
+ Tilia::Http.decode_path(path)
39
+ end
40
+
41
+ # Decodes a url-encoded path segment
42
+ #
43
+ # @deprecated use \Sabre\HTTP\decode_path_segment
44
+ # @param [String] path
45
+ # @return [String]
46
+ def self.decode_path_segment(path)
47
+ Tilia::Http.decode_path_segment(path)
48
+ end
49
+
50
+ # Returns the 'dirname' and 'basename' for a path.
51
+ #
52
+ # @deprecated Use Sabre\Uri\split.
53
+ # @param [String] path
54
+ # @return array
55
+ def self.split_path(path)
56
+ Tilia::Uri.split(path)
57
+ end
58
+
59
+ # Resolves relative urls, like a browser would.
60
+ #
61
+ # @deprecated Use Sabre\Uri\resolve.
62
+ # @param [String] base_path
63
+ # @param [String] new_path
64
+ # @return [String]
65
+ def self.resolve(base_path, new_path)
66
+ Tilia::Uri.resolve(base_path, new_path)
67
+ end
68
+ end
69
+ end
70
+ end
@@ -0,0 +1,51 @@
1
+ module Tilia
2
+ module Http
3
+ # HTTP utility methods
4
+ #
5
+ # @deprecated All these functions moved to the Tilia::Http namespace
6
+ module Util
7
+ # Content negotiation
8
+ #
9
+ # @deprecated Use Tilia::Http::negotiate_content_type
10
+ # @param [String, nil] accept_header_value
11
+ # @param array available_options
12
+ # @return [String, nil]
13
+ def self.negotiate_content_type(accept_header_value, available_options)
14
+ Http.negotiate_content_type(accept_header_value, available_options)
15
+ end
16
+
17
+ # Deprecated! Use negotiateContentType.
18
+ #
19
+ # @deprecated Use Tilia::Http::negotiate_content_type
20
+ # @param [String, nil] accept_header
21
+ # @param array available_options
22
+ # @return [String, nil]
23
+ def self.negotiate(accept_header_value, available_options)
24
+ Http.negotiate_content_type(accept_header_value, available_options)
25
+ end
26
+
27
+ # Parses a RFC2616-compatible date string
28
+ #
29
+ # This method returns false if the date is invalid
30
+ #
31
+ # @deprecated Use Tilia::Http::parse_date
32
+ # @param [String] date_header
33
+ # @return bool|DateTime
34
+ def self.parse_http_date(date_header)
35
+ Http.parse_date(date_header)
36
+ end
37
+
38
+ # Transforms a DateTime object to HTTP's most common date format.
39
+ #
40
+ # We're serializing it as the RFC 1123 date, which, for HTTP must be
41
+ # specified as GMT.
42
+ #
43
+ # @deprecated Use Tilia::Http::to_date
44
+ # @param \DateTime date_time
45
+ # @return [String]
46
+ def self.to_http_date(date_time)
47
+ Http.to_date(date_time)
48
+ end
49
+ end
50
+ end
51
+ end
@@ -0,0 +1,9 @@
1
+ module Tilia
2
+ module Http
3
+ # This class contains the version number for the HTTP package
4
+ class Version
5
+ # Full version number
6
+ VERSION = '4.1.0'
7
+ end
8
+ end
9
+ end