From f69e33d77ef3fa980979b56684c566524de8ee92 Mon Sep 17 00:00:00 2001 From: Erick Bajao <fbajao@gitlab.com> Date: Tue, 14 Mar 2023 11:15:30 +0000 Subject: [PATCH] Resolve object storage config via symbol This adds support for referencing storage config via symbols. --- .../ci/pipeline_artifact_uploader.rb | 2 +- app/uploaders/ci/secure_file_uploader.rb | 2 +- app/uploaders/deleted_object_uploader.rb | 2 +- .../dependency_proxy/file_uploader.rb | 2 +- app/uploaders/external_diff_uploader.rb | 2 +- app/uploaders/gitlab_uploader.rb | 17 +++- app/uploaders/job_artifact_uploader.rb | 2 +- app/uploaders/lfs_object_uploader.rb | 2 +- .../packages/composer/cache_uploader.rb | 2 +- .../debian/component_file_uploader.rb | 2 +- .../distribution_release_file_uploader.rb | 2 +- .../packages/package_file_uploader.rb | 2 +- .../packages/rpm/repository_file_uploader.rb | 2 +- app/uploaders/pages/deployment_uploader.rb | 2 +- app/uploaders/terraform/state_uploader.rb | 2 +- lib/object_storage/config.rb | 12 +++ .../concerns/send_file_upload_spec.rb | 2 +- spec/lib/object_storage/config_spec.rb | 2 +- spec/uploaders/gitlab_uploader_spec.rb | 17 +++- spec/uploaders/object_storage/cdn_spec.rb | 88 +++++++++---------- spec/uploaders/object_storage_spec.rb | 2 +- 21 files changed, 101 insertions(+), 67 deletions(-) diff --git a/app/uploaders/ci/pipeline_artifact_uploader.rb b/app/uploaders/ci/pipeline_artifact_uploader.rb index d3a83c5d633a3..62e00fe1a663b 100644 --- a/app/uploaders/ci/pipeline_artifact_uploader.rb +++ b/app/uploaders/ci/pipeline_artifact_uploader.rb @@ -4,7 +4,7 @@ module Ci class PipelineArtifactUploader < GitlabUploader include ObjectStorage::Concern - storage_options Gitlab.config.artifacts + storage_location :artifacts alias_method :upload, :model diff --git a/app/uploaders/ci/secure_file_uploader.rb b/app/uploaders/ci/secure_file_uploader.rb index 11cbfc6c1f210..09d9b3abafb8b 100644 --- a/app/uploaders/ci/secure_file_uploader.rb +++ b/app/uploaders/ci/secure_file_uploader.rb @@ -4,7 +4,7 @@ module Ci class SecureFileUploader < GitlabUploader include ObjectStorage::Concern - storage_options Gitlab.config.ci_secure_files + storage_location :ci_secure_files # Use Lockbox to encrypt/decrypt the stored file (registers CarrierWave callbacks) encrypt(key: :key) diff --git a/app/uploaders/deleted_object_uploader.rb b/app/uploaders/deleted_object_uploader.rb index fc0f62b920c74..eaf584c5dfa5b 100644 --- a/app/uploaders/deleted_object_uploader.rb +++ b/app/uploaders/deleted_object_uploader.rb @@ -3,7 +3,7 @@ class DeletedObjectUploader < GitlabUploader include ObjectStorage::Concern - storage_options Gitlab.config.artifacts + storage_location :artifacts def store_dir model.store_dir diff --git a/app/uploaders/dependency_proxy/file_uploader.rb b/app/uploaders/dependency_proxy/file_uploader.rb index f0222d4cf0693..d4e486bfe8427 100644 --- a/app/uploaders/dependency_proxy/file_uploader.rb +++ b/app/uploaders/dependency_proxy/file_uploader.rb @@ -5,7 +5,7 @@ class DependencyProxy::FileUploader < GitlabUploader include ObjectStorage::Concern before :cache, :set_content_type - storage_options Gitlab.config.dependency_proxy + storage_location :dependency_proxy alias_method :upload, :model diff --git a/app/uploaders/external_diff_uploader.rb b/app/uploaders/external_diff_uploader.rb index d2707cd07774c..86c3d73417424 100644 --- a/app/uploaders/external_diff_uploader.rb +++ b/app/uploaders/external_diff_uploader.rb @@ -3,7 +3,7 @@ class ExternalDiffUploader < GitlabUploader include ObjectStorage::Concern - storage_options Gitlab.config.external_diffs + storage_location :external_diffs alias_method :upload, :model diff --git a/app/uploaders/gitlab_uploader.rb b/app/uploaders/gitlab_uploader.rb index 62024bff4c080..2eb34288bd71b 100644 --- a/app/uploaders/gitlab_uploader.rb +++ b/app/uploaders/gitlab_uploader.rb @@ -3,7 +3,7 @@ class GitlabUploader < CarrierWave::Uploader::Base include ContentTypeWhitelist::Concern - class_attribute :options + class_attribute :storage_location_identifier PROTECTED_METHODS = %i(filename cache_dir work_dir store_dir).freeze @@ -11,8 +11,13 @@ class GitlabUploader < CarrierWave::Uploader::Base class << self # DSL setter - def storage_options(options) - self.options = options + def storage_location(location) + self.storage_location_identifier = location + _ = options # Ensures that we have a valid storage_location_identifier + end + + def options + ObjectStorage::Config::LOCATIONS.fetch(storage_location_identifier) end def root @@ -41,7 +46,7 @@ def version(*args, **kwargs, &block) end end - storage_options Gitlab.config.uploads + storage_location :uploads delegate :base_dir, :file_storage?, to: :class @@ -51,6 +56,10 @@ def initialize(model, mounted_as = nil, **uploader_context) super(model, mounted_as) end + def options + self.class.options + end + def file_cache_storage? cache_storage.is_a?(CarrierWave::Storage::File) end diff --git a/app/uploaders/job_artifact_uploader.rb b/app/uploaders/job_artifact_uploader.rb index b38e7d93eac8a..5ee8c42f51024 100644 --- a/app/uploaders/job_artifact_uploader.rb +++ b/app/uploaders/job_artifact_uploader.rb @@ -7,7 +7,7 @@ class JobArtifactUploader < GitlabUploader UnknownFileLocationError = Class.new(StandardError) - storage_options Gitlab.config.artifacts + storage_location :artifacts alias_method :upload, :model diff --git a/app/uploaders/lfs_object_uploader.rb b/app/uploaders/lfs_object_uploader.rb index 027857500f4da..4111bb923226d 100644 --- a/app/uploaders/lfs_object_uploader.rb +++ b/app/uploaders/lfs_object_uploader.rb @@ -4,7 +4,7 @@ class LfsObjectUploader < GitlabUploader extend Workhorse::UploadPath include ObjectStorage::Concern - storage_options Gitlab.config.lfs + storage_location :lfs alias_method :upload, :model diff --git a/app/uploaders/packages/composer/cache_uploader.rb b/app/uploaders/packages/composer/cache_uploader.rb index ad7c017c4ba21..ef581b5d6a1f6 100644 --- a/app/uploaders/packages/composer/cache_uploader.rb +++ b/app/uploaders/packages/composer/cache_uploader.rb @@ -2,7 +2,7 @@ class Packages::Composer::CacheUploader < GitlabUploader include ObjectStorage::Concern - storage_options Gitlab.config.packages + storage_location :packages alias_method :upload, :model diff --git a/app/uploaders/packages/debian/component_file_uploader.rb b/app/uploaders/packages/debian/component_file_uploader.rb index 2de4743d7f746..b1ed8d853f16d 100644 --- a/app/uploaders/packages/debian/component_file_uploader.rb +++ b/app/uploaders/packages/debian/component_file_uploader.rb @@ -3,7 +3,7 @@ class Packages::Debian::ComponentFileUploader < GitlabUploader extend Workhorse::UploadPath include ObjectStorage::Concern - storage_options Gitlab.config.packages + storage_location :packages alias_method :upload, :model diff --git a/app/uploaders/packages/debian/distribution_release_file_uploader.rb b/app/uploaders/packages/debian/distribution_release_file_uploader.rb index 268d42796e9a6..fe10861b77f02 100644 --- a/app/uploaders/packages/debian/distribution_release_file_uploader.rb +++ b/app/uploaders/packages/debian/distribution_release_file_uploader.rb @@ -3,7 +3,7 @@ class Packages::Debian::DistributionReleaseFileUploader < GitlabUploader extend Workhorse::UploadPath include ObjectStorage::Concern - storage_options Gitlab.config.packages + storage_location :packages alias_method :upload, :model diff --git a/app/uploaders/packages/package_file_uploader.rb b/app/uploaders/packages/package_file_uploader.rb index c8a09c50dc6a7..57feee9f19d8f 100644 --- a/app/uploaders/packages/package_file_uploader.rb +++ b/app/uploaders/packages/package_file_uploader.rb @@ -3,7 +3,7 @@ class Packages::PackageFileUploader < GitlabUploader extend Workhorse::UploadPath include ObjectStorage::Concern - storage_options Gitlab.config.packages + storage_location :packages alias_method :upload, :model diff --git a/app/uploaders/packages/rpm/repository_file_uploader.rb b/app/uploaders/packages/rpm/repository_file_uploader.rb index f95f861585c72..399e9fa07d511 100644 --- a/app/uploaders/packages/rpm/repository_file_uploader.rb +++ b/app/uploaders/packages/rpm/repository_file_uploader.rb @@ -4,7 +4,7 @@ module Rpm class RepositoryFileUploader < GitlabUploader include ObjectStorage::Concern - storage_options Gitlab.config.packages + storage_location :packages alias_method :upload, :model diff --git a/app/uploaders/pages/deployment_uploader.rb b/app/uploaders/pages/deployment_uploader.rb index c5ba65673ab8d..bb4f1a2235df1 100644 --- a/app/uploaders/pages/deployment_uploader.rb +++ b/app/uploaders/pages/deployment_uploader.rb @@ -4,7 +4,7 @@ module Pages class DeploymentUploader < GitlabUploader include ObjectStorage::Concern - storage_options Gitlab.config.pages + storage_location :pages alias_method :upload, :model diff --git a/app/uploaders/terraform/state_uploader.rb b/app/uploaders/terraform/state_uploader.rb index 61e7ed7b0e656..5fe3048f7b0cf 100644 --- a/app/uploaders/terraform/state_uploader.rb +++ b/app/uploaders/terraform/state_uploader.rb @@ -4,7 +4,7 @@ module Terraform class StateUploader < GitlabUploader include ObjectStorage::Concern - storage_options Gitlab.config.terraform_state + storage_location :terraform_state # TODO: Remove this line # See https://gitlab.com/gitlab-org/gitlab/-/issues/232917 diff --git a/lib/object_storage/config.rb b/lib/object_storage/config.rb index fb0334959a3f6..8a2044a8cba31 100644 --- a/lib/object_storage/config.rb +++ b/lib/object_storage/config.rb @@ -6,6 +6,18 @@ class Config AZURE_PROVIDER = 'AzureRM' GOOGLE_PROVIDER = 'Google' + LOCATIONS = { + artifacts: Gitlab.config.artifacts, + ci_secure_files: Gitlab.config.ci_secure_files, + dependency_proxy: Gitlab.config.dependency_proxy, + external_diffs: Gitlab.config.external_diffs, + lfs: Gitlab.config.lfs, + packages: Gitlab.config.packages, + pages: Gitlab.config.pages, + terraform_state: Gitlab.config.terraform_state, + uploads: Gitlab.config.uploads + }.freeze + attr_reader :options def initialize(options) diff --git a/spec/controllers/concerns/send_file_upload_spec.rb b/spec/controllers/concerns/send_file_upload_spec.rb index 6acbff6e74549..3fe6d62329ed7 100644 --- a/spec/controllers/concerns/send_file_upload_spec.rb +++ b/spec/controllers/concerns/send_file_upload_spec.rb @@ -7,7 +7,7 @@ Class.new(GitlabUploader) do include ObjectStorage::Concern - storage_options Gitlab.config.uploads + storage_location :uploads private diff --git a/spec/lib/object_storage/config_spec.rb b/spec/lib/object_storage/config_spec.rb index 3099468c07d5f..412fcb9b6b878 100644 --- a/spec/lib/object_storage/config_spec.rb +++ b/spec/lib/object_storage/config_spec.rb @@ -4,7 +4,7 @@ require 'rspec-parameterized' require 'fog/core' -RSpec.describe ObjectStorage::Config do +RSpec.describe ObjectStorage::Config, feature_category: :shared do using RSpec::Parameterized::TableSyntax let(:region) { 'us-east-1' } diff --git a/spec/uploaders/gitlab_uploader_spec.rb b/spec/uploaders/gitlab_uploader_spec.rb index f62ab7266319f..bd86f1fe08aca 100644 --- a/spec/uploaders/gitlab_uploader_spec.rb +++ b/spec/uploaders/gitlab_uploader_spec.rb @@ -3,7 +3,7 @@ require 'spec_helper' require 'carrierwave/storage/fog' -RSpec.describe GitlabUploader do +RSpec.describe GitlabUploader, feature_category: :shared do let(:uploader_class) { Class.new(described_class) } subject(:uploader) { uploader_class.new(double) } @@ -179,4 +179,19 @@ it { expect { subject }.to raise_error(RuntimeError, /not supported/) } end + + describe '.storage_location' do + it 'sets the identifier for the storage location options' do + uploader_class.storage_location(:artifacts) + + expect(uploader_class.options).to eq(Gitlab.config.artifacts) + end + + context 'when given identifier is not known' do + it 'raises an error' do + expect { uploader_class.storage_location(:foo) } + .to raise_error(KeyError) + end + end + end end diff --git a/spec/uploaders/object_storage/cdn_spec.rb b/spec/uploaders/object_storage/cdn_spec.rb index d6c638297fac5..0c1966b4df24a 100644 --- a/spec/uploaders/object_storage/cdn_spec.rb +++ b/spec/uploaders/object_storage/cdn_spec.rb @@ -3,19 +3,6 @@ require 'spec_helper' RSpec.describe ObjectStorage::CDN, feature_category: :build_artifacts do - let(:cdn_options) do - { - 'object_store' => { - 'cdn' => { - 'provider' => 'google', - 'url' => 'https://gitlab.example.com', - 'key_name' => 'test-key', - 'key' => Base64.urlsafe_encode64('12345') - } - } - }.freeze - end - let(:uploader_class) do Class.new(GitlabUploader) do include ObjectStorage::Concern @@ -39,44 +26,66 @@ def dynamic_segment subject { uploader_class.new(object, :file) } context 'with CDN config' do + let(:cdn_options) do + { + 'object_store' => { + 'cdn' => { + 'provider' => cdn_provider, + 'url' => 'https://gitlab.example.com', + 'key_name' => 'test-key', + 'key' => Base64.urlsafe_encode64('12345') + } + } + }.freeze + end + before do stub_artifacts_object_storage(enabled: true) - uploader_class.options = Settingslogic.new(Gitlab.config.uploads.deep_merge(cdn_options)) + options = Settingslogic.new(Gitlab.config.uploads.deep_merge(cdn_options)) + allow(uploader_class).to receive(:options).and_return(options) end - describe '#cdn_enabled_url' do - it 'calls #cdn_signed_url' do - expect(subject).not_to receive(:url) - expect(subject).to receive(:cdn_signed_url).with(query_params).and_call_original + context 'with a known CDN provider' do + let(:cdn_provider) { 'google' } - result = subject.cdn_enabled_url(public_ip, query_params) + describe '#cdn_enabled_url' do + it 'calls #cdn_signed_url' do + expect(subject).not_to receive(:url) + expect(subject).to receive(:cdn_signed_url).with(query_params).and_call_original + + result = subject.cdn_enabled_url(public_ip, query_params) - expect(result.used_cdn).to be true + expect(result.used_cdn).to be true + end end - end - describe '#use_cdn?' do - it 'returns true' do - expect(subject.use_cdn?(public_ip)).to be true + describe '#use_cdn?' do + it 'returns true' do + expect(subject.use_cdn?(public_ip)).to be true + end end - end - describe '#cdn_signed_url' do - it 'returns a URL' do - expect_next_instance_of(ObjectStorage::CDN::GoogleCDN) do |cdn| - expect(cdn).to receive(:signed_url).and_return("https://cdn.example.com/path") + describe '#cdn_signed_url' do + it 'returns a URL' do + expect_next_instance_of(ObjectStorage::CDN::GoogleCDN) do |cdn| + expect(cdn).to receive(:signed_url).and_return("https://cdn.example.com/path") + end + + expect(subject.cdn_signed_url).to eq("https://cdn.example.com/path") end + end + end + + context 'with an unknown CDN provider' do + let(:cdn_provider) { 'amazon' } - expect(subject.cdn_signed_url).to eq("https://cdn.example.com/path") + it 'raises an error' do + expect { subject.use_cdn?(public_ip) }.to raise_error("Unknown CDN provider: amazon") end end end context 'without CDN config' do - before do - uploader_class.options = Gitlab.config.uploads - end - describe '#cdn_enabled_url' do it 'calls #url' do expect(subject).not_to receive(:cdn_signed_url) @@ -94,15 +103,4 @@ def dynamic_segment end end end - - context 'with an unknown CDN provider' do - before do - cdn_options['object_store']['cdn']['provider'] = 'amazon' - uploader_class.options = Settingslogic.new(Gitlab.config.uploads.deep_merge(cdn_options)) - end - - it 'raises an error' do - expect { subject.use_cdn?(public_ip) }.to raise_error("Unknown CDN provider: amazon") - end - end end diff --git a/spec/uploaders/object_storage_spec.rb b/spec/uploaders/object_storage_spec.rb index 5344dbeb51229..0e293ec973cd4 100644 --- a/spec/uploaders/object_storage_spec.rb +++ b/spec/uploaders/object_storage_spec.rb @@ -8,7 +8,7 @@ class Implementation < GitlabUploader include ::RecordsUploads::Concern prepend ::ObjectStorage::Extension::RecordsUploads - storage_options Gitlab.config.uploads + storage_location :uploads private -- GitLab