[#6441] Block editing locked and closed contracts
This commit is contained in:
@@ -19,6 +19,7 @@ class Contract < ActiveRecord::Base
|
||||
validates_inclusion_of :discount_type, :in => %w($ %), :allow_blank => true, :allow_nil => true
|
||||
validates_inclusion_of :status, :in => ["open","locked","closed"], :allow_blank => true, :allow_nil => true
|
||||
validate :start_and_end_date_are_valid
|
||||
validate_on_update :validate_status_changes
|
||||
|
||||
# Accessors
|
||||
attr_accessible :name
|
||||
@@ -56,6 +57,10 @@ class Contract < ActiveRecord::Base
|
||||
update_attribute(:status, "closed")
|
||||
end
|
||||
|
||||
def open?
|
||||
self.status == "open"
|
||||
end
|
||||
|
||||
def locked?
|
||||
self.status == "locked"
|
||||
end
|
||||
@@ -261,6 +266,30 @@ class Contract < ActiveRecord::Base
|
||||
end
|
||||
end
|
||||
|
||||
def valid_status_change?
|
||||
change_to_status_only? || changing_to_the_open_status? || changing_from_the_open_status?
|
||||
end
|
||||
|
||||
def change_to_status_only?
|
||||
["status"] == changes.keys
|
||||
end
|
||||
|
||||
def changing_to_the_open_status?
|
||||
changes["status"].present? && "open" == changes["status"].second
|
||||
end
|
||||
|
||||
def changing_from_the_open_status?
|
||||
changes["status"].present? && "open" == changes["status"].first
|
||||
end
|
||||
|
||||
# TODO: duplicated on Deliverable, refactor after one more duplication
|
||||
def validate_status_changes
|
||||
return if valid_status_change?
|
||||
|
||||
errors.add_to_base(:cant_update_locked_contract) if locked?
|
||||
errors.add_to_base(:cant_update_closed_contract) if closed?
|
||||
end
|
||||
|
||||
# Currency amount of time that is logged to the project or to issues
|
||||
# that are not assigned to a Deliverable
|
||||
def orphaned_time
|
||||
@@ -279,6 +308,12 @@ class Contract < ActiveRecord::Base
|
||||
generator_for :executed => true
|
||||
generator_for(:start_date) { Date.yesterday }
|
||||
generator_for(:end_date) { Date.tomorrow }
|
||||
generator_for :discount, ''
|
||||
generator_for :details, ''
|
||||
generator_for :discount_note, ''
|
||||
generator_for :client_point_of_contact, ''
|
||||
generator_for :client_ap_contact_information, ''
|
||||
generator_for :po_number, ''
|
||||
|
||||
def self.next_name
|
||||
@last_name ||= 'Contract 0000'
|
||||
|
||||
@@ -96,6 +96,7 @@ class Deliverable < ActiveRecord::Base
|
||||
changes["status"].present? && "open" == changes["status"].first
|
||||
end
|
||||
|
||||
# TODO: duplicated on Contract, refactor after one more duplication
|
||||
def validate_status_changes
|
||||
return if valid_status_change?
|
||||
|
||||
|
||||
@@ -1,3 +1,9 @@
|
||||
<% if resource.locked? || resource.closed? %>
|
||||
<div class="error_msg">
|
||||
<p><%= resource.locked? ? l(:text_contract_locked_warning) : l(:text_contract_closed_warning) %></p>
|
||||
</div>
|
||||
<% end %>
|
||||
|
||||
<div class="box tabular">
|
||||
<% form.inputs :name => l(:text_general_legend) do %>
|
||||
<%= form.input :name, :required => true %>
|
||||
|
||||
@@ -7,6 +7,8 @@ en:
|
||||
cant_assign_to_locked_deliverable: "Can't assign issue to a locked deliverable"
|
||||
cant_update_locked_deliverable: "Can't update a locked deliverable"
|
||||
cant_update_closed_deliverable: "Can't update a closed deliverable"
|
||||
cant_update_locked_contract: "Can't update a locked contract"
|
||||
cant_update_closed_contract: "Can't update a closed contract"
|
||||
|
||||
field_end_date: End Date
|
||||
field_executed: Executed
|
||||
@@ -92,3 +94,5 @@ en:
|
||||
field_estimated: Estimated
|
||||
text_deliverable_locked_warning: "This deliverable is locked and cannot be saved without changing it's status to Open."
|
||||
text_deliverable_closed_warning: "This deliverable is closed and cannot be saved without changing it's status to Open."
|
||||
text_contract_locked_warning: "This contract is locked and cannot be saved without changing it's status to Open."
|
||||
text_contract_closed_warning: "This contract is closed and cannot be saved without changing it's status to Open."
|
||||
|
||||
@@ -48,13 +48,139 @@ class ContractsEditTest < ActionController::IntegrationTest
|
||||
end
|
||||
|
||||
fill_in "Name", :with => 'An updated name'
|
||||
select "Locked", :from => "Status"
|
||||
click_button "Save Contract"
|
||||
|
||||
assert_response :success
|
||||
assert_template 'contracts/show'
|
||||
|
||||
assert_equal "An updated name", @contract.reload.name
|
||||
assert_equal "locked", @contract.reload.status
|
||||
end
|
||||
|
||||
context "locked contract" do
|
||||
setup do
|
||||
assert @contract.lock!
|
||||
end
|
||||
|
||||
should "block edits" do
|
||||
visit_contract_page(@contract)
|
||||
click_link 'Update'
|
||||
assert_response :success
|
||||
|
||||
fill_in "Name", :with => 'An updated name'
|
||||
click_button 'Save Contract'
|
||||
|
||||
assert_response :success
|
||||
assert_template 'contracts/edit'
|
||||
|
||||
assert_not_equal "An updated name", @contract.reload.name
|
||||
end
|
||||
|
||||
should "block edits even when the status is changed to closed" do
|
||||
visit_contract_page(@contract)
|
||||
click_link 'Update'
|
||||
assert_response :success
|
||||
|
||||
fill_in "Name", :with => 'An updated name'
|
||||
select "Closed", :from => "Status"
|
||||
click_button 'Save Contract'
|
||||
|
||||
assert_response :success
|
||||
assert_template 'contracts/edit'
|
||||
|
||||
assert_not_equal "An updated name", @contract.reload.name
|
||||
assert @contract.reload.locked?
|
||||
end
|
||||
|
||||
should "be allowed to change the status from locked to open" do
|
||||
visit_contract_page(@contract)
|
||||
click_link 'Update'
|
||||
assert_response :success
|
||||
|
||||
select "Open", :from => "Status"
|
||||
click_button 'Save Contract'
|
||||
|
||||
assert_response :success
|
||||
assert_template 'contracts/show'
|
||||
|
||||
assert @contract.reload.open?
|
||||
end
|
||||
|
||||
should "be allowed to change the status from locked to closed" do
|
||||
visit_contract_page(@contract)
|
||||
click_link 'Update'
|
||||
assert_response :success
|
||||
|
||||
select "Closed", :from => "Status"
|
||||
click_button 'Save Contract'
|
||||
|
||||
assert_response :success
|
||||
assert_template 'contracts/show'
|
||||
|
||||
assert @contract.reload.closed?
|
||||
end
|
||||
end
|
||||
|
||||
context "closed contract" do
|
||||
setup do
|
||||
assert @contract.close!
|
||||
end
|
||||
|
||||
should "block edits" do
|
||||
visit_contract_page(@contract)
|
||||
click_link 'Update'
|
||||
assert_response :success
|
||||
|
||||
fill_in "Name", :with => 'An updated name'
|
||||
click_button 'Save Contract'
|
||||
|
||||
assert_response :success
|
||||
assert_template 'contracts/edit'
|
||||
|
||||
assert_not_equal "An updated name", @contract.reload.name
|
||||
end
|
||||
|
||||
should "block edits weven when the status is changed to locked" do
|
||||
visit_contract_page(@contract)
|
||||
click_link 'Update'
|
||||
assert_response :success
|
||||
|
||||
fill_in "Name", :with => 'An updated name'
|
||||
select "Locked", :from => "Status"
|
||||
click_button 'Save Contract'
|
||||
|
||||
assert_response :success
|
||||
assert_template 'contracts/edit'
|
||||
|
||||
assert_not_equal "An updated name", @contract.reload.name
|
||||
assert @contract.reload.closed?
|
||||
end
|
||||
|
||||
should "be allowed to change the status from closed to open" do
|
||||
visit_contract_page(@contract)
|
||||
click_link 'Update'
|
||||
assert_response :success
|
||||
|
||||
select "Open", :from => "Status"
|
||||
click_button 'Save Contract'
|
||||
|
||||
assert_response :success
|
||||
assert_template 'contracts/show'
|
||||
|
||||
assert @contract.reload.open?
|
||||
end
|
||||
|
||||
should "be allowed to change the status from closed to locked" do
|
||||
visit_contract_page(@contract)
|
||||
click_link 'Update'
|
||||
assert_response :success
|
||||
|
||||
select "Locked", :from => "Status"
|
||||
click_button 'Save Contract'
|
||||
|
||||
assert_response :success
|
||||
assert_template 'contracts/show'
|
||||
|
||||
assert @contract.reload.locked?
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
Reference in New Issue
Block a user