4
4
5
5
require "http/errors"
6
6
require "http/headers/mixin"
7
+ require "http/headers/normalizer"
7
8
require "http/headers/known"
8
9
9
10
module HTTP
@@ -12,12 +13,32 @@ class Headers
12
13
extend Forwardable
13
14
include Enumerable
14
15
15
- # Matches HTTP header names when in "Canonical-Http-Format"
16
- CANONICAL_NAME_RE = /\A [A-Z][a-z]*(?:-[A-Z][a-z]*)*\z /
16
+ class << self
17
+ # Coerces given `object` into Headers.
18
+ #
19
+ # @raise [Error] if object can't be coerced
20
+ # @param [#to_hash, #to_h, #to_a] object
21
+ # @return [Headers]
22
+ def coerce ( object )
23
+ unless object . is_a? self
24
+ object = case
25
+ when object . respond_to? ( :to_hash ) then object . to_hash
26
+ when object . respond_to? ( :to_h ) then object . to_h
27
+ when object . respond_to? ( :to_a ) then object . to_a
28
+ else raise Error , "Can't coerce #{ object . inspect } to Headers"
29
+ end
30
+ end
31
+
32
+ headers = new
33
+ object . each { |k , v | headers . add k , v }
34
+ headers
35
+ end
36
+ alias [] coerce
17
37
18
- # Matches valid header field name according to RFC.
19
- # @see http://tools.ietf.org/html/rfc7230#section-3.2
20
- COMPLIANT_NAME_RE = /\A [A-Za-z0-9!#$%&'*+\- .^_`|~]+\z /
38
+ def normalizer
39
+ @normalizer ||= Headers ::Normalizer . new
40
+ end
41
+ end
21
42
22
43
# Class constructor.
23
44
def initialize
@@ -194,45 +215,11 @@ def merge(other)
194
215
dup . tap { |dupped | dupped . merge! other }
195
216
end
196
217
197
- class << self
198
- # Coerces given `object` into Headers.
199
- #
200
- # @raise [Error] if object can't be coerced
201
- # @param [#to_hash, #to_h, #to_a] object
202
- # @return [Headers]
203
- def coerce ( object )
204
- unless object . is_a? self
205
- object = case
206
- when object . respond_to? ( :to_hash ) then object . to_hash
207
- when object . respond_to? ( :to_h ) then object . to_h
208
- when object . respond_to? ( :to_a ) then object . to_a
209
- else raise Error , "Can't coerce #{ object . inspect } to Headers"
210
- end
211
- end
212
-
213
- headers = new
214
- object . each { |k , v | headers . add k , v }
215
- headers
216
- end
217
- alias [] coerce
218
- end
219
-
220
218
private
221
219
222
220
# Transforms `name` to canonical HTTP header capitalization
223
- #
224
- # @param [String] name
225
- # @raise [HeaderError] if normalized name does not
226
- # match {HEADER_NAME_RE}
227
- # @return [String] canonical HTTP header name
228
221
def normalize_header ( name )
229
- return name if CANONICAL_NAME_RE . match? ( name )
230
-
231
- normalized = name . split ( /[\- _]/ ) . each ( &:capitalize! ) . join ( "-" )
232
-
233
- return normalized if COMPLIANT_NAME_RE . match? ( normalized )
234
-
235
- raise HeaderError , "Invalid HTTP header field name: #{ name . inspect } "
222
+ self . class . normalizer . call ( name )
236
223
end
237
224
238
225
# Ensures there is no new line character in the header value
0 commit comments