diff --git a/Gemfile b/Gemfile
index 390999a..8ada858 100644
--- a/Gemfile
+++ b/Gemfile
@@ -39,4 +39,5 @@ group :development, :test do
gem 'capybara'
gem 'launchy'
gem 'rspec-rails'
+ gem 'factory_girl_rails'
end
diff --git a/Gemfile.lock b/Gemfile.lock
index cd1145d..2f2e612 100644
--- a/Gemfile.lock
+++ b/Gemfile.lock
@@ -48,6 +48,11 @@ GEM
diff-lcs (1.2.5)
erubis (2.7.0)
execjs (2.7.0)
+ factory_girl (4.8.0)
+ activesupport (>= 3.0.0)
+ factory_girl_rails (4.8.0)
+ factory_girl (~> 4.8.0)
+ railties (>= 3.0.0)
faraday (0.9.2)
multipart-post (>= 1.2, < 3)
font-awesome-rails (4.6.3.1)
@@ -171,6 +176,7 @@ DEPENDENCIES
byebug
capybara
coffee-rails (~> 4.0.0)
+ factory_girl_rails
font-awesome-rails
foundation-rails
jquery-rails
@@ -189,4 +195,4 @@ RUBY VERSION
ruby 2.2.2p95
BUNDLED WITH
- 1.14.3
+ 1.14.5
diff --git a/app/models/user.rb b/app/models/user.rb
index d547333..c2a09ea 100644
--- a/app/models/user.rb
+++ b/app/models/user.rb
@@ -15,6 +15,10 @@ def admin_button_class
admin? ? "success" : "secondary"
end
+ def user_button_class
+ approved? ? "approved" : "not-approved"
+ end
+
def approved?
approval_at.present?
end
diff --git a/app/views/users/index.html.erb b/app/views/users/index.html.erb
index 1f88c66..197c8a8 100644
--- a/app/views/users/index.html.erb
+++ b/app/views/users/index.html.erb
@@ -19,8 +19,8 @@
<%= user.created_at_string %> |
- <%= link_to("No", [:approve, user], class: "button tiny secondary") unless user.approved? %>
- <%= link_to("Yes", [:remove_approval, user], class: "button tiny success") if user.approved? %>
+ <%= link_to("No", [:approve, user], class: "button tiny secondary #{user.user_button_class}") unless user.approved? %>
+ <%= link_to("Yes", [:remove_approval, user], class: "button tiny success #{user.user_button_class}") if user.approved? %>
|
<%= user.approval_at_string %> |
diff --git a/spec/factories/users.rb b/spec/factories/users.rb
new file mode 100644
index 0000000..16dba07
--- /dev/null
+++ b/spec/factories/users.rb
@@ -0,0 +1,7 @@
+FactoryGirl.define do
+ factory :user do
+ provider "google_oauth2"
+ sequence(:uid) { |n| n }
+ sequence(:name) { |n| "Fake User#{n}" }
+ end
+end
diff --git a/spec/features/users_spec.rb b/spec/features/users_spec.rb
index d783e19..a5c5157 100644
--- a/spec/features/users_spec.rb
+++ b/spec/features/users_spec.rb
@@ -1,9 +1,10 @@
-feature "User management" do
+feature "user management" do
let(:users_index_path) { polymorphic_path([:users]) }
- context "when an admin user visits the users index" do
- let!(:admin_user) { login_new_admin_user }
- subject { admin_user }
+ context "when an admin visits the users index" do
+ let!(:admin) { login_new_admin_user }
+ let!(:users) { create_list(:user, 2, approval_at: "01/01/2001") }
+ let!(:unapproved_user) { create(:user) }
before { visit users_index_path }
@@ -11,80 +12,61 @@
expect(page).to have_table("users_table")
end
- it "fills the table with the right headers and rows" do
- check_headers_and_values_on_generic_index_page(
- "users_table", {
- "Name" => "Example User",
- "Created At" => subject.created_at_string,
- "Approval At" => subject.approval_at_string,
- "Admin" => "true",
- "Actions" => "Remove Approval Delete",
- }
- )
+ it "displays a table with proper headers and admin row data" do
+ page.find("#user_#{admin.id} td:nth-of-type(1)", text: admin.name)
+ page.find("#user_#{admin.id} td:nth-of-type(2)", text: admin.created_at_string)
+ page.find("#user_#{admin.id} td:nth-of-type(3)", text: "Yes")
+ page.find("#user_#{admin.id} td:nth-of-type(4)", text: admin.approval_at_string)
+ page.find("#user_#{admin.id} td:nth-of-type(5)", text: "Yes")
+ page.find("#user_#{admin.id} td:nth-of-type(6)", text: "Delete")
end
- context "and a new non-admin user is added" do
- subject! { User.create!(name: "Joe") }
+ it "displays a table with proper headers and user row data" do
+ page.find("#user_#{users.first.id} td:nth-of-type(1)", text: users.first.name)
+ page.find("#user_#{users.first.id} td:nth-of-type(2)", text: users.first.created_at_string)
+ page.find("#user_#{users.first.id} td:nth-of-type(3)", text: "Yes")
+ page.find("#user_#{users.first.id} td:nth-of-type(4)", text: users.first.approval_at_string)
+ page.find("#user_#{users.first.id} td:nth-of-type(5)", text: "No")
+ page.find("#user_#{users.first.id} td:nth-of-type(6)", text: "Delete")
+ end
- before { visit users_index_path }
+ context "and admin clicks No for user approval" do
+ before do
+ find('.not-approved').click
- it "fills the table with that user\"s information too" do
- check_headers_and_values_on_generic_index_page(
- "users_table", {
- "Name" => "Joe",
- "Created At" => subject.created_at_string,
- "Approval At" => "",
- "Admin" => "",
- "Actions" => "Approve Delete",
- }
- )
end
- context "and the current user clicks the approve link for that user" do
- before do
- within(:row_for, subject) do
- click_link "Approve"
- end
- end
+ it "approves the user" do
+ expect(unapproved_user.reload).to be_approved
+ end
- it "approves the user" do
- expect(subject.reload).to be_approved
- end
+ it "displays an approval time" do
+ expect(page).to have_content(unapproved_user.approval_at_string)
+ end
- it "displays an approval time" do
- within(:row_for, subject) do
- expect(find(:value_under_header, "Approval At").text).to_not be_blank
- end
- end
+ it "shows Yes instead of No button" do
+ expect(page).to have_link('Yes', href: remove_approval_user_path(unapproved_user))
+ end
- it "no longer shows the approve link" do
- within(:row_for, subject) do
- expect(find(:value_under_header, "Actions").text).to eq "Remove Approval Delete"
- end
+ context "and the admin clicks No for user approval for same user" do
+ before do
+ find(:xpath, "//a[@href='/users/#{unapproved_user.id}/remove_approval']").click
end
- context "and the current user clicks the Remove Approval link for that user" do
- before do
- within(:row_for, subject) do
- click_link "Remove Approval"
- end
- end
-
- it "removes the user's approval" do
- expect(subject.reload).to_not be_approved
- end
+ it "removes the user's approval" do
+ expect(unapproved_user.reload).to_not be_approved
end
end
- context "and the current user clicks the delete link for that user" do
+ context "and the admin clicks the delete link for same user" do
before do
- within(:row_for, subject) do
+ within(:css, "#user_#{unapproved_user.id}") do
click_link "Delete"
end
end
it "deletes the user" do
- expect(User.find_by_id(subject.id)).to be_nil
+ expect(User.find_by_id(unapproved_user.id)).to be_nil
end
end
end
diff --git a/spec/support/factory_girl.rb b/spec/support/factory_girl.rb
new file mode 100644
index 0000000..eec437f
--- /dev/null
+++ b/spec/support/factory_girl.rb
@@ -0,0 +1,3 @@
+RSpec.configure do |config|
+ config.include FactoryGirl::Syntax::Methods
+end
diff --git a/spec/support/feature_helpers.rb b/spec/support/feature_helpers.rb
index 72a18d1..406f941 100644
--- a/spec/support/feature_helpers.rb
+++ b/spec/support/feature_helpers.rb
@@ -1,7 +1,9 @@
module FeatureHelpers
def login_new_user(options = {})
visit "/"
- click_link "Sign in"
+ within(".super-button") do
+ click_link "Sign in or sign up"
+ end
user = User.last
user.admin = options[:admin] || false
user.approval_at = options[:approval_at] || Time.now
@@ -22,7 +24,7 @@ def check_headers_and_values_on_generic_index_page(table_locator, headers_and_va
end
end
- within(:row_for, subject) do
+ within(:row_for, headers_and_values_hash) do
headers_and_values_hash.each do |header, value|
expect({ header => find(:value_under_header, header).text }).to eq({ header => value })
end