summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--app/assets/javascripts/jobs/components/sidebar_details_block.vue15
-rw-r--r--app/models/ci/build.rb12
-rw-r--r--app/serializers/build_details_entity.rb5
-rw-r--r--db/migrate/20180221022556_add_used_timeout_and_timeout_source_columns_to_ci_builds.rb15
-rw-r--r--db/schema.rb2
-rw-r--r--spec/lib/gitlab/import_export/safe_model_attributes.yml2
-rw-r--r--spec/models/concerns/chronic_duration_attribute_spec.rb50
-rw-r--r--spec/services/ci/retry_build_service_spec.rb3
8 files changed, 84 insertions, 20 deletions
diff --git a/app/assets/javascripts/jobs/components/sidebar_details_block.vue b/app/assets/javascripts/jobs/components/sidebar_details_block.vue
index 56814a52525..94c2084623b 100644
--- a/app/assets/javascripts/jobs/components/sidebar_details_block.vue
+++ b/app/assets/javascripts/jobs/components/sidebar_details_block.vue
@@ -39,6 +39,15 @@
runnerId() {
return `#${this.job.runner.id}`;
},
+ timeout() {
+ let t = `${this.job.timeout.value}`;
+
+ if (this.job.timeout.source != null) {
+ t += ` (from ${this.job.timeout.source})`;
+ }
+
+ return t;
+ },
renderBlock() {
return this.job.merge_request ||
this.job.duration ||
@@ -115,6 +124,12 @@
:value="queued"
/>
<detail-row
+ class="js-job-timeout"
+ v-if="job.timeout"
+ title="Timeout"
+ :value="timeout"
+ />
+ <detail-row
class="js-job-runner"
v-if="job.runner"
title="Runner"
diff --git a/app/models/ci/build.rb b/app/models/ci/build.rb
index 61a0ef08dde..3072817f443 100644
--- a/app/models/ci/build.rb
+++ b/app/models/ci/build.rb
@@ -6,6 +6,7 @@ module Ci
include ObjectStorage::BackgroundMove
include Presentable
include Importable
+ include ChronicDurationAttribute
MissingDependenciesError = Class.new(StandardError)
@@ -90,6 +91,8 @@ module Ci
after_commit :update_project_statistics_after_save, on: [:create, :update]
after_commit :update_project_statistics, on: :destroy
+ chronic_duration_attribute_reader :used_timeout_user_readable, :used_timeout
+
class << self
# This is needed for url_for to work,
# as the controller is JobsController
@@ -120,6 +123,10 @@ module Ci
end
after_transition pending: :running do |build|
+ build.used_timeout = build.timeout
+ build.timeout_source = build.should_use_runner_timeout? ? 'Runner' : 'Project'
+ build.save!
+
build.run_after_commit do
BuildHooksWorker.perform_async(id)
end
@@ -232,15 +239,14 @@ module Ci
end
def timeout
- return runner.maximum_job_timeout if should_use_runner_timeout
+ return runner.maximum_job_timeout if should_use_runner_timeout?
project.build_timeout
end
- def should_use_runner_timeout
+ def should_use_runner_timeout?
!runner.nil? && runner.defines_maximum_job_timeout? && runner.maximum_job_timeout < project.build_timeout
end
- private :should_use_runner_timeout
def triggered_by?(current_user)
user == current_user
diff --git a/app/serializers/build_details_entity.rb b/app/serializers/build_details_entity.rb
index 69d46f5ec14..d1a4a9561d2 100644
--- a/app/serializers/build_details_entity.rb
+++ b/app/serializers/build_details_entity.rb
@@ -5,6 +5,11 @@ class BuildDetailsEntity < JobEntity
expose :runner, using: RunnerEntity
expose :pipeline, using: PipelineEntity
+ expose :timeout, if: -> (*) { !build.used_timeout.nil? } do |build|
+ { value: build.used_timeout_user_readable,
+ source: build.timeout_source }
+ end
+
expose :erased_by, if: -> (*) { build.erased? }, using: UserEntity
expose :erase_path, if: -> (*) { build.erasable? && can?(current_user, :erase_build, build) } do |build|
erase_project_job_path(project, build)
diff --git a/db/migrate/20180221022556_add_used_timeout_and_timeout_source_columns_to_ci_builds.rb b/db/migrate/20180221022556_add_used_timeout_and_timeout_source_columns_to_ci_builds.rb
new file mode 100644
index 00000000000..cb8651b1cfd
--- /dev/null
+++ b/db/migrate/20180221022556_add_used_timeout_and_timeout_source_columns_to_ci_builds.rb
@@ -0,0 +1,15 @@
+class AddUsedTimeoutAndTimeoutSourceColumnsToCiBuilds < ActiveRecord::Migration
+ include Gitlab::Database::MigrationHelpers
+
+ DOWNTIME = false
+
+ def up
+ add_column :ci_builds, :used_timeout, :integer
+ add_column :ci_builds, :timeout_source, :string
+ end
+
+ def down
+ remove_column :ci_builds, :used_timeout
+ remove_column :ci_builds, :timeout_source
+ end
+end
diff --git a/db/schema.rb b/db/schema.rb
index 806e829dcbd..61f15944f5a 100644
--- a/db/schema.rb
+++ b/db/schema.rb
@@ -311,6 +311,8 @@ ActiveRecord::Schema.define(version: 20180327101207) do
t.integer "artifacts_metadata_store"
t.boolean "protected"
t.integer "failure_reason"
+ t.integer "used_timeout"
+ t.string "timeout_source"
end
add_index "ci_builds", ["artifacts_expire_at"], name: "index_ci_builds_on_artifacts_expire_at", where: "(artifacts_file <> ''::text)", using: :btree
diff --git a/spec/lib/gitlab/import_export/safe_model_attributes.yml b/spec/lib/gitlab/import_export/safe_model_attributes.yml
index 0716852f57f..bd7e60a5d9e 100644
--- a/spec/lib/gitlab/import_export/safe_model_attributes.yml
+++ b/spec/lib/gitlab/import_export/safe_model_attributes.yml
@@ -283,6 +283,8 @@ CommitStatus:
- retried
- protected
- failure_reason
+- used_timeout
+- timeout_source
Ci::Variable:
- id
- project_id
diff --git a/spec/models/concerns/chronic_duration_attribute_spec.rb b/spec/models/concerns/chronic_duration_attribute_spec.rb
index 1a352537aaf..85adfaf4487 100644
--- a/spec/models/concerns/chronic_duration_attribute_spec.rb
+++ b/spec/models/concerns/chronic_duration_attribute_spec.rb
@@ -1,28 +1,46 @@
require 'spec_helper'
-shared_examples 'ChronicDurationAttribute' do
- describe 'dynamically defined methods' do
- it { expect(subject.class).to be_public_method_defined(virtual_field) }
- it { expect(subject.class).to be_public_method_defined("#{virtual_field}=") }
+shared_examples 'ChronicDurationAttribute reader' do
+ it 'contains dynamically created reader method' do
+ expect(subject.class).to be_public_method_defined(virtual_field)
+ end
- it 'parses chronic duration input' do
- subject.send("#{virtual_field}=", "10m")
+ it 'outputs chronic duration formated value' do
+ subject.send("#{source_field}=", 120)
- expect(subject.send(source_field)).to eq(600)
- end
+ expect(subject.send(virtual_field)).to eq('2m')
+ end
+end
+
+shared_examples 'ChronicDurationAttribute writer' do
+ it 'contains dynamically created writer method' do
+ expect(subject.class).to be_public_method_defined("#{virtual_field}=")
+ end
- it 'outputs chronic duration formated value' do
- subject.send("#{source_field}=", 120)
+ it 'parses chronic duration input' do
+ subject.send("#{virtual_field}=", "10m")
- expect(subject.send(virtual_field)).to eq('2m')
- end
+ expect(subject.send(source_field)).to eq(600)
end
end
describe 'ChronicDurationAttribute' do
- let(:source_field) { :maximum_job_timeout }
- let(:virtual_field) { :maximum_job_timeout_user_readable }
- subject { Ci::Runner.new }
+ let(:source_field) {:maximum_job_timeout}
+ let(:virtual_field) {:maximum_job_timeout_user_readable}
+ subject {Ci::Runner.new}
+
+ it_behaves_like 'ChronicDurationAttribute reader'
+ it_behaves_like 'ChronicDurationAttribute writer'
+end
+
+describe 'ChronicDurationAttribute - reader' do
+ let(:source_field) {:used_timeout}
+ let(:virtual_field) {:used_timeout_user_readable}
+ subject {Ci::Build.new}
+
+ it "doesn't contain dynamically created writer method" do
+ expect(subject.class).not_to be_public_method_defined("#{virtual_field}=")
+ end
- it_behaves_like 'ChronicDurationAttribute'
+ it_behaves_like 'ChronicDurationAttribute reader'
end
diff --git a/spec/services/ci/retry_build_service_spec.rb b/spec/services/ci/retry_build_service_spec.rb
index b86a3d72bb4..e425e80e51e 100644
--- a/spec/services/ci/retry_build_service_spec.rb
+++ b/spec/services/ci/retry_build_service_spec.rb
@@ -29,7 +29,8 @@ describe Ci::RetryBuildService do
commit_id deployments erased_by_id last_deployment project_id
runner_id tag_taggings taggings tags trigger_request_id
user_id auto_canceled_by_id retried failure_reason
- artifacts_file_store artifacts_metadata_store].freeze
+ artifacts_file_store artifacts_metadata_store
+ used_timeout timeout_source].freeze
shared_examples 'build duplication' do
let(:another_pipeline) { create(:ci_empty_pipeline, project: project) }