Hartl Rails Tutorial (3.2) 8.2.5 Rspec failure - ruby-on-rails-3

UPDATE:
My test was not submitting the user info. The relavant code was in the previous chapter's exercises:
describe "after saving user" do
before { click_button submit }
let(:user) { User.find_by_email('user#example.com') }
it { should have_selector('title', text: user.name) }
it { should have_selector('div.alert.alert-success', text: 'Welcome') }
it { should have_link('Profile') }
end
/UPDATE
I've completed section 8.2.5 (Signin upon signup) and the app behaves exactly as described:
the user is signed-in upon signup
then redirected to their profile page
where the header has been changed to include a 'Sign out' link.
But my test for the 'Sign out' link fails. Here's my code, all copied from the tutorial:
relevant controller code (users_controller.rb):
def create
#user = User.new(params[:user])
if #user.save
sign_in #user
flash[:success] = "Welcome to the Sample App!"
redirect_to #user
else
render 'new'
end
end
relevant view code (_header.html.erb):
<ul class="dropdown-menu">
<li><%= link_to "Profile", current_user %></li>
<li><%= link_to "Settings", '#' %></li>
<li class="divider"></li>
<li>
<%= link_to "Sign out", signout_path, method: "delete" %>
</li>
</ul>
relevant test code (user_pages_spec.rb):
describe "signup" do
before { visit signup_path }
let(:submit) { "Create my account" }
describe "with invalid information" do
it "should not create a user" do
expect { click_button submit }.not_to change(User, :count)
end
end
describe "with valid information" do
before do
fill_in "Name", with: "Example User"
fill_in "Email", with: "user#example.com"
fill_in "Password", with: "foobar"
fill_in "Confirmation", with: "foobar"
end
it "should create a user" do
expect { click_button submit }.to change(User, :count).by(1)
end
describe "after saving user" do
it { should have_link('Profile') }
end
end
end
The error is rspec ./spec/requests/user_pages_spec.rb:47 # User pages signup with valid information after saving user
Thanks!

I think the last 'describe' block should look like this:
describe "after saving user" do
before { click_button submit }
it { should have_content('Profile') }
end
The test missed clicking the "submit" button before examining if there is appropriate content on a page.

Related

Rspec issues with Devise

In my tickets_controller.rb:
def create
#ticket = #project.tickets.build(ticket_params)
#ticket.author = current_user
if #ticket.save
flash[:notice] = "Ticket has been created."
redirect_to [#project, #ticket]
else
flash.now[:alert] = "Ticket has not been created."
render "new"
end
end
So I assumed, I should be OK to pass the test, but it's giving me the errors below.
I'm under impression it's not invoking the email address from current_user.email...
The repo here https://github.com/tenzan/ticketee.
Deployed version here https://github.com/tenzan/ticketee
$ rspec spec/features/creating_tickets_spec.rb
...F
Failures:
1) Users can create new tickets with valid attributes
Failure/Error: expect(page).to have_content "Author: #{user.email}"
expected to find text "Author: test4#example.com" in "Internet Explorer Non-standards compliance My pages are ugly!"
# ./spec/features/creating_tickets_spec.rb:36:in `block (3 levels) in <top (required)>'
# ./spec/features/creating_tickets_spec.rb:35:in `block (2 levels) in <top (required)>'
Finished in 0.64558 seconds (files took 1.3 seconds to load)
4 examples, 1 failure
Failed examples:
rspec ./spec/features/creating_tickets_spec.rb:30 # Users can create new tickets with valid attributes
UPDATE 1:
show.html.erb for ticket:
<header>
<h2><%= #ticket.name %></h2>
<ul class="actions">
<li><%= link_to "Edit Ticket", [:edit, #project, #ticket],
class: "edit" %></li>
<li><%= link_to "Delete Ticket", [#project, #ticket], method: :delete,
data: { confirm: "Are you sure you want to delete this ticket?"},
class: "delete" %></li>
</ul>
</header>
<table id="attributes">
<tr>
<th>Author: </th>
<td><%= #ticket.author.email %></td>
</tr>
<tr>
<th>Created: </th>
<td><%= time_ago_in_words(#ticket.created_at) %> ago</td>
</tr>
</table>
<div id="ticket">
<header>
<h1><%= #project.name %></h1>
</header>
<header>
<h2><%= #ticket.name %></h2>
</header>
<%= simple_format(#ticket.description) %>
</div>
creating_tickets_specs.rb:
require 'rails_helper'
RSpec.feature 'Users can create new tickets' do
let(:user) { FactoryGirl.create(:user) }
before do
login_as(user)
project = FactoryGirl.create(:project, name: "Internet Explorer")
visit project_path(project)
click_link "New Ticket"
end
scenario "with valid attributes" do
fill_in "Name", with: "Non-standards compliance"
fill_in "Description", with: "My pages are ugly!"
click_button "Create Ticket"
expect(page).to have_content "Ticket has been created."
within("#ticket") do
expect(page).to have_content "Author: #{user.email}"
end
end
scenario "when providing invalid attributes" do
click_button "Create Ticket"
expect(page).to have_content "Ticket has not been created."
expect(page).to have_content "Name can't be blank"
expect(page).to have_content "Description can't be blank"
end
scenario "with an invalid description" do
fill_in "Name", with: "Non-standards compliance"
fill_in "Description", with: "It sucks"
click_button "Create Ticket"
expect(page).to have_content "Ticket has not been created."
expect(page).to have_content "Description is too short"
end
end
A couple things
After you set author on ticket, are you calling save?
What is in the show template where it's blowing up?
Typically I would write your controller code as:
current_user.tickets.create ticket_params
Which, assuming the relationships are set up correctly, will automatically set up the relationships as you would expect.
Rspec was looking for "Author: test4#example.com" within ticket tag as per within("#ticket") as described in the creating_tickets_spec.rb, but in my case it was out of that scope.
So, putting it inside solved the issue.

Issue in acceptance test while redirecting to another page

I am writing an acceptance test to check on clicking a button it gets redirected to another page(carts page), but I am getting an error while trying to do the same.
my code is:-
gift_cards_controller.rb
class GiftCardsController < ApplicationController
before_filter :get_order_and_shipment, only: [:create]
def create
super do |format|
if resource.errors.messages.any?
format.html { render :new }
else
format.html { redirect_to carts_path }
end
end
end
end
acceptance spec :-
gift_card_spec.rb
require 'spec_helper'
include Warden::Test::Helpers
Warden.test_mode!
describe 'Gift Card', type: :feature do
before(:all) do
Address.delete_all
end
it 'redirects to cart page' do
user = create(:user)
login_as(user, scope: :user)
address = create(:address, name: 'ABC',
street: 'PQR',
postal_code: '12345',
state_or_region: 'XYZ',
phone_number: '123-456-7890',
city: 'LMN',
user: user)
add_str = 'ABC, PQR, LMN, XYZ, 12345'
visit new_gift_card_path
page.should_not have_content('Please add address before creating a gift card')
page.should have_button('create gift card')
fill_in 'gift_card_name', with: 'Gift Card'
fill_in 'gift_card_value', with: 1000.99
fill_in 'gift_card_message', with: "This is A Gift Card"
option = first('#gift_card_address_list option').text
expect(option).to eq(add_str)
click_button 'create gift card'
expect(page.current_url).to eq(carts_url)
page.should have_content('ORDER SUMMARY')
end
end
error:-
Gift Card
redirects to cart page (FAILED - 1)
Failures:
1) Gift Card redirects to cart page
Failure/Error: expect(page.current_url).to eq(carts_url)
expected: "http://www.example.com/cart"
got: "http://www.example.com/gift_cards/new?gift_card[code]=75C4FC&gift_card[name]=Gift+Card&gift_card[value]=1000.99&gift_card[message]=This+is+A+Gift+Card&commit=create+gift+card"
[Edit]
On execution of click_button 'create gift card' line in the rspec, the control does not enter the create method in the controller. Because of which I am unable to check resourse.errors.messages.any?
view/gift_cards/new.html.haml
#giftcard
.giftCard
%h1
Create A Gift Card
= simple_form_for :gift_card, url: gift_cards_path, method: :post do |f|
%form
%fieldset
.form-inputs
= f.input :code,input_html: {value: GiftCard.generate_code}, required: true
= f.input :name, label: 'Gift Card Name/Caption', required: false
= f.input :value, label: 'Amount'
= f.input :address_list, collection: current_user.addresses,
label_method: :get_address_string, include_blank: false
= f.input :message, as: :text, required: false
= f.button :submit, 'create gift card',
class: 'gift_card_submit', disable_with: "creating your gift card..."
routes.rb
resources :gift_cards
gift_cards_path GET /gift_cards(.:format) gift_cards#index
POST /gift_cards(.:format) gift_cards#create
new_gift_card_path GET /gift_cards/new(.:format) gift_cards#new
edit_gift_card_path GET /gift_cards/:id/edit(.:format) gift_cards#edit
gift_card_path GET /gift_cards/:id(.:format) gift_cards#show
PUT /gift_cards/:id(.:format) gift_cards#update
DELETE /gift_cards/:id(.:format) gift_cards#destroy
Seems your form is incorrect.
= simple_form_for :gift_card, url: gift_cards_path, method: :post do |f|
%form
%fieldset
.form-inputs
remove the %form element
Use REST convention simple_form_for #gift_card do |f|
Based on the controller code you shared, it appears that either it's failing your before_filter or resource.errors.messages.any? was truthy and you rendered the new view rather than redirecting to carts_path. Without any other code, there's not much else to tell.

Recaptcha only showing up after page refresh - Rails 4 - Devise

I have installed recaptcha according to the gem instructions, however when I view the sign_up page (using Devise), the catcha doesn't appear until I refresh the page.
Looking through other comments, the recommendation is to disable turbolinks (which I am using) by changing the sign_in link to:
<%= link_to "Sign up", new_registration_path, "data-no-turbolink" => true %><br />
I have tried this, but I still don't get the captcha until I do a page refresh.
Relevant code:
Views/devise/registrations/new.html.erb
................
<%= recaptcha_tags %>
................
/controllers/users/registrations_controller.rb
class Users::RegistrationsController < Devise::RegistrationsController
def create
if !verify_recaptcha
flash.delete :recaptcha_error
build_resource
resource.valid?
resource.errors.add(:base, "There was an error with the recaptcha code below. Please re-enter the code.")
clean_up_passwords(resource)
respond_with_navigational(resource) { render_with_scope :new }
else
flash.delete :recaptcha_error
super
end
end
def clean_up_passwords(*args)
# Delete or comment out this method to prevent the password fields from
# repopulating after a failed registration
end
end
Issue was that I needed to still include "class:" in the link:
<%= link_to "Sign up", new_user_registration_path, "data-no-turbolink" => true, class: "btn btn-primary btn-med" %>
Just try in controller this code
def create
if resource.valid? && !verify_recaptcha
clean_up_passwords(resource)
flash.delete :recaptcha_error
elsif !resource.valid? && verify_recaptcha
clean_up_passwords resource
respond_with resource
elsif !resource.valid? && !verify_recaptcha
flash.now[:alert] = "Recaptcha error"
flash.delete :recaptcha_error
clean_up_passwords resource
respond_with resource
end
end
And in your Views/devise/registrations/new.html.erb
<%= recaptcha_tags display: {theme: 'red', tabindex: 5}, ssl: false, noscript: false %>

why does this cucumber code fail

I have this code : https://github.com/roelof1967/tamara
But when I do cucumber it fails with this error message : https://gist.github.com/4008123
Can anyone explain to me what's wrong with my code?
Roelof
Edit 1:
Code that fails:
class Output
def messages
#messages ||= []
end
def puts(message)
messages << message
end
def output
#output ||= Output.new
end
end
When /^he logs in$/ do
visit("/users/sign_in")
fill_in('Email', :with => #user.email)
fill_in('Password', :with => #user.password)
click_button('Sign in')
end
Then /^he should see "(.*?)"$/ do |message|
#output.messages.should include (message)
end
And here is the error message :
undefined method `[]' for nil:NilClass NoMethodError)
./features/step_definitions/login_steps.rb:6:in `/^he logs in$/'
features/login.feature:5:in `When he logs in'
Do this for your solution:
Step 1 : create home controller
class HomeController < ApplicationController
def index
end
end
step 2 : create home folder in view and create index.html.erb file and your content look like as a example
<% if current_user.present? %>
<h1> <%= link_to "Sign Out", destroy_user_session_path, :method => :delete %> </h1>
<% else %>
<h1> <%= link_to "Sign Up", "/users/sign_up" %> |<%= link_to "Sign In", user_session_path %> </h1>
<% end %>
step 3 : now your login.feature file look like
Feature: login and authecation
Scenario: log in as existing user
Given a user "roelof" exists
When he logs in
Then he should see "Signed in successfully."
And he should see "Sign Out"
Scenario: log in with bad password
Given a user "Aslak" exists
When he logs in with a bad password
Then he should not see "Welcome, Aslak"
And he should see "Login failed"
step 4 now, run cucumber
your scenario "log in as existing user" will pass.

Problems Using Thinking Sphinx with Rails 3.2.1

I am attempting to implement Thinking Sphinx 2.0.10 which from my understanding is compatible with Rails 3. I am very new to programming using Ruby on Rails. I have gone through quite a few articles on StackOverflow but could not find a solution to my problem.
I installed the gem without the :require parameter using in my Gemfile.
gem 'thinking-sphinx', '2.0.10'
I have a working Rails application that displays a list that I would like to add a search to.
Here is my code for defining the indexes in my model file.
define_index do
indexes :email, :sortable => true
indexes :name, :sortable => true
indexes microposts.content, :as => :micropost_content
end
Here is the Rails code in my controller file. The commented out line is the original code that is working. I have a default for will_paginate I think in the application controller for 15 records per page.
def index
#users = User.search params[:search], :per_page => 15
# #users = User.paginate(page: params[:page])
end
Here is the search box that I added to my index page.
<p>
<%= text_field_tag :search, params[:search] %>
<%= submit_tag "Search", :name => nil %>
</p>
Here is my rSpec code. This is the original code that I was using before I attempted to implement Thinking Sphinx.
describe "index" do
let(:user) { FactoryGirl.create(:user) }
before(:each) do
sign_in user
visit users_path
end
it { should have_selector('title', text: 'All users') }
describe "pagination" do
before(:all) { 15.times { FactoryGirl.create(:user) } }
after(:all) { User.delete_all }
let(:first_page) { User.paginate(page: 1) }
let(:second_page) { User.paginate(page: 2) }
it { should have_link('Next') }
it { should have_link('2') }
it { should_not have_link('delete') }
it "should list each user" do
User.all[0..2].each do |user|
page.should have_selector('li', text: user.name)
end
end
it "should list the first page of users" do
first_page.each do |user|
page.should have_selector('li', text: user.name)
end
end
it "should not list the second page of users" do
second_page.each do |user|
page.should_not have_selector('li', text: user.name)
end
end
describe "as an admin user" do
let(:admin) { FactoryGirl.create(:admin) }
before do
sign_in admin
visit users_path
end
it { should have_link('delete', href: user_path(User.first)) }
it "should be able to delete another user" do
expect { click_link('delete') }.to change(User, :count).by(-1)
end
it { should_not have_link('delete', href: user_path(admin)) }
end
end
end
When I run my rSpec test I get the following error:
Failure/Error: visit users_path
ActionView::Template::Error:
getaddrinfo: nodename nor servname provided, or not known
The page displays just fine. When I enter text in the search box and click the button nothing happens which is no surprise to me.
I am able to run Sphinx on the terminal. The searches work fine. I just do not know enough to debug this problem with Thinking Sphinx. I have searched many pages on this website and many others the past few days but none of them are dealing with this issue. Any help would be appreciated.
Did you initialize the sphinx database?
Usually you just need to do something like:
rake ts:rebuild
This should automatically run rake ts:conf for you and rebuild your indexes.
You could also use rake ts:in to update the indexes.
A simple way to test if this is working is to run the rails console (rails c) and try manually searching your users (User.search).
If you get any results, the indexes are available and you can troubleshoot your views/controllers next ;)