summaryrefslogtreecommitdiff
path: root/lib/api
diff options
context:
space:
mode:
Diffstat (limited to 'lib/api')
-rw-r--r--lib/api/helpers/caching.rb7
-rw-r--r--lib/api/helpers/headers_helpers.rb2
-rw-r--r--lib/api/internal/base.rb2
-rw-r--r--lib/api/releases.rb16
4 files changed, 22 insertions, 5 deletions
diff --git a/lib/api/helpers/caching.rb b/lib/api/helpers/caching.rb
index d0f22109879..64b681633b6 100644
--- a/lib/api/helpers/caching.rb
+++ b/lib/api/helpers/caching.rb
@@ -119,8 +119,11 @@ module API
objs.flatten!
map = multi_key_map(objs, context: context)
- cache.fetch_multi(*map.keys, **kwargs) do |key|
- yield map[key]
+ # TODO: `contextual_cache_key` should be constructed based on the guideline https://docs.gitlab.com/ee/development/redis.html#multi-key-commands.
+ Gitlab::Instrumentation::RedisClusterValidator.allow_cross_slot_commands do
+ cache.fetch_multi(*map.keys, **kwargs) do |key|
+ yield map[key]
+ end
end
end
diff --git a/lib/api/helpers/headers_helpers.rb b/lib/api/helpers/headers_helpers.rb
index 908c57bb04e..56445ccbd0d 100644
--- a/lib/api/helpers/headers_helpers.rb
+++ b/lib/api/helpers/headers_helpers.rb
@@ -8,7 +8,7 @@ module API
def set_http_headers(header_data)
header_data.each do |key, value|
if value.is_a?(Enumerable)
- raise ArgumentError.new("Header value should be a string")
+ raise ArgumentError, "Header value should be a string"
end
header "X-Gitlab-#{key.to_s.split('_').collect(&:capitalize).join('-')}", value.to_s
diff --git a/lib/api/internal/base.rb b/lib/api/internal/base.rb
index 4dcfc0cf7eb..ec69e1da961 100644
--- a/lib/api/internal/base.rb
+++ b/lib/api/internal/base.rb
@@ -158,7 +158,7 @@ module API
status 200
unless actor.key_or_user
- raise ActiveRecord::RecordNotFound.new('User not found!')
+ raise ActiveRecord::RecordNotFound, 'User not found!'
end
actor.update_last_used_at!
diff --git a/lib/api/releases.rb b/lib/api/releases.rb
index 0fdbe8ff866..cefdf40d789 100644
--- a/lib/api/releases.rb
+++ b/lib/api/releases.rb
@@ -33,7 +33,21 @@ module API
get ':id/releases' do
releases = ::ReleasesFinder.new(user_project, current_user, declared_params.slice(:order_by, :sort)).execute
- present paginate(releases), with: Entities::Release, current_user: current_user
+ if Feature.enabled?(:api_caching_releases, user_project, default_enabled: :yaml)
+ # We cache the serialized payload per user in order to avoid repeated renderings.
+ # Since the cached result could contain sensitive information,
+ # it will expire in a short interval.
+ present_cached paginate(releases),
+ with: Entities::Release,
+ # `current_user` could be absent if the releases are publicly accesible.
+ # We should not use `cache_key` for the user because the version/updated_at
+ # context is unnecessary here.
+ cache_context: -> (_) { "user:{#{current_user&.id}}" },
+ expires_in: 5.minutes,
+ current_user: current_user
+ else
+ present paginate(releases), with: Entities::Release, current_user: current_user
+ end
end
desc 'Get a single project release' do