Commit e2aff3de authored by Michael Kozono's avatar Michael Kozono

Create JobArtifactDeletedEvent on destroy artifact

parent b7dd9dec
......@@ -7,7 +7,19 @@ module EE
extend ActiveSupport::Concern
prepended do
after_destroy :log_geo_event
scope :with_files_stored_locally, -> { where(file_store: [nil, JobArtifactUploader::LOCAL_STORE]) }
end
def local_store?
[nil, JobArtifactUploader::LOCAL_STORE].include?(self.file_store)
end
private
def log_geo_event
::Geo::JobArtifactDeletedEventStore.new(self).create
end
end
end
......@@ -4,6 +4,6 @@ module Geo
belongs_to :job_artifact, class_name: 'Ci::JobArtifact'
validates :job_artifact, presence: true
validates :job_artifact, :file_path, presence: true
end
end
module Geo
class JobArtifactDeletedEventStore < EventStore
self.event_type = :job_artifact_deleted_event
attr_reader :job_artifact
def initialize(job_artifact)
@job_artifact = job_artifact
end
def create
return unless job_artifact.local_store?
super
end
private
def build_event
Geo::JobArtifactDeletedEvent.new(
job_artifact: job_artifact,
file_path: relative_file_path
)
end
def local_store_path
Pathname.new(JobArtifactUploader.local_store_path)
end
def relative_file_path
return unless job_artifact.file.present?
Pathname.new(job_artifact.file.path).relative_path_from(local_store_path)
end
# This is called by ProjectLogHelpers to build json log with context info
#
# @see ::Gitlab::Geo::ProjectLogHelpers
def base_log_data(message)
{
class: self.class.name,
job_artifact_id: job_artifact.id,
file_path: job_artifact.file.path,
message: message
}
end
end
end
require 'spec_helper'
describe EE::Ci::JobArtifact do
describe '#destroy' do
set(:primary) { create(:geo_node, :primary) }
set(:secondary) { create(:geo_node) }
it 'creates a JobArtifactDeletedEvent' do
job_artifact = create(:ci_job_artifact, :archive)
expect do
job_artifact.destroy
end.to change { Geo::JobArtifactDeletedEvent.count }.by(1)
end
end
end
require 'spec_helper'
describe Geo::JobArtifactDeletedEventStore do
set(:secondary_node) { create(:geo_node) }
let(:job_artifact) { create(:ci_job_artifact, :archive) }
subject(:event_store) { described_class.new(job_artifact) }
describe '#create' do
it 'does not create an event when not running on a primary node' do
allow(Gitlab::Geo).to receive(:primary?) { false }
expect { event_store.create }.not_to change(Geo::JobArtifactDeletedEvent, :count)
end
context 'when running on a primary node' do
before do
allow(Gitlab::Geo).to receive(:primary?) { true }
end
it 'does not create an event when LFS object is not on a local store' do
allow(job_artifact).to receive(:local_store?).and_return(false)
expect { event_store.create }.not_to change(Geo::JobArtifactDeletedEvent, :count)
end
it 'does not create an event when there are no secondary nodes' do
allow(Gitlab::Geo).to receive(:secondary_nodes) { [] }
expect { event_store.create }.not_to change(Geo::JobArtifactDeletedEvent, :count)
end
it 'creates a LFS object deleted event' do
expect { event_store.create }.to change(Geo::JobArtifactDeletedEvent, :count).by(1)
end
it 'tracks LFS object attributes' do
event_store.create
event = Geo::JobArtifactDeletedEvent.last
expect(event.job_artifact_id).to eq(job_artifact.id)
expect(event.file_path).to match(%r{\A\h+/\h+/\h+/[\d_]+/\d+/\d+/ci_build_artifacts.zip\z})
end
it 'logs an error message when event creation fail' do
invalid_job_artifact = create(:ci_job_artifact)
event_store = described_class.new(invalid_job_artifact)
expected_message = {
class: "Geo::JobArtifactDeletedEventStore",
job_artifact_id: invalid_job_artifact.id,
file_path: nil,
message: "Job artifact deleted event could not be created",
error: "Validation failed: File path can't be blank"
}
expect(Gitlab::Geo::Logger).to receive(:error)
.with(expected_message).and_call_original
event_store.create
end
end
end
end
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment