2020-10-24 23:57:45 +05:30
# frozen_string_literal: true
# This class is being used to persist additional artifacts after a pipeline completes, which is a great place to cache a computed result in object storage
module Ci
2021-10-27 15:23:28 +05:30
class PipelineArtifact < Ci :: ApplicationRecord
2020-11-24 15:15:51 +05:30
include UpdateProjectStatistics
2020-10-24 23:57:45 +05:30
include Artifactable
include FileStoreMounter
2022-10-11 01:57:18 +05:30
include Lockable
2020-11-24 15:15:51 +05:30
include Presentable
2020-10-24 23:57:45 +05:30
FILE_SIZE_LIMIT = 10 . megabytes . freeze
2020-11-24 15:15:51 +05:30
EXPIRATION_DATE = 1 . week . freeze
DEFAULT_FILE_NAMES = {
2021-03-11 19:13:27 +05:30
code_coverage : 'code_coverage.json' ,
code_quality_mr_diff : 'code_quality_mr_diff.json'
} . freeze
REPORT_TYPES = {
code_coverage : :raw ,
code_quality_mr_diff : :raw
2020-11-24 15:15:51 +05:30
} . freeze
2020-10-24 23:57:45 +05:30
belongs_to :project , class_name : " Project " , inverse_of : :pipeline_artifacts
belongs_to :pipeline , class_name : " Ci::Pipeline " , inverse_of : :pipeline_artifacts
validates :pipeline , :project , :file_format , :file , presence : true
2020-11-24 15:15:51 +05:30
validates :file_store , presence : true , inclusion : { in : ObjectStorage :: SUPPORTED_STORES }
2020-10-24 23:57:45 +05:30
validates :size , presence : true , numericality : { less_than_or_equal_to : FILE_SIZE_LIMIT }
validates :file_type , presence : true
mount_file_store_uploader Ci :: PipelineArtifactUploader
2020-11-24 15:15:51 +05:30
update_project_statistics project_statistics_name : :pipeline_artifacts_size
2020-10-24 23:57:45 +05:30
enum file_type : {
2021-03-11 19:13:27 +05:30
code_coverage : 1 ,
code_quality_mr_diff : 2
2020-10-24 23:57:45 +05:30
}
2021-06-08 01:23:25 +05:30
scope :unlocked , - > { joins ( :pipeline ) . merge ( :: Ci :: Pipeline . unlocked ) }
2021-03-11 19:13:27 +05:30
class << self
def report_exists? ( file_type )
return false unless REPORT_TYPES . key? ( file_type )
where ( file_type : file_type ) . exists?
end
2020-11-24 15:15:51 +05:30
2021-03-11 19:13:27 +05:30
def find_by_file_type ( file_type )
find_by ( file_type : file_type )
end
2022-08-13 15:12:31 +05:30
2022-10-11 01:57:18 +05:30
def create_or_replace_for_pipeline! ( pipeline : , file_type : , file : , size : , locked : :unknown )
2022-08-13 15:12:31 +05:30
transaction do
pipeline . pipeline_artifacts . find_by_file_type ( file_type ) & . destroy!
pipeline . pipeline_artifacts . create! (
file_type : file_type ,
project_id : pipeline . project_id ,
size : size ,
file : file ,
file_format : REPORT_TYPES [ file_type ] ,
2022-10-11 01:57:18 +05:30
expire_at : EXPIRATION_DATE . from_now ,
locked : locked
2022-08-13 15:12:31 +05:30
)
end
rescue ActiveRecord :: ActiveRecordError = > err
Gitlab :: ErrorTracking . track_and_raise_exception ( err , { pipeline_id : pipeline . id , file_type : file_type } )
end
2020-11-24 15:15:51 +05:30
end
def present
super ( presenter_class : " Ci::PipelineArtifacts:: #{ self . file_type . camelize } Presenter " . constantize )
2020-10-24 23:57:45 +05:30
end
end
end
2021-04-29 21:17:54 +05:30
2021-06-08 01:23:25 +05:30
Ci :: PipelineArtifact . prepend_mod