Skip to content

Commit e9d7ca5

Browse files
authored
Merge pull request rails#54777 from Shopify/load_lazy_routes_in_test
Load lazy route set before inserting test routes
2 parents 87b32b7 + 4c629b6 commit e9d7ca5

File tree

3 files changed

+60
-2
lines changed

3 files changed

+60
-2
lines changed

actionpack/CHANGELOG.md

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,10 @@
1+
* Load lazy route sets before inserting test routes
2+
3+
Without loading lazy route sets early, we miss `after_routes_loaded` callbacks, or risk
4+
invoking them with the test routes instead of the real ones if another load is triggered by an engine.
5+
6+
*Gannon McGibbon*
7+
18
* Raise `AbstractController::DoubleRenderError` if `head` is called after rendering.
29

310
After this change, invoking `head` will lead to an error if response body is already set:

actionpack/lib/action_dispatch/testing/assertions/routing.rb

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -25,7 +25,7 @@ def with_routing(&block)
2525
old_integration_session = nil
2626

2727
setup do
28-
old_routes = app.routes
28+
old_routes = initialize_lazy_routes(app.routes)
2929
old_routes_call_method = old_routes.method(:call)
3030
old_integration_session = integration_session
3131
create_routes(&block)
@@ -38,7 +38,7 @@ def with_routing(&block)
3838
end
3939

4040
def with_routing(&block)
41-
old_routes = app.routes
41+
old_routes = initialize_lazy_routes(app.routes)
4242
old_routes_call_method = old_routes.method(:call)
4343
old_integration_session = integration_session
4444
create_routes(&block)
@@ -47,6 +47,14 @@ def with_routing(&block)
4747
end
4848

4949
private
50+
def initialize_lazy_routes(routes)
51+
if defined?(Rails::Engine::LazyRouteSet) && routes.is_a?(Rails::Engine::LazyRouteSet)
52+
routes.tap(&:routes)
53+
else
54+
routes
55+
end
56+
end
57+
5058
def create_routes
5159
app = self.app
5260
routes = ActionDispatch::Routing::RouteSet.new

railties/test/application/integration_test_case_test.rb

Lines changed: 43 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -72,5 +72,48 @@ def test_app_returns_action_dispatch_test_app_by_default
7272
output = rails("test")
7373
assert_match(/0 failures, 0 errors/, output)
7474
end
75+
76+
test "routes are loaded before inserting test routes" do
77+
app_file "config/routes.rb", <<-RUBY
78+
Rails.application.routes.draw do
79+
get "/c", as: :c, to: "users#show"
80+
end
81+
RUBY
82+
83+
app_file "config/initializers/after_routes_loaded.rb", <<-RUBY
84+
Rails.configuration.after_routes_loaded do
85+
$after_routes_loaded = true
86+
end
87+
RUBY
88+
89+
app_file "app/controllers/users_controller.rb", <<-RUBY
90+
class UsersController < ActionController::Base
91+
def index
92+
render json: { loaded: $after_routes_loaded }
93+
end
94+
end
95+
RUBY
96+
97+
app_file "test/controllers/users_controller_test.rb", <<-RUBY
98+
require "test_helper"
99+
100+
class UsersControllerTest < ActionDispatch::IntegrationTest
101+
with_routing do |set|
102+
set.draw do
103+
resources(:users, only: :index)
104+
end
105+
end
106+
107+
test "lazy route loading" do
108+
get("/users")
109+
110+
assert_equal({ "loaded" => true }, JSON.parse(response.body))
111+
end
112+
end
113+
RUBY
114+
115+
output = rails("test")
116+
assert_match(/0 failures, 0 errors/, output)
117+
end
75118
end
76119
end

0 commit comments

Comments
 (0)