diff --git a/app/controllers/admin/account_requests_controller.rb b/app/controllers/admin/account_requests_controller.rb
index e93495a555..5ab55e3309 100644
--- a/app/controllers/admin/account_requests_controller.rb
+++ b/app/controllers/admin/account_requests_controller.rb
@@ -1,4 +1,6 @@
class Admin::AccountRequestsController < AdminController
+ before_action :set_account_request, only: [:reject, :close]
+
def index
@open_account_requests = AccountRequest.requested.order('created_at DESC')
.page(params[:open_page]).per(15)
@@ -11,12 +13,24 @@ def for_rejection
end
def reject
- account_request = AccountRequest.find(account_request_params[:id])
- account_request.reject!(account_request_params[:rejection_reason])
+ @account_request.reject!(account_request_params[:rejection_reason])
redirect_to admin_account_requests_path, notice: "Account request rejected!"
end
+ def close
+ @account_request.close!(account_request_params[:rejection_reason])
+ redirect_to admin_account_requests_path, notice: "Account request closed!"
+ rescue => e
+ redirect_to admin_account_requests_path, alert: e.message
+ end
+
def account_request_params
params.require(:account_request).permit(:id, :rejection_reason)
end
+
+ private
+
+ def set_account_request
+ @account_request = AccountRequest.find(account_request_params[:id])
+ end
end
diff --git a/app/models/account_request.rb b/app/models/account_request.rb
index a704cddcdb..c68fe75559 100644
--- a/app/models/account_request.rb
+++ b/app/models/account_request.rb
@@ -30,10 +30,10 @@ class AccountRequest < ApplicationRecord
has_one :organization, dependent: :nullify
- enum status: %w[started user_confirmed admin_approved rejected].map { |v| [v, v] }.to_h
+ enum status: %w[started user_confirmed admin_approved rejected admin_closed].map { |v| [v, v] }.to_h
scope :requested, -> { where(status: %w[started user_confirmed]) }
- scope :closed, -> { where(status: %w[admin_approved rejected]) }
+ scope :closed, -> { where(status: %w[admin_approved rejected admin_closed]) }
def self.get_by_identity_token(identity_token)
decrypted_token = JWT.decode(identity_token, Rails.application.secret_key_base, true, { algorithm: 'HS256' })
@@ -62,6 +62,11 @@ def processed?
organization.present?
end
+ # @return [Boolean]
+ def can_be_closed?
+ started? || user_confirmed?
+ end
+
def confirm!
update!(confirmed_at: Time.current, status: 'user_confirmed')
AccountRequestMailer.approval_request(account_request_id: id).deliver_later
@@ -73,6 +78,12 @@ def reject!(reason)
AccountRequestMailer.rejection(account_request_id: id).deliver_later
end
+ # @param reason [String]
+ def close!(reason)
+ raise 'Cannot be closed from this state' unless can_be_closed?
+ update!(status: 'admin_closed', rejection_reason: reason)
+ end
+
private
def email_not_already_used_by_organization
diff --git a/app/views/admin/account_requests/_open_account_request.html.erb b/app/views/admin/account_requests/_open_account_request.html.erb
index d06023658d..4f05036f0a 100644
--- a/app/views/admin/account_requests/_open_account_request.html.erb
+++ b/app/views/admin/account_requests/_open_account_request.html.erb
@@ -13,5 +13,10 @@
<%= js_button(text: 'Reject',
icon: 'ban',
class: 'reject-button',
- data: { request_id: open_account_request.id }) %> |
+ data: { request_id: open_account_request.id, modal: 'reject' }) %>
+ <%= js_button(text: 'Close (Admin)',
+ icon: 'times',
+ class: 'reject-button',
+ data: { request_id: open_account_request.id, modal: 'close' }) %> |
+
diff --git a/app/views/admin/account_requests/_rejection_modal.html.erb b/app/views/admin/account_requests/_rejection_modal.html.erb
index 1a4d198d38..4dc350165f 100644
--- a/app/views/admin/account_requests/_rejection_modal.html.erb
+++ b/app/views/admin/account_requests/_rejection_modal.html.erb
@@ -1,19 +1,18 @@
-
+
-
-
+
- <%= simple_form_for AccountRequest.new, url: reject_admin_account_requests_path, method: :post do |f| %>
+ <%= simple_form_for AccountRequest.new, url: '', method: :post do |f| %>
<%= f.hidden_field :id, id: :reject_account_request_id %>
<%= submit_button %>
<% end %>
@@ -23,14 +22,24 @@
-
+
diff --git a/app/views/admin/account_requests/index.html.erb b/app/views/admin/account_requests/index.html.erb
index 341212634b..0847b827bc 100644
--- a/app/views/admin/account_requests/index.html.erb
+++ b/app/views/admin/account_requests/index.html.erb
@@ -103,14 +103,3 @@
-
-
diff --git a/config/routes.rb b/config/routes.rb
index a97548c5cd..17e4398dc0 100644
--- a/config/routes.rb
+++ b/config/routes.rb
@@ -76,6 +76,7 @@ def set_up_flipper
resources :barcode_items
resources :account_requests, only: [:index] do
post :reject, on: :collection
+ post :close, on: :collection
get :for_rejection, on: :collection
end
resources :questions
diff --git a/spec/controllers/admin/account_requests_controller_spec.rb b/spec/controllers/admin/account_requests_controller_spec.rb
new file mode 100644
index 0000000000..632d0eacfb
--- /dev/null
+++ b/spec/controllers/admin/account_requests_controller_spec.rb
@@ -0,0 +1,15 @@
+RSpec.describe Admin::AccountRequestsController, type: :controller do
+ before do
+ sign_in(create(:super_admin, organization: nil))
+ end
+
+ let(:account_request) { create(:account_request, status: :admin_approved) }
+
+ describe "POST #close" do
+ it "should not close the account request if it is invalid" do
+ post :close, params: {account_request: {id: account_request.id}}
+ expect(flash[:alert]).to eq("Cannot be closed from this state")
+ expect(response).to redirect_to(admin_account_requests_path)
+ end
+ end
+end
diff --git a/spec/models/account_request_spec.rb b/spec/models/account_request_spec.rb
index 50570a8665..a3e5c412c9 100644
--- a/spec/models/account_request_spec.rb
+++ b/spec/models/account_request_spec.rb
@@ -129,6 +129,18 @@
end
end
+ describe '#can_be_closed?' do
+ it 'returns true when the status can be closed' do
+ subject.status = %w[started user_confirmed].sample
+ expect(subject.can_be_closed?).to eq(true)
+ end
+
+ it 'returns false when the status cannot be closed' do
+ subject.status = 'rejected'
+ expect(subject.can_be_closed?).to eq(false)
+ end
+ end
+
specify '#confirm!' do
mail_double = instance_double(ActionMailer::MessageDelivery, deliver_later: nil)
allow(AccountRequestMailer).to receive(:approval_request).and_return(mail_double)
@@ -159,6 +171,12 @@
expect(mail_double).to have_received(:deliver_later)
end
+ specify "#close!" do
+ account_request.close!('because I said so')
+ expect(account_request.reload.rejection_reason).to eq('because I said so')
+ expect(account_request).to be_admin_closed
+ end
+
describe "versioning" do
it { is_expected.to be_versioned }
end
diff --git a/spec/system/admin/account_requests_system_spec.rb b/spec/system/admin/account_requests_system_spec.rb
index dd79ed4a58..3539bdf8b9 100644
--- a/spec/system/admin/account_requests_system_spec.rb
+++ b/spec/system/admin/account_requests_system_spec.rb
@@ -29,7 +29,7 @@
end
it 'should reject the account', js: true do
- find(%(a[data-request-id="#{request4.id}"])).click
+ find(%(a[data-modal="reject"][data-request-id="#{request4.id}"])).click
fill_in 'account_request_rejection_reason', with: 'Because I said so'
click_on 'Save'
expect(request4.reload).to be_rejected
@@ -40,6 +40,19 @@
expect(page).not_to have_content(request4.name)
end
end
+
+ it 'should close the account', js: true do
+ find(%(a[data-modal="close"][data-request-id="#{request4.id}"])).click
+ fill_in 'account_request_rejection_reason', with: 'Because I said so'
+ click_on 'Save'
+ expect(request4.reload).to be_admin_closed
+ within "#closed-account-requests" do
+ expect(page).to have_content(request4.name)
+ end
+ within '#open-account-requests' do
+ expect(page).not_to have_content(request4.name)
+ end
+ end
end
context "user visits the index page" do
@@ -89,7 +102,7 @@
end
it 'should reject the account', js: true do
- find(%(a[data-request-id="#{request4.id}"])).click
+ find(%(a[data-modal="reject"][data-request-id="#{request4.id}"])).click
fill_in 'account_request_rejection_reason', with: 'Because I said so'
click_on 'Save'
expect(request4.reload).to be_rejected
@@ -100,6 +113,33 @@
expect(page).not_to have_content(request4.name)
end
end
+
+ it 'should close the account', js: true do
+ find(%(a[data-modal="close"][data-request-id="#{request4.id}"])).click
+ fill_in 'account_request_rejection_reason', with: 'Because I said so'
+ click_on 'Save'
+ expect(request4.reload).to be_admin_closed
+ within "#closed-account-requests" do
+ expect(page).to have_content(request4.name)
+ end
+ within '#open-account-requests' do
+ expect(page).not_to have_content(request4.name)
+ end
+ end
+
+ it "should validate the rejection reason on reject modal" do
+ find(%(a[data-modal="reject"][data-request-id="#{request4.id}"])).click
+ fill_in 'account_request_rejection_reason', with: ''
+ click_on 'Save'
+ expect(page).to have_content('Reason must be provided')
+ end
+
+ it "should validate the rejection reason on close modal" do
+ find(%(a[data-modal="close"][data-request-id="#{request4.id}"])).click
+ fill_in 'account_request_rejection_reason', with: ' '
+ click_on 'Save'
+ expect(page).to have_content('Reason must be provided')
+ end
end
end
end