Trying to generate rspec test for Controllers - ruby-on-rails

I type:
rails g rspec:controller application
But nothing appears in the spec file?

If you type script/rails generate, the only RSpec generator you'll
actually see is rspec:install. That's because RSpec is registered with
Rails as the test framework, so whenever you generate application
components like models, controllers, etc, RSpec specs are generated
instead of Test::Unit tests.
rails g rspec:integration [name]
controller
helper
install
integration
mailer
model
observer
scaffold
view
example:
=> rails g rspec:integration controller
=> create spec/requests/controllers_spec.rb

Related

Rails scaffolding for test generating curious attributes for test fixtures

When using rails scaffolding
rails g Somemodel nation:references
the fixtures automatically generated in the test directory take this form
one:
nation: one
why is that? the datatype is an integer and the attribute is nation_id.

How do I customise test generators in default Rails?

Edit: Originally this was a Rails 5.2 question but it still seems relevant with Rails 6 and 6.1
I am trying to customise which tests are generated by default in a vanilla Rails 5.2.x app. I don't seem to be able to configure the Minitest generators though. The following code in my config/application.rb causes a error minitest [not found] error when I try and generate a model.
config.generators do |generate|
generate.test_framework :minitest, model: false
end
My Assumptions/Understanding
In Rails 5.2 the default test frameworks are Minitest and Capybara
Minitest gem is included automatically with rails new
You can customise generator behaviour with a config.generators do block in config/application.rb
test_framework "defines which test framework to use. Defaults to false and will use Minitest by default"
Clearly there's a gap in my understanding or one of my assumptions is wrong.
Steps to Reproduce
rails -v
# Rails 5.2.1.1
rails new testing-test-frameworks
# Bundle install outputs: 'Using minitest 5.11.3'
cd testing-test-frameworks
rails g model --help
# Default [test framework]: test_unit [why???]
rails g model person
# invoke test_unit [why???]
# create test/models/person_test.rb
# create test/fixtures/people.yml
Strangely enough, the official Rails testing guide also has lots of references to invoke test_unit for both unit tests and system tests.
Other Things I Tried
I tried other settings in the config.generators block just to make sure it's working
Given that the test_unit generators seem to be non-negotiable I tried changing the generations through test_unit; config.generators.test_framework :test_unit, model: false
I tried to disable various other tests; fixture:false, integration: false, model: false, spec: false, system: false, view: false
I tried to confirm I don't have any other gems or settings that might be messing with things (several similar sounding problems related to an old version of FactoryBot/Girl)
I tried variations such as generate.test_framework :mini_test mentioned in other answers
Questions
How do I control these generators?
Where (on the Internet or on my filesystem) do I go to learn about the valid options that can be passed to the generators for each test framework?
Why does the help system in my vanilla app say the default test generator is TestUnit when the official documentation says it's Minitest?
I'm attempting to partially answer some of my own questions (2+ years later) based on recent learnings (and based on Rails 6). If I'm wrong, hopefully Cunningham's Law holds true.
1. :test_unit == :minitest (more or less)
The first big point of confusion for me was that Minitest is indeed the default test framework under the hood but just about everything within Rails (still?) seems to refer to TestUnit/test_unit.
Examples include:
rails g model --help output (snippets below)
-t, [--test-framework=NAME] # Test framework to be invoked
# Default: test_unit
^^^^^^^^^
TestUnit options:
^^^^^^^^
rails g scaffold Example output (snippets below):
create app/models/example.rb
invoke test_unit
^^^^^^^^^
create test/models/example_test.rb
invoke scaffold_controller
create app/controllers/examples_controller.rb
invoke test_unit
^^^^^^^^^
create test/controllers/examples_controller_test.rb
create app/helpers/examples_helper.rb
invoke test_unit
^^^^^^^^^
The way we generate tests:
bin/rails generate test_unit:model article title:string body:text
^^^^^^^^^
2. Digging into Test Unit
Sure enough, if we look in all.rb we see that "Test Unit" is being included via the test_unit Railtie. If (like me) you don't really know what a Railtie is, check out this blog post, I found it quite helpful.
In terms of what options we can provide in our config/application.rb config.generators block, I think the only options we can pass with config.generators.test_framework :test_unit are fixture: true/false (and maybe specifying a fixture_replacement path(?), based on the apparent defaults in the test_unit railtie).
3. What else can "TestUnit" generate?
If you run rails g to get a list of available generators, only four TestUnit ones are mentioned in the output:
TestUnit:
test_unit:channel
test_unit:generator
test_unit:mailbox
test_unit:plugin
But the Rails Testing Guide mentions test_unit:model and test_unit:scaffold as well. And when I tried rails g test_unit:foo Rails suggested perhaps I meant rails g test_unit:job so that's three "undocumented" generators.
From what I can tell, those three extras come from this generators folder, along with a few others. If so, I think the complete list is:
test_unit:channel *not in that folder, seems to be added by
ActionCable
test_unit:controller
test_unit:generator
test_unit:helper
test_unit:integration
test_unit:job
test_unit:mailbox *not in that folder, seems to be added by ActionMailbox
test_unit:mailer
test_unit:model
test_unit:plugin
test_unit:scaffold
test_unit:system

Rails have not created test directory for me?

I have created a new application of Ruby on Rails. I use RubyMine and created the project using New Project->RailsApps Sample->rails-devise-pundit
I have created models and controllers, but just realized I do not have any test directory under my root path.
For example, I have a Transaction model and when I do:
rails g resource Post --skip --no-resource-route --no-migration --no-helper --no-assets
I get this:
invoke active_record
skip app/models/transaction.rb
invoke rspec
identical spec/models/transaction_spec.rb
invoke factory_girl
identical spec/factories/transactions.rb
invoke controller
skip app/controllers/transactions_controller.rb
invoke erb
exist app/views/transactions
invoke rspec
See, there is no test directory at all here
How can I auto generate test directories with resources for all of my models and controllers? (As I see a guide for testing in Ruby here: http://guides.rubyonrails.org/testing.html)

Rails: How to run `rails generate scaffold` when the model already exists?

I'm new to Rails so my current project is in a weird state.
One of the first things I generated was a "Movie" model. I then started defining it in more detail, added a few methods, etc.
I now realize I should have generated it with rails generate scaffold to hook up things like the routing, views, controller, etc.
I tried to generate the scaffolding but I got an error saying a migration file with the same name already exists.
What's the best way for me to create scaffolding for my "Movie" now? (using rails 3)
TL;DR: rails g scaffold_controller <name>
Even though you already have a model, you can still generate the necessary controller and migration files by using the rails generate option. If you run rails generate -h you can see all of the options available to you.
Rails:
controller
generator
helper
integration_test
mailer
migration
model
observer
performance_test
plugin
resource
scaffold
scaffold_controller
session_migration
stylesheets
If you'd like to generate a controller scaffold for your model, see scaffold_controller. Just for clarity, here's the description on that:
Stubs out a scaffolded controller and its views. Pass the model name,
either CamelCased or under_scored, and a list of views as arguments.
The controller name is retrieved as a pluralized version of the model
name.
To create a controller within a module, specify the model name as a
path like 'parent_module/controller_name'.
This generates a controller class in app/controllers and invokes helper,
template engine and test framework generators.
To create your resource, you'd use the resource generator, and to create a migration, you can also see the migration generator (see, there's a pattern to all of this madness). These provide options to create the missing files to build a resource. Alternatively you can just run rails generate scaffold with the --skip option to skip any files which exist :)
I recommend spending some time looking at the options inside of the generators. They're something I don't feel are documented extremely well in books and such, but they're very handy.
Great answer by Lee Jarvis, this is just the command e.g; we already have an existing model called User:
rails g scaffold_controller User
For the ones starting a rails app with existing database there is a cool gem called schema_to_scaffold to generate a scaffold script.
it outputs:
rails g scaffold users fname:string lname:string bdate:date email:string encrypted_password:string
from your schema.rb our your renamed schema.rb. Check it
In Rails 5, you can still run
$rails generate scaffold movie --skip
to create all the missing scaffold files or
rails generate scaffold_controller Movie
to create the controller and view only.
For a better explanation check out rails scaffold
This command should do the trick:
$ rails g scaffold movie --skip
You can make use of scaffold_controller and remember to pass the attributes of the model, or scaffold will be generated without the attributes.
rails g scaffold_controller User name email
# or
rails g scaffold_controller User name:string email:string
This command will generate following files:
create app/controllers/users_controller.rb
invoke haml
create app/views/users
create app/views/users/index.html.haml
create app/views/users/edit.html.haml
create app/views/users/show.html.haml
create app/views/users/new.html.haml
create app/views/users/_form.html.haml
invoke test_unit
create test/controllers/users_controller_test.rb
invoke helper
create app/helpers/users_helper.rb
invoke test_unit
invoke jbuilder
create app/views/users/index.json.jbuilder
create app/views/users/show.json.jbuilder
I had this challenge when working on a Rails 6 API application in Ubuntu 20.04.
I had already existing models, and I needed to generate corresponding controllers for the models and also add their allowed attributes in the controller params.
Here's how I did it:
I used the rails generate scaffold_controller to get it done.
I simply ran the following commands:
rails generate scaffold_controller School name:string logo:json motto:text address:text
rails generate scaffold_controller Program name:string logo:json school:references
This generated the corresponding controllers for the models and also added their allowed attributes in the controller params, including the foreign key attributes.
create app/controllers/schools_controller.rb
invoke test_unit
create test/controllers/schools_controller_test.rb
create app/controllers/programs_controller.rb
invoke test_unit
create test/controllers/programs_controller_test.rb
That's all.
I hope this helps

How to test devise models, controllers and views using RSpec?

I am used to generating my rspec controllers & models using rspec_X syntax, e.g.
script/generate rspec_model Person
script/generate rspec_controller Person
However if I want to use devise to create a Person model the syntax is:
script/generate devise Person
which works OK, but does not create any of the rspec test files / dirs.
Is there are command I can use to generate both?
(Ruby 1.8, Rails 2.3)
Thanks!
These models and controllers are tested internally to Devise and so you shouldn't be duplicating the effort yourself. If you'd like to test that users can sign in, sign out, register and retrieve their password, I would recommend you use Cucumber to write tests to test Devise's integration with your application.
I am used to generating my rspec controllers & models using rspec_X syntax
You can still use that if you want to create the rspec structures but you'll likely want to decline overwriting your model. For example, here's my rspec_model output:
$ script/generate rspec_model Person
exists app/models/
create spec/models/
create spec/fixtures/
overwrite app/models/person.rb? (enter "h" for help) [Ynaqdh] n
skip app/models/person.rb
create spec/models/person_spec.rb
create spec/fixtures/people.yml
exists db/migrate
create db/migrate/20100826043436_create_people.rb
I just told it not to overwrite app/models/person.rb.

Resources