1
0
Fork 0
mirror of https://github.com/rails/rails.git synced 2022-11-09 12:12:34 -05:00

Merge pull request #23225 from vipulnsward/20420-rake-routes-options

Add options for rake routes task
This commit is contained in:
Kasper Timm Hansen 2016-02-01 22:09:22 +01:00
commit baae952588
7 changed files with 163 additions and 30 deletions

View file

@ -1,3 +1,13 @@
* Add `-g` and `-c` (short for _grep_ and _controller_ respectively) options
to `bin/rake routes`. These options return the url `name`, `verb` and
`path` field that match the pattern or match a specific controller.
Deprecate `CONTROLLER` env variable in `bin/rake routes`.
See #18902.
*Anton Davydov* & *Vipul A M*
* Response etags to always be weak: Prefixes 'W/' to value returned by
`ActionDispatch::Http::Cache::Response#etag=`, such that etags set in
`fresh_when` and `stale?` are weak.

View file

@ -239,7 +239,8 @@ module ActionDispatch
#
# rails routes
#
# Target specific controllers by prefixing the command with <tt>CONTROLLER=x</tt>.
# Target specific controllers by prefixing the command with <tt>--controller</tt> option
# - or its <tt>-c</tt> shorthand.
#
module Routing
extend ActiveSupport::Autoload

View file

@ -60,12 +60,11 @@ module ActionDispatch
end
def format(formatter, filter = nil)
routes_to_display = filter_routes(filter)
filter_options = normalize_filter(filter)
routes_to_display = filter_routes(filter_options)
routes = collect_routes(routes_to_display)
if routes.none?
formatter.no_routes(collect_routes(@routes), filter)
formatter.no_routes(collect_routes(@routes))
return formatter.result
end
@ -82,10 +81,21 @@ module ActionDispatch
private
def filter_routes(filter)
if filter
filter_name = filter.underscore.sub(/_controller$/, '')
@routes.select { |route| route.defaults[:controller] == filter_name }
def normalize_filter(filter)
if filter.is_a?(Hash) && filter[:controller]
{controller: /#{filter[:controller].downcase.sub(/_?controller\z/, '').sub('::', '/')}/}
elsif filter.is_a?(String)
{controller: /#{filter}/, action: /#{filter}/}
else
nil
end
end
def filter_routes(filter_options)
if filter_options
@routes.select do |route|
filter_options.any? { |default, filter| route.defaults[default] =~ filter }
end
else
@routes
end
@ -137,7 +147,7 @@ module ActionDispatch
@buffer << draw_header(routes)
end
def no_routes(routes, filter)
def no_routes(routes)
@buffer <<
if routes.none?
<<-MESSAGE.strip_heredoc
@ -145,8 +155,6 @@ module ActionDispatch
Please add some routes in config/routes.rb.
MESSAGE
elsif missing_controller?(filter)
"The controller #{filter} does not exist!"
else
"No routes were found for this controller"
end
@ -154,10 +162,6 @@ module ActionDispatch
end
private
def missing_controller?(controller_name)
[ controller_name.camelize, "#{controller_name.camelize}Controller" ].none?(&:safe_constantize)
end
def draw_section(routes)
header_lengths = ['Prefix', 'Verb', 'URI Pattern'].map(&:length)
name_width, verb_width, path_width = widths(routes).zip(header_lengths).map(&:max)

View file

@ -17,10 +17,10 @@ module ActionDispatch
@set = ActionDispatch::Routing::RouteSet.new
end
def draw(options = {}, &block)
def draw(options = nil, &block)
@set.draw(&block)
inspector = ActionDispatch::Routing::RoutesInspector.new(@set.routes)
inspector.format(ActionDispatch::Routing::ConsoleFormatter.new, options[:filter]).split("\n")
inspector.format(ActionDispatch::Routing::ConsoleFormatter.new, options).split("\n")
end
def test_displaying_routes_for_engines
@ -297,7 +297,7 @@ module ActionDispatch
end
def test_routes_can_be_filtered
output = draw(filter: 'posts') do
output = draw('posts') do
resources :articles
resources :posts
end
@ -313,6 +313,26 @@ module ActionDispatch
" DELETE /posts/:id(.:format) posts#destroy"], output
end
def test_routes_can_be_filtered_with_namespaced_controllers
output = draw('admin/posts') do
resources :articles
namespace :admin do
resources :posts
end
end
assert_equal [" Prefix Verb URI Pattern Controller#Action",
" admin_posts GET /admin/posts(.:format) admin/posts#index",
" POST /admin/posts(.:format) admin/posts#create",
" new_admin_post GET /admin/posts/new(.:format) admin/posts#new",
"edit_admin_post GET /admin/posts/:id/edit(.:format) admin/posts#edit",
" admin_post GET /admin/posts/:id(.:format) admin/posts#show",
" PATCH /admin/posts/:id(.:format) admin/posts#update",
" PUT /admin/posts/:id(.:format) admin/posts#update",
" DELETE /admin/posts/:id(.:format) admin/posts#destroy"], output
end
def test_regression_route_with_controller_regexp
output = draw do
get ':controller(/:action)', controller: /api\/[^\/]+/, format: false
@ -336,18 +356,18 @@ module ActionDispatch
end
def test_routes_with_undefined_filter
output = draw(:filter => 'Rails::MissingController') do
output = draw(controller: 'Rails::MissingController') do
get 'photos/:id' => 'photos#show', :id => /[A-Z]\d{5}/
end
assert_equal [
"The controller Rails::MissingController does not exist!",
"No routes were found for this controller",
"For more information about routes, see the Rails guide: http://guides.rubyonrails.org/routing.html."
], output
end
def test_no_routes_matched_filter
output = draw(:filter => 'rails/dummy') do
output = draw('rails/dummy') do
get 'photos/:id' => 'photos#show', :id => /[A-Z]\d{5}/
end
@ -358,7 +378,7 @@ module ActionDispatch
end
def test_no_routes_were_defined
output = draw(:filter => 'Rails::DummyController') { }
output = draw('Rails::DummyController') {}
assert_equal [
"You don't have any routes defined!",

View file

@ -1136,10 +1136,21 @@ For example, here's a small section of the `rails routes` output for a RESTful r
edit_user GET /users/:id/edit(.:format) users#edit
```
You may restrict the listing to the routes that map to a particular controller setting the `CONTROLLER` environment variable:
You can search through your routes with the --grep option (-g for short). This outputs any routes that partially match the URL helper method name, the HTTP verb, or the URL path.
```bash
$ CONTROLLER=users bin/rails routes
```
$ bin/rake routes --grep new_comment
$ bin/rake routes -g POST
$ bin/rake routes -g admin
```
If you only want to see the routes that map to a specific controller, there's the --controller option (-c for short).
```
$ bin/rake routes --controller users
$ bin/rake routes --controller admin/users
$ bin/rake routes -c Comments
$ bin/rake routes -c Articles::CommentsController
```
TIP: You'll find that the output from `rails routes` is much more readable if you widen your terminal window until the output lines don't wrap.

View file

@ -1,7 +1,35 @@
desc 'Print out all defined routes in match order, with names. Target specific controller with CONTROLLER=x.'
require 'active_support/deprecation'
require 'active_support/core_ext/string/strip' # for strip_heredoc
require 'optparse'
desc 'Print out all defined routes in match order, with names. Target specific controller with --controller option - or its -c shorthand.'
task routes: :environment do
all_routes = Rails.application.routes.routes
require 'action_dispatch/routing/inspector'
inspector = ActionDispatch::Routing::RoutesInspector.new(all_routes)
puts inspector.format(ActionDispatch::Routing::ConsoleFormatter.new, ENV['CONTROLLER'])
if ARGV.any?{ |argv| argv.start_with? 'CONTROLLER' }
puts <<-eow.strip_heredoc
Passing `CONTROLLER` to `bin/rake routes` is deprecated and will be removed in Rails 5.1.
Please use `bin/rake routes -c controller_name` instead.
eow
end
routes_filter = nil
routes_filter = {controller: ENV['CONTROLLER']} if ENV['CONTROLLER']
OptionParser.new do |opts|
opts.banner = "Usage: rake routes [options]"
opts.on("-c", "--controller [CONTROLLER]") do |controller|
routes_filter = { controller: controller }
end
opts.on("-g", "--grep [PATTERN]") do |pattern|
routes_filter = pattern
end
end.parse!(ARGV.reject { |x| x == "routes" })
puts inspector.format(ActionDispatch::Routing::ConsoleFormatter.new, routes_filter)
exit 0 # ensure extra arguments aren't interpreted as Rake tasks
end

View file

@ -141,8 +141,67 @@ module ApplicationTests
end
RUBY
ENV['CONTROLLER'] = 'cart'
output = Dir.chdir(app_path){ `bin/rails routes` }
output = Dir.chdir(app_path){ `bin/rake routes CONTROLLER=cart` }
assert_equal ["Passing `CONTROLLER` to `bin/rake routes` is deprecated and will be removed in Rails 5.1.",
"Please use `bin/rake routes -c controller_name` instead.",
"Prefix Verb URI Pattern Controller#Action",
" cart GET /cart(.:format) cart#show\n"].join("\n"), output
output = Dir.chdir(app_path){ `bin/rails routes -c cart` }
assert_equal "Prefix Verb URI Pattern Controller#Action\n cart GET /cart(.:format) cart#show\n", output
end
def test_rake_routes_with_namespaced_controller_environment
app_file "config/routes.rb", <<-RUBY
Rails.application.routes.draw do
namespace :admin do
resource :post
end
end
RUBY
expected_output = [" Prefix Verb URI Pattern Controller#Action",
" admin_post POST /admin/post(.:format) admin/posts#create",
" new_admin_post GET /admin/post/new(.:format) admin/posts#new",
"edit_admin_post GET /admin/post/edit(.:format) admin/posts#edit",
" GET /admin/post(.:format) admin/posts#show",
" PATCH /admin/post(.:format) admin/posts#update",
" PUT /admin/post(.:format) admin/posts#update",
" DELETE /admin/post(.:format) admin/posts#destroy\n"].join("\n")
output = Dir.chdir(app_path){ `bin/rails routes -c Admin::PostController` }
assert_equal expected_output, output
output = Dir.chdir(app_path){ `bin/rails routes -c PostController` }
assert_equal expected_output, output
end
def test_rake_routes_with_global_search_key
app_file "config/routes.rb", <<-RUBY
Rails.application.routes.draw do
get '/cart', to: 'cart#show'
get '/basketball', to: 'basketball#index'
end
RUBY
output = Dir.chdir(app_path){ `bin/rake routes -g show` }
assert_equal "Prefix Verb URI Pattern Controller#Action\n cart GET /cart(.:format) cart#show\n", output
end
def test_rake_routes_with_controller_search_key
app_file "config/routes.rb", <<-RUBY
Rails.application.routes.draw do
get '/cart', to: 'cart#show'
get '/basketball', to: 'basketball#index'
end
RUBY
output = Dir.chdir(app_path){ `bin/rake routes -c cart` }
assert_equal "Prefix Verb URI Pattern Controller#Action\n cart GET /cart(.:format) cart#show\n", output
output = Dir.chdir(app_path){ `bin/rake routes -c Cart` }
assert_equal "Prefix Verb URI Pattern Controller#Action\n cart GET /cart(.:format) cart#show\n", output
output = Dir.chdir(app_path){ `bin/rake routes -c CartController` }
assert_equal "Prefix Verb URI Pattern Controller#Action\n cart GET /cart(.:format) cart#show\n", output
end