BigW Consortium Gitlab

Added concern for a faster "cache_key" method

This concern provides an optimized/simplified version of the "cache_key" method. This method is about 9 times faster than the default "cache_key" method. The produced cache keys _are_ different from the previous ones but this is worth the performance improvement. To showcase this I set up a benchmark (using benchmark-ips) that compares FasterCacheKeys#cache_key with the regular cache_key. The output of this benchmark was: Calculating ------------------------------------- cache_key 4.825k i/100ms cache_key_fast 21.723k i/100ms ------------------------------------------------- cache_key 59.422k (± 7.2%) i/s - 299.150k cache_key_fast 543.243k (± 9.2%) i/s - 2.694M Comparison: cache_key_fast: 543243.4 i/s cache_key: 59422.0 i/s - 9.14x slower To see the impact on real code I applied these changes and benchmarked Issue#referenced_merge_requests. For an issue referencing 10 merge requests these changes shaved off between 40 and 60 milliseconds.
parent 685c048d
......@@ -25,6 +25,7 @@ v 8.11.0 (unreleased)
- Limit git rev-list output count to one in forced push check
- Clean up unused routes (Josef Strzibny)
- Add green outline to New Branch button. !5447 (winniehell)
- Optimize generating of cache keys for issues and notes
- Improve performance of syntax highlighting Markdown code blocks
- Update to gitlab_git 10.4.1 and take advantage of preserved Ref objects
- Remove delay when hitting "Reply..." button on page with a lot of discussions
......
module FasterCacheKeys
# A faster version of Rails' "cache_key" method.
#
# Rails' default "cache_key" method uses all kind of complex logic to figure
# out the cache key. In many cases this complexity and overhead may not be
# needed.
#
# This method does not do any timestamp parsing as this process is quite
# expensive and not needed when generating cache keys. This method also relies
# on the table name instead of the cache namespace name as the latter uses
# complex logic to generate the exact same value (as when using the table
# name) in 99% of the cases.
def cache_key
"#{self.class.table_name}/#{id}-#{read_attribute_before_type_cast(:updated_at)}"
end
end
......@@ -7,6 +7,7 @@ class Issue < ActiveRecord::Base
include Sortable
include Taskable
include Spammable
include FasterCacheKeys
DueDateStruct = Struct.new(:title, :name).freeze
NoDueDate = DueDateStruct.new('No Due Date', '0').freeze
......
......@@ -5,6 +5,7 @@ class Note < ActiveRecord::Base
include Mentionable
include Awardable
include Importable
include FasterCacheKeys
# Attribute containing rendered and redacted Markdown as generated by
# Banzai::ObjectRenderer.
......
require 'spec_helper'
describe FasterCacheKeys do
describe '#cache_key' do
it 'returns a String' do
# We're using a fixed string here so it's easier to set an expectation for
# the resulting cache key.
time = '2016-08-08 16:39:00+02'
issue = build(:issue, updated_at: time)
issue.extend(described_class)
expect(issue).to receive(:id).and_return(1)
expect(issue.cache_key).to eq("issues/1-#{time}")
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