Commit 386b9ace authored by Fabio Pitino's avatar Fabio Pitino Committed by Douglas Barbosa Alexandre

Create shared examples and helpers to test EventStore

Have a consistent way of testing publishing and consumption
of events.
parent 53920cb3
......@@ -290,3 +290,43 @@ executed synchronously every time the given event is published.
For complex conditions it's best to subscribe to all the events and then handle the logic
in the `handle_event` method of the subscriber worker.
## Testing
A publisher doesn't must care what subscribed to the event being published. The publisher's
responsibility is to ensure that the event is published correctly.
To test that an event has been published correctly, we can use the RSpec matcher `:publish_event`:
```ruby
it 'publishes a ProjectDeleted event with project id and namespace id' do
expected_data = { project_id: project.id, namespace_id: project.namespace_id }
# The matcher verifies that when the block is called, the block publishes the expected event and data.
expect { destroy_project(project, user, {}) }
.to publish_event(Projects::ProjectDeletedEvent)
.with(expected_data)
end
```
The subscriber must ensure that a published event can be consumed correctly. For this purpose
we have added helpers and shared examples to standardize the way we test subscribers:
```ruby
RSpec.describe MergeRequests::UpdateHeadPipelineWorker do
let(:event) { Ci::PipelineCreatedEvent.new(data: ({ pipeline_id: pipeline.id })) }
# This shared example ensures that an event is published and correctly processed by
# the current subscriber (`described_class`).
it_behaves_like 'consumes the published event' do
let(:event) { event }
end
it 'does something' do
# This helper directly executes `perform` ensuring that `handle_event` is called correctly.
consume_event(subscriber: described_class, event: event)
# run expectations
end
end
```
......@@ -11,17 +11,15 @@ RSpec.describe Geo::CreateRepositoryUpdatedEventWorker do
let(:event) { Repositories::KeepAroundRefsCreatedEvent.new(data: { project_id: project.id }) }
subject { consume_event(event) }
def consume_event(event)
described_class.new.perform(event.class.name, event.data)
end
subject { consume_event(subscriber: described_class, event: event) }
context 'on a Geo primary site' do
before do
stub_current_geo_node(primary_site)
end
it_behaves_like 'subscribes to event'
include_examples 'an idempotent worker' do
let(:job_args) { [event.class.name, event.data] }
......
......@@ -4,16 +4,18 @@ require 'spec_helper'
RSpec.describe Security::Findings::DeleteByJobIdWorker do
let(:job_ids) { [1, 2, 3] }
let(:event) { Ci::PipelineCreatedEvent.new(data: { job_ids: job_ids }) }
let(:event) { Ci::JobArtifactsDeletedEvent.new(data: { job_ids: job_ids }) }
subject(:consume_event) { described_class.new.perform(event.class.name, event.data) }
subject { consume_event(subscriber: described_class, event: event) }
before do
allow(::Security::Findings::CleanupService).to receive(:delete_by_build_ids)
end
it_behaves_like 'subscribes to event'
it 'initiates the cleanup by build ids' do
consume_event
subject
expect(::Security::Findings::CleanupService).to have_received(:delete_by_build_ids).with(job_ids)
end
......
# frozen_string_literal: true
RSpec.shared_examples 'subscribes to event' do
include AfterNextHelpers
it 'consumes the published event', :sidekiq_inline do
expect_next(described_class)
.to receive(:handle_event)
.with(instance_of(event.class))
.and_call_original
::Gitlab::EventStore.publish(event)
end
end
def consume_event(subscriber:, event:)
subscriber.new.perform(event.class.name, event.data)
end
......@@ -11,11 +11,9 @@ RSpec.describe MergeRequests::UpdateHeadPipelineWorker do
let(:pipeline) { create(:ci_pipeline, project: project, ref: ref) }
let(:event) { Ci::PipelineCreatedEvent.new(data: { pipeline_id: pipeline.id }) }
subject { consume_event(event) }
subject { consume_event(subscriber: described_class, event: event) }
def consume_event(event)
described_class.new.perform(event.class.name, event.data)
end
it_behaves_like 'subscribes to event'
context 'when merge requests already exist for this source branch', :sidekiq_inline do
let(:merge_request_1) do
......
......@@ -9,11 +9,9 @@ RSpec.describe Namespaces::UpdateRootStatisticsWorker do
Projects::ProjectDeletedEvent.new(data: { project_id: 1, namespace_id: namespace_id })
end
subject { consume_event(event) }
subject { consume_event(subscriber: described_class, event: event) }
def consume_event(event)
described_class.new.perform(event.class.name, event.data)
end
it_behaves_like 'subscribes to event'
it 'enqueues ScheduleAggregationWorker' do
expect(Namespaces::ScheduleAggregationWorker).to receive(:perform_async).with(namespace_id)
......
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