Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Show default help when calling help outside a Rails application #41425

Closed
wants to merge 1 commit into from
Closed

Show default help when calling help outside a Rails application #41425

wants to merge 1 commit into from

Conversation

p8
Copy link
Member

@p8 p8 commented Feb 12, 2021

Summary

When running rails -h or just rails outside a Rails application,
Rails outputs all options for running the rails new command. This can be
confusing to users when they probably want to see the common Rails commands.

Instead, we should always show the common commands when running rails -h
inside or outside a Rails application.

With this change help works as follows...

Outside a Rails application we always show the default help when calling rails
without a command like new.
We never show the extended commands: db:migrate, etc...
The extended commands require a Rails application.
They also take up a lot screen space.

  • rails outputs the help for the common commands
  • rails -h outputs the help for the common commands.
  • rails new -h outputs the help for the new command.

Inside a Rails application it works mostly as before. The only change is
that calling plain bin/rails now only outputs the common commands and
not the extended commands.

  • bin/rails outputs the help for the common commands
  • bin/rails -h outputs the help for the common commands and the
    extended commands

This is a work in progress for #40823
cc @olivierlacan

@rails-bot rails-bot bot added the railties label Feb 12, 2021
railties/lib/rails/command.rb Outdated Show resolved Hide resolved
railties/lib/rails/command.rb Outdated Show resolved Hide resolved
@@ -1009,7 +1009,7 @@ def test_skip_webpack_install
assert_no_file "config/webpacker.yml"

output = Dir.chdir(destination_root) do
`bin/rails help`
`bin/rails -h`
Copy link
Member Author

@p8 p8 Feb 13, 2021

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

bin/rails help no longer outputs the extended commands (just the common commands ). So this had to be changed to bin/rails -h which does output the extended commands.

@p8 p8 changed the title Default help to only show common commands Always show default help when calling help without a command Feb 13, 2021
@p8 p8 changed the title Always show default help when calling help without a command Show default help when calling help outside a Rails application Feb 13, 2021
@p8 p8 marked this pull request as ready for review February 13, 2021 16:06
Comment on lines 35 to 39
if char = namespace =~ /:(\w+)$/
command_name, namespace = $1, namespace.slice(0, char)
elsif namespace.blank?
command_name, namespace = "help", "help"
elsif HELP_MAPPINGS.include?(namespace)
command_name, namespace = "help_extended", "help"
elsif VERSION_MAPPINGS.include?(namespace)
command_name, namespace = "version", "version"
else
command_name = namespace
end
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If HELP_MAPPINGS and VERSION_MAPPINGS were Sets or Regexps, we could write:

Suggested change
if char = namespace =~ /:(\w+)$/
command_name, namespace = $1, namespace.slice(0, char)
elsif namespace.blank?
command_name, namespace = "help", "help"
elsif HELP_MAPPINGS.include?(namespace)
command_name, namespace = "help_extended", "help"
elsif VERSION_MAPPINGS.include?(namespace)
command_name, namespace = "version", "version"
else
command_name = namespace
end
case namespace
when /^(.+):(\w+)$/
namespace, command_name = $1, $2
when ""
namespace, command_name = "help", "help"
when HELP_MAPPINGS
namespace, command_name = "help", "help_extended"
when VERSION_MAPPINGS
namespace, command_name = "version", "version"

Also, it might be good to factor this out into a method like split_command_name or split_namespace_and_command_name which would return a [namespace, command_name] pair.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ah, that looks very nice. 👍
I've extracted it to a split_namespace method.

@olivierlacan
Copy link
Contributor

Checking back in on this @p8. Do you need any help getting it across the finish line?

@p8
Copy link
Member Author

p8 commented May 11, 2021

Hi @olivierlacan, sorry for not getting back to you when this issue was raised. 🙇

I think this PR is good to go but more reviews are welcome 😄
Maybe some things are still unclear?
Could you maybe test it to see if this the expected behaviour?

I've rebased the PR to main and I'll add some screenshots for extra clarity.

BTW the USAGE file is printed on the following line:


The definition of desc is here:
def desc(usage = nil, description = nil, options = {})

@olivierlacan
Copy link
Contributor

Comparing to 6.1.3.

6.1.3.2

Outside of a Rails app directory:

$ rails -v
Rails 6.1.3.2
in perso
$ rails -h # or rails help
Usage:
  rails new APP_PATH [options]

Options:
      [--skip-namespace], [--no-skip-namespace]              # Skip namespace (affects only isolated engines)
      [--skip-collision-check], [--no-skip-collision-check]  # Skip collision check
  -r, [--ruby=PATH]                                          # Path to the Ruby binary of your choice
                                                             # Default: /Users/olivierlacan/.rbenv/versions/3.0.1/bin/ruby
  -m, [--template=TEMPLATE]                                  # Path to some application template (can be a filesystem path or URL)
  -d, [--database=DATABASE]                                  # Preconfigure for selected database (options: mysql/postgresql/sqlite3/oracle/sqlserver/jdbcmysql/jdbcsqlite3/jdbcpostgresql/jdbc)
                                                             # Default: sqlite3
      [--skip-gemfile], [--no-skip-gemfile]                  # Don't create a Gemfile
  -G, [--skip-git], [--no-skip-git]                          # Skip .gitignore file
      [--skip-keeps], [--no-skip-keeps]                      # Skip source control .keep files
  -M, [--skip-action-mailer], [--no-skip-action-mailer]      # Skip Action Mailer files
      [--skip-action-mailbox], [--no-skip-action-mailbox]    # Skip Action Mailbox gem
      [--skip-action-text], [--no-skip-action-text]          # Skip Action Text gem
  -O, [--skip-active-record], [--no-skip-active-record]      # Skip Active Record files
      [--skip-active-job], [--no-skip-active-job]            # Skip Active Job
      [--skip-active-storage], [--no-skip-active-storage]    # Skip Active Storage files
  -P, [--skip-puma], [--no-skip-puma]                        # Skip Puma related files
  -C, [--skip-action-cable], [--no-skip-action-cable]        # Skip Action Cable files
  -S, [--skip-sprockets], [--no-skip-sprockets]              # Skip Sprockets files
      [--skip-spring], [--no-skip-spring]                    # Don't install Spring application preloader
      [--skip-listen], [--no-skip-listen]                    # Don't generate configuration that depends on the listen gem
  -J, [--skip-javascript], [--no-skip-javascript]            # Skip JavaScript files
      [--skip-turbolinks], [--no-skip-turbolinks]            # Skip turbolinks gem
      [--skip-jbuilder], [--no-skip-jbuilder]                # Skip jbuilder gem
  -T, [--skip-test], [--no-skip-test]                        # Skip test files
      [--skip-system-test], [--no-skip-system-test]          # Skip system test files
      [--skip-bootsnap], [--no-skip-bootsnap]                # Skip bootsnap gem
      [--dev], [--no-dev]                                    # Set up the application with Gemfile pointing to your Rails checkout
      [--edge], [--no-edge]                                  # Set up the application with Gemfile pointing to Rails repository
      [--master], [--no-master]                              # Set up the application with Gemfile pointing to Rails repository main branch
      [--rc=RC]                                              # Path to file containing extra configuration options for rails command
      [--no-rc], [--no-no-rc]                                # Skip loading of extra configuration options from .railsrc file
      [--api], [--no-api]                                    # Preconfigure smaller stack for API only apps
      [--minimal], [--no-minimal]                            # Preconfigure a minimal rails app
  -B, [--skip-bundle], [--no-skip-bundle]                    # Don't run bundle install
  --webpacker, [--webpack=WEBPACK]                           # Preconfigure Webpack with a particular framework (options: react, vue, angular, elm, stimulus)
      [--skip-webpack-install], [--no-skip-webpack-install]  # Don't run Webpack install

Runtime options:
  -f, [--force]                    # Overwrite files that already exist
  -p, [--pretend], [--no-pretend]  # Run but do not make any changes
  -q, [--quiet], [--no-quiet]      # Suppress status output
  -s, [--skip], [--no-skip]        # Skip files that already exist

Rails options:
  -h, [--help], [--no-help]        # Show this help message and quit
  -v, [--version], [--no-version]  # Show Rails version number and quit

Description:
    The 'rails new' command creates a new Rails application with a default
    directory structure and configuration at the path you specify.

    You can specify extra command-line arguments to be used every time
    'rails new' runs in the .railsrc configuration file in your home directory,
    or in $XDG_CONFIG_HOME/rails/railsrc if XDG_CONFIG_HOME is set.

    Note that the arguments specified in the .railsrc file don't affect the
    defaults values shown above in this help message.

Example:
    rails new ~/Code/Ruby/weblog

    This generates a skeletal Rails installation in ~/Code/Ruby/weblog.

Inside of a Rails app directory:

$ rails -h
The most common rails commands are:
 generate     Generate new code (short-cut alias: "g")
 console      Start the Rails console (short-cut alias: "c")
 server       Start the Rails server (short-cut alias: "s")
 test         Run tests except system tests (short-cut alias: "t")
 test:system  Run system tests
 dbconsole    Start a console for the database specified in config/database.yml
              (short-cut alias: "db")

 new          Create a new Rails application. "rails new my_app" creates a
              new application called MyApp in "./my_app"


All commands can be run with -h (or --help) for more information.
In addition to those commands, there are:

  about
  action_mailbox:ingress:exim
  action_mailbox:ingress:postfix
  action_mailbox:ingress:qmail
  action_mailbox:install
  action_mailbox:install:migrations
  action_text:install
  action_text:install:migrations
  active_storage:install
  app:template
  app:update
  assets:clean[keep]
  assets:clobber
  assets:environment
  assets:precompile
  cache_digests:dependencies
  cache_digests:nested_dependencies
  credentials:diff
  credentials:edit
  credentials:show
  db:create
  db:drop
  db:environment:set
  db:fixtures:load
  db:migrate
  db:migrate:down
  db:migrate:redo
  db:migrate:status
  db:migrate:up
  db:prepare
  db:reset
  db:rollback
  db:schema:cache:clear
  db:schema:cache:dump
  db:schema:dump
  db:schema:load
  db:seed
  db:seed:replant
  db:setup
  db:structure:dump
  db:structure:load
  db:system:change
  db:version
  destroy
  dev:cache
  encrypted:edit
  encrypted:show
  initializers
  log:clear
  middleware
  notes
  restart
  routes
  runner
  secret
  secrets:edit
  secrets:setup
  secrets:show
  spec
  spec:helpers
  spec:models
  spec:requests
  spec:routing
  spec:views
  stats
  test:all
  test:db
  time:zones[country_or_offset]
  tmp:clear
  tmp:create
  version
  webpacker
  webpacker:binstubs
  webpacker:check_binstubs
  webpacker:check_node
  webpacker:check_yarn
  webpacker:clean[keep,age]
  webpacker:clobber
  webpacker:compile
  webpacker:info
  webpacker:install
  webpacker:install:angular
  webpacker:install:coffee
  webpacker:install:elm
  webpacker:install:erb
  webpacker:install:react
  webpacker:install:stimulus
  webpacker:install:svelte
  webpacker:install:typescript
  webpacker:install:vue
  webpacker:verify_install
  webpacker:yarn_install
  yarn:install
  zeitwerk:check

This PR

Outside of a Rails app directory:

$ ruby railties/exe/rails -h
The most common rails commands are:
 generate     Generate new code (short-cut alias: "g")
 console      Start the Rails console (short-cut alias: "c")
 server       Start the Rails server (short-cut alias: "s")
 test         Run tests except system tests (short-cut alias: "t")
 test:system  Run system tests
 dbconsole    Start a console for the database specified in config/database.yml
              (short-cut alias: "db")
 new          Create a new Rails application. "rails new my_app" creates a
              new application called MyApp in "./my_app"

All commands can be run with -h (or --help) for more information.

Inside of a rails app directory:

$ ruby /Users/olivierlacan/Development/oss/rails/railties/exe/rails -h
The most common rails commands are:
 generate     Generate new code (short-cut alias: "g")
 console      Start the Rails console (short-cut alias: "c")
 server       Start the Rails server (short-cut alias: "s")
 test         Run tests except system tests (short-cut alias: "t")
 test:system  Run system tests
 dbconsole    Start a console for the database specified in config/database.yml
              (short-cut alias: "db")

 new          Create a new Rails application. "rails new my_app" creates a
              new application called MyApp in "./my_app"


All commands can be run with -h (or --help) for more information.
In addition to those commands, there are:

  about
  action_mailbox:ingress:exim
  action_mailbox:ingress:postfix
  action_mailbox:ingress:qmail
  action_mailbox:install
  action_mailbox:install:migrations
  action_text:install
  action_text:install:migrations
  active_storage:install
  app:template
  app:update
  assets:clean[keep]
  assets:clobber
  assets:environment
  assets:precompile
  cache_digests:dependencies
  cache_digests:nested_dependencies
  credentials:diff
  credentials:edit
  credentials:show
  db:create
  db:drop
  db:environment:set
  db:fixtures:load
  db:migrate
  db:migrate:down
  db:migrate:redo
  db:migrate:status
  db:migrate:up
  db:prepare
  db:reset
  db:rollback
  db:schema:cache:clear
  db:schema:cache:dump
  db:schema:dump
  db:schema:load
  db:seed
  db:seed:replant
  db:setup
  db:structure:dump
  db:structure:load
  db:system:change
  db:version
  destroy
  dev:cache
  encrypted:edit
  encrypted:show
  initializers
  log:clear
  middleware
  notes
  restart
  routes
  runner
  secret
  secrets:edit
  secrets:setup
  secrets:show
  spec
  spec:helpers
  spec:models
  spec:requests
  spec:routing
  spec:views
  stats
  test:all
  test:db
  time:zones[country_or_offset]
  tmp:clear
  tmp:create
  version
  webpacker
  webpacker:binstubs
  webpacker:check_binstubs
  webpacker:check_node
  webpacker:check_yarn
  webpacker:clean[keep,age]
  webpacker:clobber
  webpacker:compile
  webpacker:info
  webpacker:install
  webpacker:install:angular
  webpacker:install:coffee
  webpacker:install:elm
  webpacker:install:erb
  webpacker:install:react
  webpacker:install:stimulus
  webpacker:install:svelte
  webpacker:install:typescript
  webpacker:install:vue
  webpacker:verify_install
  webpacker:yarn_install
  yarn:install
  zeitwerk:check

I think this makes a lot of sense. But you know what I realized? The order of the "most common Rails command" makes no sense.

Why would generate be above new? That's silly. We should do a follow up PR to address that.

Anyway, to me this is a great improvement already. 👍

@olivierlacan
Copy link
Contributor

@p8 You need another rebase but aside from that @jonathanhefner do you think this looks good?

@p8
Copy link
Member Author

p8 commented May 20, 2021

Thanks for the review @olivierlacan ! I've rebased against main.

@p8
Copy link
Member Author

p8 commented May 20, 2021

@olivierlacan I agree that outside an app folder, new should be at the top.
But inside an app folder it might be better to even hide it, or add an explanation that you should move outside the app folder?

When running `rails -h` or just `rails` outside a Rails application,
Rails outputs all options for running the `rails new` command. This can be
confusing to users when they probably want to see the common Rails commands.

Instead, we should always show the common commands when running `rails -h`
inside or outside a Rails application.

With this change help works as follows...

Outside a Rails application we never show the extended commands:
db:migrate, etc...
The extended commands require a Rails application.
They also take up a lot screen space.

- `rails`        outputs the help for the common commands
- `rails -h`     outputs the help for the common commands.
- `rails new -h` outputs the help for the new command.

Inside a Rails application it works mostly as before. The only change is
that calling plain `bin/rails` now only outputs the common commands and
not the extended commands.

- `bin/rails`    outputs the help for the common commands
- `bin/rails -h` outputs the help for the common commands and the
  extended commands
@rails-bot
Copy link

rails-bot bot commented Oct 28, 2021

This pull request has been automatically marked as stale because it has not had recent activity. It will be closed if no further activity occurs.
Thank you for your contributions.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet

3 participants