diff --git a/app/models/user_contributed_projects.rb b/app/models/user_contributed_projects.rb index bc63f6be1b7..1f8e9a3f480 100644 --- a/app/models/user_contributed_projects.rb +++ b/app/models/user_contributed_projects.rb @@ -7,37 +7,39 @@ class UserContributedProjects < ActiveRecord::Base CACHE_EXPIRY_TIME = 1.day - def self.track(event) - # For events without a project, we simply don't care. - # An example of this is the creation of a snippet (which - # is not related to any project). - return unless event.project + class << self + def track(event) + # For events without a project, we simply don't care. + # An example of this is the creation of a snippet (which + # is not related to any project). + return unless event.project - # This is a precaution because the cache lookup - # will work just fine without an author. - # - # However, this should never happen (tm). - raise 'event#author not present unexpectedly' unless event.author + # This is a precaution because the cache lookup + # will work just fine without an author. + # + # However, this should never happen (tm). + raise 'event#author not present unexpectedly' unless event.author - attributes = { - project_id: event.project_id, - user_id: event.author_id - } + attributes = { + project_id: event.project_id, + user_id: event.author_id + } - cached_exists?(attributes) do - begin - find_or_create_by!(attributes) - true # not caching the whole record here for now - rescue ActiveRecord::RecordNotUnique - retry + cached_exists?(attributes) do + begin + find_or_create_by!(attributes) + true # not caching the whole record here for now + rescue ActiveRecord::RecordNotUnique + retry + end end end - end - private + private - def self.cached_exists?(project_id:, user_id:, &block) - cache_key = "user_contributed_projects:#{project_id}:#{user_id}" - Rails.cache.fetch(cache_key, expires_in: CACHE_EXPIRY_TIME, &block) + def cached_exists?(project_id:, user_id:, &block) + cache_key = "user_contributed_projects:#{project_id}:#{user_id}" + Rails.cache.fetch(cache_key, expires_in: CACHE_EXPIRY_TIME, &block) + end end end diff --git a/spec/models/user_contributed_projects_spec.rb b/spec/models/user_contributed_projects_spec.rb index 776f36675d8..f92a9d91f8b 100644 --- a/spec/models/user_contributed_projects_spec.rb +++ b/spec/models/user_contributed_projects_spec.rb @@ -1,7 +1,6 @@ require 'spec_helper' describe UserContributedProjects do - describe '.track' do subject { described_class.track(event) } let(:event) { build(:event) } @@ -10,33 +9,33 @@ describe UserContributedProjects do context "for all actions (event types)" do let(:event) { build(:event, action: action) } it 'creates a record' do - expect { subject }.to change { UserContributedProjects.count }.from(0).to(1) + expect { subject }.to change { described_class.count }.from(0).to(1) end end end it 'sets project accordingly' do subject - expect(UserContributedProjects.first.project).to eq(event.project) + expect(described_class.first.project).to eq(event.project) end it 'sets user accordingly' do subject - expect(UserContributedProjects.first.user).to eq(event.author) + expect(described_class.first.user).to eq(event.author) end it 'only creates a record once per user/project' do expect do subject described_class.track(event) - end.to change { UserContributedProjects.count }.from(0).to(1) + end.to change { described_class.count }.from(0).to(1) end describe 'with an event without a project' do let(:event) { build(:event, project: nil) } it 'ignores the event' do - expect { subject }.not_to change { UserContributedProjects.count } + expect { subject }.not_to change { described_class.count } end end end