def self.decode(query)
return nil if query == nil
params = {}
query.split("&").each do |pair|
next if pair.empty?
key, value = pair.split("=", 2)
key = unescape(key)
value = unescape(value.gsub(/\+/, ' ')) if value
subkeys = key.scan(/[^\[\]]+(?:\]?\[\])?/)
context = params
subkeys.each_with_index do |subkey, i|
is_array = subkey =~ /[\[\]]+\Z/
subkey = $` if is_array
last_subkey = i == subkeys.length - 1
if !last_subkey || is_array
value_type = is_array ? Array : Hash
if context[subkey] && !context[subkey].is_a?(value_type)
raise TypeError, "expected %s (got %s) for param `%s'" % [
value_type.name,
context[subkey].class.name,
subkey
]
end
context = (context[subkey] ||= value_type.new)
end
if context.is_a?(Array) && !is_array
if !context.last.is_a?(Hash) || context.last.has_key?(subkey)
context << {}
end
context = context.last
end
if last_subkey
if is_array
context << value
else
context[subkey] = value
end
end
end
end
dehash(params, 0)
end