Imported Upstream version 4.2.4

parent 08a4dad1
......@@ -25,8 +25,6 @@ rvm:
- 2.1
- 2.2
- ruby-head
- rbx-2
- jruby
matrix:
allow_failures:
- rvm: ruby-head
......@@ -36,8 +34,6 @@ matrix:
env: "GEM=ar:mysql"
- rvm: ruby-head
env: "GEM=ar:mysql"
- rvm: rbx-2
- rvm: jruby
- env: "GEM=aj:integration"
fast_finish: true
notifications:
......
......@@ -14,55 +14,55 @@ GIT
PATH
remote: .
specs:
actionmailer (4.2.2)
actionpack (= 4.2.2)
actionview (= 4.2.2)
activejob (= 4.2.2)
actionmailer (4.2.4.rc1)
actionpack (= 4.2.4.rc1)
actionview (= 4.2.4.rc1)
activejob (= 4.2.4.rc1)
mail (~> 2.5, >= 2.5.4)
rails-dom-testing (~> 1.0, >= 1.0.5)
actionpack (4.2.2)
actionview (= 4.2.2)
activesupport (= 4.2.2)
actionpack (4.2.4.rc1)
actionview (= 4.2.4.rc1)
activesupport (= 4.2.4.rc1)
rack (~> 1.6)
rack-test (~> 0.6.2)
rails-dom-testing (~> 1.0, >= 1.0.5)
rails-html-sanitizer (~> 1.0, >= 1.0.1)
actionview (4.2.2)
activesupport (= 4.2.2)
rails-html-sanitizer (~> 1.0, >= 1.0.2)
actionview (4.2.4.rc1)
activesupport (= 4.2.4.rc1)
builder (~> 3.1)
erubis (~> 2.7.0)
rails-dom-testing (~> 1.0, >= 1.0.5)
rails-html-sanitizer (~> 1.0, >= 1.0.1)
activejob (4.2.2)
activesupport (= 4.2.2)
rails-html-sanitizer (~> 1.0, >= 1.0.2)
activejob (4.2.4.rc1)
activesupport (= 4.2.4.rc1)
globalid (>= 0.3.0)
activemodel (4.2.2)
activesupport (= 4.2.2)
activemodel (4.2.4.rc1)
activesupport (= 4.2.4.rc1)
builder (~> 3.1)
activerecord (4.2.2)
activemodel (= 4.2.2)
activesupport (= 4.2.2)
activerecord (4.2.4.rc1)
activemodel (= 4.2.4.rc1)
activesupport (= 4.2.4.rc1)
arel (~> 6.0)
activesupport (4.2.2)
activesupport (4.2.4.rc1)
i18n (~> 0.7)
json (~> 1.7, >= 1.7.7)
minitest (~> 5.1)
thread_safe (~> 0.3, >= 0.3.4)
tzinfo (~> 1.1)
rails (4.2.2)
actionmailer (= 4.2.2)
actionpack (= 4.2.2)
actionview (= 4.2.2)
activejob (= 4.2.2)
activemodel (= 4.2.2)
activerecord (= 4.2.2)
activesupport (= 4.2.2)
rails (4.2.4.rc1)
actionmailer (= 4.2.4.rc1)
actionpack (= 4.2.4.rc1)
actionview (= 4.2.4.rc1)
activejob (= 4.2.4.rc1)
activemodel (= 4.2.4.rc1)
activerecord (= 4.2.4.rc1)
activesupport (= 4.2.4.rc1)
bundler (>= 1.3.0, < 2.0)
railties (= 4.2.2)
railties (= 4.2.4.rc1)
sprockets-rails
railties (4.2.2)
actionpack (= 4.2.2)
activesupport (= 4.2.2)
railties (4.2.4.rc1)
actionpack (= 4.2.4.rc1)
activesupport (= 4.2.4.rc1)
rake (>= 0.8.7)
thor (>= 0.18.1, < 2.0)
......@@ -70,7 +70,7 @@ GEM
remote: https://rubygems.org/
specs:
amq-protocol (1.9.2)
arel (6.0.0)
arel (6.0.3)
backburner (0.4.6)
beaneater (~> 0.3.1)
dante (~> 0.1.5)
......@@ -101,7 +101,7 @@ GEM
delayed_job (>= 3.0, < 4.1)
erubis (2.7.0)
execjs (2.4.0)
globalid (0.3.5)
globalid (0.3.6)
activesupport (>= 4.1.0)
hitimes (1.2.2)
hitimes (1.2.2-x86-mingw32)
......@@ -198,9 +198,9 @@ GEM
serverengine
thor
thread
sprockets (3.2.0)
sprockets (3.0.3)
rack (~> 1.0)
sprockets-rails (2.3.1)
sprockets-rails (2.3.2)
actionpack (>= 3.0)
activesupport (>= 3.0)
sprockets (>= 2.8, < 4.0)
......@@ -280,4 +280,4 @@ DEPENDENCIES
w3c_validators
BUNDLED WITH
1.10.2
1.10.5
## Rails 4.2.4 (August 24, 2015) ##
* No Changes *
## Rails 4.2.3 (June 25, 2015) ##
* `assert_emails` in block form use the given number as expected value.
......
......@@ -7,7 +7,7 @@ def self.gem_version
module VERSION
MAJOR = 4
MINOR = 2
TINY = 3
TINY = 4
PRE = nil
STRING = [MAJOR, MINOR, TINY, PRE].compact.join(".")
......
## Rails 4.2.4 (August 24, 2015) ##
* ActionController::TestSession now accepts a default value as well as
a block for generating a default value based off the key provided.
This fixes calls to session#fetch in ApplicationController instances that
take more two arguments or a block from raising `ArgumentError: wrong
number of arguments (2 for 1)` when performing controller tests.
*Matthew Gerrior*
* Fix to keep original header instance in `ActionDispatch::SSL`
`ActionDispatch::SSL` changes headers to `Hash`.
So some headers will be broken if there are some middlewares
on `ActionDispatch::SSL` and if it uses `Rack::Utils::HeaderHash`.
*Fumiaki Matsushima*
## Rails 4.2.3 (June 25, 2015) ##
* Fix rake routes not showing the right format when
......
......@@ -183,7 +183,7 @@ class Base < Metal
# Shortcut helper that returns all the modules included in
# ActionController::Base except the ones passed as arguments:
#
# class MetalController
# class MyBaseController < ActionController::Metal
# ActionController::Base.without_modules(:ParamsWrapper, :Streaming).each do |left|
# include left
# end
......
......@@ -4,6 +4,7 @@ module ActionController #:nodoc:
module MimeResponds
extend ActiveSupport::Concern
# :stopdoc:
module ClassMethods
def respond_to(*)
raise NoMethodError, "The controller-level `respond_to' feature has " \
......@@ -21,6 +22,7 @@ def respond_with(*)
" gem 'responders', '~> 2.0'\n" \
"Consult the Rails upgrade guide for details."
end
# :startdoc:
# Without web-service support, an action which collects the data for displaying a list of people
# might look something like this:
......
......@@ -5,8 +5,8 @@
require 'action_dispatch/http/mime_type'
module ActionController
# Wraps the parameters hash into a nested hash. This will allow clients to submit
# POST requests without having to specify any root elements.
# Wraps the parameters hash into a nested hash. This will allow clients to
# submit requests without having to specify any root elements.
#
# This functionality is enabled in +config/initializers/wrap_parameters.rb+
# and can be customized. If you are upgrading to \Rails 3.1, this file will
......@@ -16,7 +16,7 @@ module ActionController
# a non-empty array:
#
# class UsersController < ApplicationController
# wrap_parameters format: [:json, :xml]
# wrap_parameters format: [:json, :xml, :url_encoded_form, :multipart_form]
# end
#
# If you enable +ParamsWrapper+ for +:json+ format, instead of having to
......
......@@ -327,6 +327,10 @@ def destroy
clear
end
def fetch(*args, &block)
@data.fetch(*args, &block)
end
private
def load!
......@@ -601,6 +605,7 @@ def process(action, http_method = 'GET', *args)
parameters = paramify_values(parameters) if html_format?(parameters)
@html_document = nil
@html_scanner_document = nil
unless @controller.respond_to?(:recycle!)
@controller.extend(Testing::Functional)
......
......@@ -28,7 +28,13 @@ def initialize(hash) # :nodoc:
raise(ArgumentError, ':tempfile is required') unless @tempfile
@original_filename = hash[:filename]
@original_filename &&= @original_filename.encode "UTF-8"
if @original_filename
begin
@original_filename.encode!(Encoding::UTF_8)
rescue EncodingError
@original_filename.force_encoding(Encoding::UTF_8)
end
end
@content_type = hash[:type]
@headers = hash[:head]
end
......
......@@ -121,7 +121,8 @@ def find_routes req
end
def match_head_routes(routes, req)
head_routes = match_routes(routes, req)
verb_specific_routes = routes.reject { |route| route.verb == // }
head_routes = match_routes(verb_specific_routes, req)
if head_routes.empty?
begin
......
......@@ -22,7 +22,7 @@ def call(env)
if request.ssl?
status, headers, body = @app.call(env)
headers = hsts_headers.merge(headers)
headers.reverse_merge!(hsts_headers)
flag_cookies_as_secure!(headers)
[status, headers, body]
else
......
......@@ -165,7 +165,7 @@ def with_routing
# ROUTES TODO: These assertions should really work in an integration context
def method_missing(selector, *args, &block)
if defined?(@controller) && @controller && @routes && @routes.named_routes.route_defined?(selector)
if defined?(@controller) && @controller && defined?(@routes) && @routes && @routes.named_routes.route_defined?(selector)
@controller.send(selector, *args, &block)
else
super
......
......@@ -301,6 +301,7 @@ def process(method, path, parameters = nil, headers_or_env = nil)
response = _mock_session.last_response
@response = ActionDispatch::TestResponse.from_response(response)
@html_document = nil
@html_scanner_document = nil
@url_options = nil
@controller = session.last_request.env['action_controller.instance']
......@@ -338,6 +339,7 @@ def remove! # :nodoc:
# reset the html_document variable, except for cookies/assigns calls
unless method == 'cookies' || method == 'assigns'
@html_document = nil
@html_scanner_document = nil
reset_template_assertion
end
......
......@@ -7,7 +7,7 @@ def self.gem_version
module VERSION
MAJOR = 4
MINOR = 2
TINY = 3
TINY = 4
PRE = nil
STRING = [MAJOR, MINOR, TINY, PRE].compact.join(".")
......
......@@ -64,6 +64,17 @@ def teardown
assert_equal 'contents', file.read
end
test "parses utf8 filename with percent character" do
params = parse_multipart('utf8_filename')
assert_equal %w(file foo), params.keys.sort
assert_equal 'bar', params['foo']
file = params['file']
assert_equal 'ファイル%名.txt', file.original_filename
assert_equal "text/plain", file.content_type
assert_equal 'contents', file.read
end
test "parses boundary problem file" do
params = parse_multipart('boundary_problem_file')
assert_equal %w(file foo), params.keys.sort
......
......@@ -3472,6 +3472,24 @@ def test_scope_shallow_path_is_not_overwritten_by_path
assert_equal '/bar/comments/1', comment_path('1')
end
def test_head_fetch_with_mount_on_root
draw do
get '/home' => 'test#index'
mount lambda { |env| [200, {}, [env['REQUEST_METHOD']]] }, at: '/'
end
# HEAD request should match `get /home` rather than the
# lower-precedence Rack app mounted at `/`.
head '/home'
assert_response :ok
assert_equal 'test#index', @response.body
# But the Rack app can still respond to its own HEAD requests.
head '/foobar'
assert_response :ok
assert_equal 'HEAD', @response.body
end
private
def draw(&block)
......
......@@ -40,4 +40,14 @@ def test_keys_and_values
assert_equal %w(one two), session.keys
assert_equal %w(1 2), session.values
end
def test_fetch_returns_default
session = ActionController::TestSession.new(one: '1')
assert_equal('2', session.fetch(:two, '2'))
end
def test_fetch_returns_block_value
session = ActionController::TestSession.new(one: '1')
assert_equal(2, session.fetch('2') { |key| key.to_i })
end
end
......@@ -216,4 +216,15 @@ def test_redirect_to_secure_subdomain_when_on_deep_subdomain
assert_equal "https://example.co.uk/path?key=value",
response.headers['Location']
end
def test_keeps_original_headers_behavior
headers = Rack::Utils::HeaderHash.new(
"Content-Type" => "text/html",
"Connection" => ["close"]
)
self.app = ActionDispatch::SSL.new(lambda { |env| [200, headers, ["OK"]] })
get "https://example.org/"
assert_equal "close", response.headers["Connection"]
end
end
--AaB03x
Content-Disposition: form-data; name="foo"
bar
--AaB03x
Content-Disposition: form-data; name="file"; filename="ファイル%名.txt"
Content-Type: text/plain
contents
--AaB03x--
## Rails 4.2.4 (August 24, 2015) ##
* No Changes *
## Rails 4.2.3 (June 25, 2015) ##
* `translate` should handle `raise` flag correctly in case of both main and default
......@@ -21,7 +26,6 @@
*Justin Coyne*
* `number_to_percentage` does not crash with `Float::NAN` or `Float::INFINITY`
as input when `precision: 0` is used.
......
......@@ -7,7 +7,7 @@ def self.gem_version
module VERSION
MAJOR = 4
MINOR = 2
TINY = 3
TINY = 4
PRE = nil
STRING = [MAJOR, MINOR, TINY, PRE].compact.join(".")
......
......@@ -463,7 +463,8 @@ def mail_to(email_address, name = nil, html_options = {}, &block)
}.compact
extras = extras.empty? ? '' : '?' + extras.join('&')
html_options["href"] = "mailto:#{email_address}#{extras}"
encoded_email_address = ERB::Util.url_encode(email_address).gsub("%40", "@")
html_options["href"] = "mailto:#{encoded_email_address}#{extras}"
content_tag(:a, name || email_address, html_options, &block)
end
......
......@@ -241,7 +241,8 @@ def view
:@view,
:@view_context_class,
:@_subscribers,
:@html_document
:@html_document,
:@html_scanner_document
]
def _user_defined_ivars
......
......@@ -501,6 +501,13 @@ def test_mail_to
mail_to("david@loudthinking.com", "David Heinemeier Hansson", class: "admin")
end
def test_mail_to_with_special_characters
assert_dom_equal(
%{<a href="mailto:%23%21%24%25%26%27%2A%2B-%2F%3D%3F%5E_%60%7B%7D%7C%7E@example.org">#!$%&amp;&#39;*+-/=?^_`{}|~@example.org</a>},
mail_to("#!$%&'*+-/=?^_`{}|~@example.org")
)
end
def test_mail_with_options
assert_dom_equal(
%{<a href="mailto:me@example.com?cc=ccaddress%40example.com&amp;bcc=bccaddress%40example.com&amp;body=This%20is%20the%20body%20of%20the%20message.&amp;subject=This%20is%20an%20example%20email">My email</a>},
......
## Rails 4.2.4 (August 24, 2015) ##
* Include I18n.locale into job serialization/deserialization and use it around
`perform`.
Fixes #20799.
*Johannes Opper*
## Rails 4.2.3 (June 25, 2015) ##
* `assert_enqueued_jobs` and `assert_performed_jobs` in block form use the
......
......@@ -5,6 +5,7 @@
require 'active_job/execution'
require 'active_job/callbacks'
require 'active_job/logging'
require 'active_job/translation'
module ActiveJob #:nodoc:
# = Active Job
......@@ -60,6 +61,7 @@ class Base
include Execution
include Callbacks
include Logging
include Translation
ActiveSupport.run_load_hooks(:active_job, self)
end
......
......@@ -15,6 +15,9 @@ module Core
# Queue in which the job will reside.
attr_writer :queue_name
# I18n.locale to be used during the job.
attr_accessor :locale
end
# These methods will be included into any Active Job object, adding
......@@ -26,6 +29,7 @@ def deserialize(job_data)
job.job_id = job_data['job_id']
job.queue_name = job_data['queue_name']
job.serialized_arguments = job_data['arguments']
job.locale = job_data['locale'] || I18n.locale
job
end
......@@ -65,7 +69,8 @@ def serialize
'job_class' => self.class.name,
'job_id' => job_id,
'queue_name' => queue_name,
'arguments' => serialize_arguments(arguments)
'arguments' => serialize_arguments(arguments),
'locale' => I18n.locale
}
end
......
......@@ -7,7 +7,7 @@ def self.gem_version
module VERSION
MAJOR = 4
MINOR = 2
TINY = 3
TINY = 4
PRE = nil
STRING = [MAJOR, MINOR, TINY, PRE].compact.join(".")
......
......@@ -15,23 +15,22 @@ module ActiveJob
#
# === Backends Features
#
# | | Async | Queues | Delayed | Priorities | Timeout | Retries |
# |-------------------|-------|--------|-----------|------------|---------|---------|
# | Backburner | Yes | Yes | Yes | Yes | Job | Global |
# | Delayed Job | Yes | Yes | Yes | Job | Global | Global |
# | Qu | Yes | Yes | No | No | No | Global |
# | Que | Yes | Yes | Yes | Job | No | Job |
# | queue_classic | Yes | Yes | No* | No | No | No |
# | Resque | Yes | Yes | Yes (Gem) | Queue | Global | Yes |
# | Sidekiq | Yes | Yes | Yes | Queue | No | Job |
# | Sneakers | Yes | Yes | No | Queue | Queue | No |
# | Sucker Punch | Yes | Yes | No | No | No | No |
# | Active Job Inline | No | Yes | N/A | N/A | N/A | N/A |
# | | Async | Queues | Delayed | Priorities | Timeout | Retries |
# |-------------------|-------|--------|------------|------------|---------|---------|
# | Backburner | Yes | Yes | Yes | Yes | Job | Global |
# | Delayed Job | Yes | Yes | Yes | Job | Global | Global |
# | Qu | Yes | Yes | No | No | No | Global |
# | Que | Yes | Yes | Yes | Job | No | Job |
# | queue_classic | Yes | Yes | Yes* | No | No | No |
# | Resque | Yes | Yes | Yes (Gem) | Queue | Global | Yes |
# | Sidekiq | Yes | Yes | Yes | Queue | No | Job |
# | Sneakers | Yes | Yes | No | Queue | Queue | No |
# | Sucker Punch | Yes | Yes | No | No | No | No |
# | Active Job Inline | No | Yes | N/A | N/A | N/A | N/A |
#
# NOTE:
# queue_classic does not support Job scheduling. However you can implement this
# yourself or you can use the queue_classic-later gem. See the documentation for
# ActiveJob::QueueAdapters::QueueClassicAdapter.
# queue_classic supports job scheduling since version 3.1.
# For older versions you can use the queue_classic-later gem.
#
module QueueAdapters
extend ActiveSupport::Autoload
......
module ActiveJob
module Translation #:nodoc:
extend ActiveSupport::Concern
included do
around_perform do |job, block, _|
I18n.with_locale(job.locale, &block)
end
end
end
end
require 'helper'
require 'jobs/gid_job'
require 'jobs/hello_job'
require 'models/person'
class JobSerializationTest < ActiveSupport::TestCase
......@@ -12,4 +13,18 @@ class JobSerializationTest < ActiveSupport::TestCase
GidJob.perform_later @person
assert_equal "Person with ID: 5", JobBuffer.last_value
end
test 'serialize includes current locale' do
assert_equal :en, HelloJob.new.serialize['locale']
end
test 'deserialize sets locale' do
job = HelloJob.deserialize 'job_class' => 'HelloJob', 'locale' => :es
assert_equal :es, job.locale
end
test 'deserialize sets default locale' do
job = HelloJob.deserialize 'job_class' => 'HelloJob'
assert_equal :en, job.locale
end
end
require 'helper'
require 'jobs/translated_hello_job'
class TranslationTest < ActiveSupport::TestCase
setup do
JobBuffer.clear
I18n.available_locales = [:en, :de]
@job = TranslatedHelloJob.new('Johannes')
end
teardown do
I18n.available_locales = [:en]
end
test 'it performs the job in the given locale' do
@job.locale = :de
@job.perform_now
assert_equal "Johannes says Guten Tag", JobBuffer.last_value
end
end
......@@ -57,4 +57,21 @@ class QueuingTest < ActiveSupport::TestCase
skip
end
end
test 'current locale is kept while running perform_later' do
skip if adapter_is?(:inline)
begin
I18n.available_locales = [:en, :de]
I18n.locale = :de
TestJob.perform_later @id
wait_for_jobs_to_finish_for(5.seconds)
assert job_executed
assert_equal 'de', job_output
ensure
I18n.available_locales = [:en]
I18n.locale = :en
end
end
end
require_relative '../support/job_buffer'
class TranslatedHelloJob < ActiveJob::Base
def perform(greeter = "David")
translations = { en: 'Hello', de: 'Guten Tag' }
hello = translations[I18n.locale]
JobBuffer.add("#{greeter} says #{hello}")
end
end
......@@ -8,13 +8,17 @@
JobsManager.current_manager.setup
CODE
initializer 'i18n.rb', <<-CODE
I18n.available_locales = [:en, :de]
CODE
file 'app/jobs/test_job.rb', <<-CODE
class TestJob < ActiveJob::Base
queue_as :integration_tests