debian-mirror-gitlab/lib/gitlab/etag_caching/store.rb

58 lines
1.3 KiB
Ruby
Raw Normal View History

2019-02-15 15:39:39 +05:30
# frozen_string_literal: true
2017-08-17 22:00:37 +05:30
module Gitlab
module EtagCaching
class Store
2021-04-17 20:07:23 +05:30
InvalidKeyError = Class.new(StandardError)
2017-08-17 22:00:37 +05:30
EXPIRY_TIME = 20.minutes
2019-12-04 20:38:33 +05:30
SHARED_STATE_NAMESPACE = 'etag:'
2017-08-17 22:00:37 +05:30
def get(key)
2017-09-10 17:25:29 +05:30
Gitlab::Redis::SharedState.with { |redis| redis.get(redis_shared_state_key(key)) }
2017-08-17 22:00:37 +05:30
end
def touch(key, only_if_missing: false)
etag = generate_etag
2017-09-10 17:25:29 +05:30
Gitlab::Redis::SharedState.with do |redis|
redis.set(redis_shared_state_key(key), etag, ex: EXPIRY_TIME, nx: only_if_missing)
2017-08-17 22:00:37 +05:30
end
etag
end
private
def generate_etag
SecureRandom.hex
end
2017-09-10 17:25:29 +05:30
def redis_shared_state_key(key)
2021-04-17 20:07:23 +05:30
raise InvalidKeyError, "#{key} is invalid" unless valid_key?(key)
2017-09-10 17:25:29 +05:30
"#{SHARED_STATE_NAMESPACE}#{key}"
2021-04-17 20:07:23 +05:30
rescue InvalidKeyError => e
Gitlab::ErrorTracking.track_and_raise_for_dev_exception(e)
end
def valid_key?(key)
return true if skip_validation?
path, header = key.split(':', 2)
env = {
'PATH_INFO' => path,
'HTTP_X_GITLAB_GRAPHQL_RESOURCE_ETAG' => header
}
fake_request = ActionDispatch::Request.new(env)
!!Gitlab::EtagCaching::Router.match(fake_request)
end
def skip_validation?
Rails.env.production?
2017-08-17 22:00:37 +05:30
end
end
end
end