diff options
Diffstat (limited to 'spec/lib/gitlab/issuables_count_for_state_spec.rb')
-rw-r--r-- | spec/lib/gitlab/issuables_count_for_state_spec.rb | 102 |
1 files changed, 102 insertions, 0 deletions
diff --git a/spec/lib/gitlab/issuables_count_for_state_spec.rb b/spec/lib/gitlab/issuables_count_for_state_spec.rb index a6170c146ab..cc4ebba863d 100644 --- a/spec/lib/gitlab/issuables_count_for_state_spec.rb +++ b/spec/lib/gitlab/issuables_count_for_state_spec.rb @@ -66,4 +66,106 @@ RSpec.describe Gitlab::IssuablesCountForState do end end end + + context 'when store_in_redis_cache is `true`', :clean_gitlab_redis_cache do + let_it_be(:user) { create(:user) } + let_it_be(:group) { create(:group) } + + let(:cache_options) { { expires_in: 1.hour } } + let(:cache_key) { ['group', group.id, 'issues'] } + let(:threshold) { described_class::THRESHOLD } + let(:states_count) { { opened: 1, closed: 1, all: 2 } } + let(:params) { {} } + + subject { described_class.new(finder, fast_fail: true, store_in_redis_cache: true ) } + + before do + allow(finder).to receive(:count_by_state).and_return(states_count) + allow_next_instance_of(described_class) do |counter| + allow(counter).to receive(:parent_group).and_return(group) + end + end + + shared_examples 'calculating counts without caching' do + it 'does not store in redis store' do + expect(Rails.cache).not_to receive(:read) + expect(finder).to receive(:count_by_state) + expect(Rails.cache).not_to receive(:write) + expect(subject[:all]).to eq(states_count[:all]) + end + end + + context 'with Issues' do + let(:finder) { IssuesFinder.new(user, params) } + + it 'returns -1 for the requested state' do + allow(finder).to receive(:count_by_state).and_raise(ActiveRecord::QueryCanceled) + expect(Rails.cache).not_to receive(:write) + + expect(subject[:all]).to eq(-1) + end + + context 'when parent group is not present' do + let(:group) { nil } + + it_behaves_like 'calculating counts without caching' + end + + context 'when params include search filters' do + let(:parent) { group } + + before do + finder.params[:assignee_username] = [user.username, 'root'] + end + + it_behaves_like 'calculating counts without caching' + end + + context 'when counts are stored in cache' do + before do + allow(Rails.cache).to receive(:read).with(cache_key, cache_options) + .and_return({ opened: 1000, closed: 1000, all: 2000 }) + end + + it 'does not call finder count_by_state' do + expect(finder).not_to receive(:count_by_state) + + expect(subject[:all]).to eq(2000) + end + end + + context 'when cache is empty' do + context 'when state counts are under threshold' do + let(:states_count) { { opened: 1, closed: 1, all: 2 } } + + it 'does not store state counts in cache' do + expect(Rails.cache).to receive(:read).with(cache_key, cache_options) + expect(finder).to receive(:count_by_state) + expect(Rails.cache).not_to receive(:write) + expect(subject[:all]).to eq(states_count[:all]) + end + end + + context 'when state counts are over threshold' do + let(:states_count) do + { opened: threshold + 1, closed: threshold + 1, all: (threshold + 1) * 2 } + end + + it 'stores state counts in cache' do + expect(Rails.cache).to receive(:read).with(cache_key, cache_options) + expect(finder).to receive(:count_by_state) + expect(Rails.cache).to receive(:write).with(cache_key, states_count, cache_options) + + expect(subject[:all]).to eq((threshold + 1) * 2) + end + end + end + end + + context 'with Merge Requests' do + let(:finder) { MergeRequestsFinder.new(user, params) } + + it_behaves_like 'calculating counts without caching' + end + end end |