Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix/transaction for update progress job #15236

Merged
merged 3 commits into from
Apr 15, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion app/services/journals/create_service.rb
Original file line number Diff line number Diff line change
Expand Up @@ -48,7 +48,7 @@ def initialize(journable, user)
self.journable = journable
end

def call(notes: '', cause: {})
def call(notes: "", cause: {})
# JSON columns read from the database always have string keys. As we do not know what is passed in here,
# and we want to compare it to values read from the DB, we need to stringify the keys here as well
normalized_cause = cause.deep_stringify_keys
Expand Down
10 changes: 6 additions & 4 deletions app/workers/work_packages/apply_statuses_p_complete_job.rb
Original file line number Diff line number Diff line change
Expand Up @@ -88,10 +88,12 @@ def journal_cause_from(cause_type, status_name:, status_id:, change:)
end

def with_temporary_progress_table
create_temporary_progress_table
yield
ensure
drop_temporary_progress_table
WorkPackage.transaction do
create_temporary_progress_table
yield
ensure
drop_temporary_progress_table
end
end

def create_temporary_progress_table
Expand Down
13 changes: 8 additions & 5 deletions app/workers/work_packages/update_progress_job.rb
Original file line number Diff line number Diff line change
Expand Up @@ -60,10 +60,12 @@ def perform(current_mode:, previous_mode:)
private

def with_temporary_progress_table
create_temporary_progress_table
yield
ensure
drop_temporary_progress_table
WorkPackage.transaction do
create_temporary_progress_table
yield
ensure
drop_temporary_progress_table
end
end

def create_temporary_progress_table
Expand Down Expand Up @@ -242,7 +244,8 @@ def copy_progress_values_to_work_packages

def create_journals_for_updated_work_packages(updated_work_package_ids)
WorkPackage.where(id: updated_work_package_ids).find_each do |work_package|
Journals::CreateService.new(work_package, system_user)
Journals::CreateService
.new(work_package, system_user)
.call(cause: { type: "system_update", feature: "progress_calculation_changed" })
end
end
Expand Down
2 changes: 1 addition & 1 deletion db/migrate/20240402072213_update_progress_calculation.rb
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ def up
current_mode = "field"
end

perform_method = Rails.env.production? ? :perform_later : :perform_now
perform_method = Rails.env.development? ? :perform_now : :perform_later
WorkPackages::UpdateProgressJob.public_send(perform_method, current_mode:, previous_mode:)
end

Expand Down
49 changes: 48 additions & 1 deletion spec/migrations/update_progress_calculation_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -31,7 +31,11 @@

RSpec.describe UpdateProgressCalculation, type: :model do
# Silencing migration logs, since we are not interested in that during testing
subject(:run_migration) { ActiveRecord::Migration.suppress_messages { described_class.new.up } }
subject(:run_migration) do
perform_enqueued_jobs do
ActiveRecord::Migration.suppress_messages { described_class.new.up }
end
end

shared_let(:author) { create(:user) }
shared_let(:priority) { create(:priority, name: "Normal") }
Expand Down Expand Up @@ -686,4 +690,47 @@ def expect_migrates(from:, to:)
end
end
end

describe "error during job execution" do
cbliard marked this conversation as resolved.
Show resolved Hide resolved
let_work_packages(<<~TABLE)
subject | work | remaining work | % complete | ∑ work | ∑ remaining work | ∑ % complete
wp working | | 4h | 60% | 10h | 4h | 60%
wp breaking | | 4h | 60% | 10h | 4h | 60%
TABLE

before do
Setting.work_package_done_ratio = "field"

allow(Journals::CreateService)
.to receive(:new)
.with(wp_working, User.system)
.and_call_original

allow(Journals::CreateService)
.to receive(:new)
.with(wp_breaking, User.system)
.and_return(nil)

ActiveRecord::Migration.suppress_messages { described_class.new.up }

begin
perform_enqueued_jobs
rescue StandardError
end
end

it "does not create a journal entry" do
table_work_packages.each do |wp|
expect(wp.journals.count).to eq(1)
end
end

it "does not update the work packages" do
expect_work_packages(WorkPackage.all, <<~TABLE)
subject | work | remaining work | % complete | ∑ work | ∑ remaining work | ∑ % complete
wp working | | 4h | 60% | 10h | 4h | 60%
wp breaking | | 4h | 60% | 10h | 4h | 60%
TABLE
end
end
end
40 changes: 40 additions & 0 deletions spec/workers/work_packages/apply_statuses_p_complete_job_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -219,4 +219,44 @@ def expect_performing_job_changes(from:, to:,
end
end
end

context "with errors during job execution",
with_settings: { work_package_done_ratio: "status" } do
let_work_packages(<<~TABLE)
subject | status | % complete
wp | Doing (40%) |
wp 0% | To do (0%) | 50%
wp 40% | Doing (40%) | 50%
wp 100% | Done (100%) | 50%
TABLE

before do
allow(Journals::CreateService)
.to receive(:new)
.and_call_original

allow(Journals::CreateService)
.to receive(:new)
.with(WorkPackage.last, User.system)
.and_return(nil)

begin
job.perform_now(cause_type: "status_p_complete_changed",
status_name: "New",
status_id: 99,
change: [33, 66])
rescue StandardError
end
end

it "does not update any work package" do
expect_work_packages(WorkPackage.all, <<~TABLE)
subject | status | % complete
wp | Doing (40%) |
wp 0% | To do (0%) | 50%
wp 40% | Doing (40%) | 50%
wp 100% | Done (100%) | 50%
TABLE
end
end
end
Loading