Class: Mechanize::HTTP::ContentDispositionParser
- Inherits:
-
Object
- Object
- Mechanize::HTTP::ContentDispositionParser
- Defined in:
- lib/mechanize/http/content_disposition_parser.rb
Overview
Parser Content-Disposition headers that loosely follows RFC 2183.
Beyond RFC 2183, this parser allows:
-
Missing disposition-type
-
Multiple semicolons
-
Whitespace around semicolons
-
Dates in ISO 8601 format
Instance Attribute Summary collapse
-
#scanner ⇒ Object
:nodoc:.
Class Method Summary collapse
-
.parse(content_disposition) ⇒ Object
Parses the disposition type and params in the
content_disposition
string.
Instance Method Summary collapse
-
#initialize ⇒ ContentDispositionParser
constructor
Creates a new parser Content-Disposition headers.
-
#parse(content_disposition, header = false) ⇒ Object
Parses the
content_disposition
header. -
#parse_parameters ⇒ Object
Extracts disposition-param and returns a Hash.
-
#rfc_2045_quoted_string ⇒ Object
quoted-string = <“> *(qtext/quoted-pair) <”> qtext = <any CHAR excepting <“>, ”" & CR, and including linear-white-space quoted-pair = “" CHAR.
-
#rfc_2045_token ⇒ Object
token := 1*<any (US-ASCII) CHAR except SPACE, CTLs, or tspecials>.
-
#rfc_2045_value ⇒ Object
value := token / quoted-string.
-
#spaces ⇒ Object
1*SP.
Constructor Details
#initialize ⇒ ContentDispositionParser
Creates a new parser Content-Disposition headers
40 41 42 |
# File 'lib/mechanize/http/content_disposition_parser.rb', line 40 def initialize @scanner = nil end |
Instance Attribute Details
#scanner ⇒ Object
:nodoc:
24 25 26 |
# File 'lib/mechanize/http/content_disposition_parser.rb', line 24 def scanner @scanner end |
Class Method Details
.parse(content_disposition) ⇒ Object
Parses the disposition type and params in the content_disposition
string. The “Content-Disposition:” must be removed.
32 33 34 35 |
# File 'lib/mechanize/http/content_disposition_parser.rb', line 32 def self.parse content_disposition @parser ||= self.new @parser.parse content_disposition end |
Instance Method Details
#parse(content_disposition, header = false) ⇒ Object
Parses the content_disposition
header. If header
is set to true the “Content-Disposition:” portion will be parsed
48 49 50 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 76 77 78 79 80 81 |
# File 'lib/mechanize/http/content_disposition_parser.rb', line 48 def parse content_disposition, header = false return nil if content_disposition.empty? @scanner = StringScanner.new content_disposition if header then return nil unless @scanner.scan(/Content-Disposition/i) return nil unless @scanner.scan(/:/) spaces end type = rfc_2045_token @scanner.scan(/;+/) if @scanner.peek(1) == '=' then @scanner.pos = 0 type = nil end disposition = Mechanize::HTTP::ContentDisposition.new type spaces return nil unless parameters = parse_parameters disposition.filename = parameters.delete 'filename' disposition.creation_date = parameters.delete 'creation-date' disposition.modification_date = parameters.delete 'modification-date' disposition.read_date = parameters.delete 'read-date' disposition.size = parameters.delete 'size' disposition.parameters = parameters disposition end |
#parse_parameters ⇒ Object
Extracts disposition-param and returns a Hash.
86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 |
# File 'lib/mechanize/http/content_disposition_parser.rb', line 86 def parse_parameters parameters = {} while true do return nil unless param = rfc_2045_token param.downcase! return nil unless @scanner.scan(/=/) value = case param when /^filename$/ then rfc_2045_value when /^(creation|modification|read)-date$/ then date = rfc_2045_quoted_string begin Time.rfc822 date rescue ArgumentError begin Time.iso8601 date rescue ArgumentError nil end end when /^size$/ then rfc_2045_value.to_i(10) else rfc_2045_value end return nil unless value parameters[param] = value spaces break if @scanner.eos? or not @scanner.scan(/;+/) spaces end parameters end |
#rfc_2045_quoted_string ⇒ Object
quoted-string = <“> *(qtext/quoted-pair) <”>
qtext = <any CHAR excepting <">, "\" & CR,
and including linear-white-space
quoted-pair = "\" CHAR
Parses an RFC 2045 quoted-string
137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 |
# File 'lib/mechanize/http/content_disposition_parser.rb', line 137 def rfc_2045_quoted_string return nil unless @scanner.scan(/"/) text = String.new while true do chunk = @scanner.scan(/[\000-\014\016-\041\043-\133\135-\177]+/) # not \r " if chunk then text << chunk if @scanner.peek(1) == '\\' then @scanner.get_byte return nil if @scanner.eos? text << @scanner.get_byte elsif @scanner.scan(/\r\n[\t ]+/) then text << " " end else if '\\"' == @scanner.peek(2) then @scanner.skip(/\\/) text << @scanner.get_byte elsif '"' == @scanner.peek(1) then @scanner.get_byte break else return nil end end end text end |
#rfc_2045_token ⇒ Object
token := 1*<any (US-ASCII) CHAR except SPACE, CTLs, or tspecials>
Parses an RFC 2045 token
176 177 178 |
# File 'lib/mechanize/http/content_disposition_parser.rb', line 176 def rfc_2045_token @scanner.scan(/[^\000-\037\177()<>@,;:\\"\/\[\]?= ]+/) end |
#rfc_2045_value ⇒ Object
value := token / quoted-string
Parses an RFC 2045 value
185 186 187 188 189 190 191 |
# File 'lib/mechanize/http/content_disposition_parser.rb', line 185 def rfc_2045_value if @scanner.peek(1) == '"' then rfc_2045_quoted_string else rfc_2045_token end end |
#spaces ⇒ Object
1*SP
Parses spaces
198 199 200 |
# File 'lib/mechanize/http/content_disposition_parser.rb', line 198 def spaces @scanner.scan(/ +/) end |