From a5429833e411ad30b1fe8aff63f10e244c95e83d Mon Sep 17 00:00:00 2001 From: Kunpei Sakai Date: Thu, 11 Apr 2019 17:19:35 +0900 Subject: [PATCH] avoid multiple errors even if `params` contains special values The original fixes are #1506 and #1517. This commit considers `FrozenError` and `TypeEror` for the case. --- lib/sinatra/base.rb | 7 ++++++- test/middleware_test.rb | 19 +++++++++++++++++++ 2 files changed, 25 insertions(+), 1 deletion(-) diff --git a/lib/sinatra/base.rb b/lib/sinatra/base.rb index aef747e7..f1fd0f10 100644 --- a/lib/sinatra/base.rb +++ b/lib/sinatra/base.rb @@ -1089,7 +1089,12 @@ module Sinatra # Dispatch a request with error handling. def dispatch! - @params.merge!(@request.params).each { |key, val| @params[key] = val && force_encoding(val.dup) } + # Avoid passing frozen string in force_encoding + @params.merge!(@request.params).each do |key, val| + next unless val.respond_to?(:force_encoding) + val = val.dup if val.frozen? + @params[key] = force_encoding(val) + end invoke do static! if settings.static? && (request.get? || request.head?) diff --git a/test/middleware_test.rb b/test/middleware_test.rb index 7f715886..370f874a 100644 --- a/test/middleware_test.rb +++ b/test/middleware_test.rb @@ -78,4 +78,23 @@ class MiddlewareTest < Minitest::Test @app.use FreezeMiddleware get '/Foo' end + + class SpecialConstsMiddleware < MockMiddleware + def call(env) + req = Rack::Request.new(env) + req.update_param('s', :s) + req.update_param('i', 1) + req.update_param('c', 3.to_c) + req.update_param('t', true) + req.update_param('f', false) + req.update_param('n', nil) + super + end + end + + it "handles params when the params contains true/false values" do + @app.use SpecialConstsMiddleware + get '/' + end + end