Commit 5a72461a authored by Shinya Maeda's avatar Shinya Maeda

Merge branch 'afontaine/remove-legacy-flag-enum' into 'master'

Remove Legacy Flag from Feature Flag Enum

See merge request gitlab-org/gitlab!68408
parents 76f9e2bd c229d56e
...@@ -10,9 +10,6 @@ class Projects::FeatureFlagsController < Projects::ApplicationController ...@@ -10,9 +10,6 @@ class Projects::FeatureFlagsController < Projects::ApplicationController
before_action :feature_flag, only: [:edit, :update, :destroy] before_action :feature_flag, only: [:edit, :update, :destroy]
before_action :ensure_flag_writable!, only: [:update]
before_action :exclude_legacy_flags_check, only: [:edit]
feature_category :feature_flags feature_category :feature_flags
def index def index
...@@ -98,18 +95,6 @@ class Projects::FeatureFlagsController < Projects::ApplicationController ...@@ -98,18 +95,6 @@ class Projects::FeatureFlagsController < Projects::ApplicationController
@feature_flag ||= @noteable = project.operations_feature_flags.find_by_iid!(params[:iid]) @feature_flag ||= @noteable = project.operations_feature_flags.find_by_iid!(params[:iid])
end end
def ensure_flag_writable!
if feature_flag.legacy_flag?
render_error_json(['Legacy feature flags are read-only'])
end
end
def exclude_legacy_flags_check
if feature_flag.legacy_flag?
not_found
end
end
def create_params def create_params
params.require(:operations_feature_flag) params.require(:operations_feature_flag)
.permit(:name, :description, :active, :version, .permit(:name, :description, :active, :version,
......
...@@ -17,6 +17,7 @@ module Operations ...@@ -17,6 +17,7 @@ module Operations
has_internal_id :iid, scope: :project has_internal_id :iid, scope: :project
default_value_for :active, true default_value_for :active, true
default_value_for :version, :new_version_flag
# scopes exists only for the first version # scopes exists only for the first version
has_many :scopes, class_name: 'Operations::FeatureFlagScope' has_many :scopes, class_name: 'Operations::FeatureFlagScope'
...@@ -39,8 +40,6 @@ module Operations ...@@ -39,8 +40,6 @@ module Operations
validate :first_default_scope, on: :create, if: :has_scopes? validate :first_default_scope, on: :create, if: :has_scopes?
validate :version_associations validate :version_associations
before_create :build_default_scope, if: -> { legacy_flag? && scopes.none? }
accepts_nested_attributes_for :scopes, allow_destroy: true accepts_nested_attributes_for :scopes, allow_destroy: true
accepts_nested_attributes_for :strategies, allow_destroy: true accepts_nested_attributes_for :strategies, allow_destroy: true
...@@ -52,7 +51,6 @@ module Operations ...@@ -52,7 +51,6 @@ module Operations
scope :new_version_only, -> { where(version: :new_version_flag)} scope :new_version_only, -> { where(version: :new_version_flag)}
enum version: { enum version: {
legacy_flag: 1,
new_version_flag: 2 new_version_flag: 2
} }
...@@ -127,8 +125,6 @@ module Operations ...@@ -127,8 +125,6 @@ module Operations
def version_associations def version_associations
if new_version_flag? && scopes.any? if new_version_flag? && scopes.any?
errors.add(:version_associations, 'version 2 feature flags may not have scopes') errors.add(:version_associations, 'version 2 feature flags may not have scopes')
elsif legacy_flag? && strategies.any?
errors.add(:version_associations, 'version 1 feature flags may not have strategies')
end end
end end
......
# frozen_string_literal: true # frozen_string_literal: true
# All of the legacy flags have been removed in 14.1, including all of the
# `operations_feature_flag_scopes` rows. Therefore, this model and the database
# table are unused and should be removed.
module Operations module Operations
class FeatureFlagScope < ApplicationRecord class FeatureFlagScope < ApplicationRecord
prepend HasEnvironmentScope prepend HasEnvironmentScope
......
...@@ -48,10 +48,12 @@ module FeatureFlags ...@@ -48,10 +48,12 @@ module FeatureFlags
end end
end end
def created_scope_message(scope) def created_strategy_message(strategy)
"Created rule #{scope.environment_scope} "\ scopes = strategy.scopes
"and set it as #{scope.active ? "active" : "inactive"} "\ .map { |scope| %Q("#{scope.environment_scope}") }
"with strategies #{scope.strategies}." .join(', ')
%Q(Created strategy \"#{strategy.name}\" )\
"with scopes #{scopes}."
end end
def feature_flag_by_name def feature_flag_by_name
......
...@@ -24,8 +24,8 @@ module FeatureFlags ...@@ -24,8 +24,8 @@ module FeatureFlags
def audit_message(feature_flag) def audit_message(feature_flag)
message_parts = ["Created feature flag #{feature_flag.name} with description \"#{feature_flag.description}\"."] message_parts = ["Created feature flag #{feature_flag.name} with description \"#{feature_flag.description}\"."]
message_parts += feature_flag.scopes.map do |scope| message_parts += feature_flag.strategies.map do |strategy|
created_scope_message(scope) created_strategy_message(strategy)
end end
message_parts.join(" ") message_parts.join(" ")
......
...@@ -2,10 +2,9 @@ ...@@ -2,10 +2,9 @@
module FeatureFlags module FeatureFlags
class UpdateService < FeatureFlags::BaseService class UpdateService < FeatureFlags::BaseService
AUDITABLE_SCOPE_ATTRIBUTES_HUMAN_NAMES = { AUDITABLE_STRATEGY_ATTRIBUTES_HUMAN_NAMES = {
'active' => 'active state', 'scopes' => 'environment scopes',
'environment_scope' => 'environment scope', 'parameters' => 'parameters'
'strategies' => 'strategies'
}.freeze }.freeze
def execute(feature_flag) def execute(feature_flag)
...@@ -41,7 +40,7 @@ module FeatureFlags ...@@ -41,7 +40,7 @@ module FeatureFlags
def audit_message(feature_flag) def audit_message(feature_flag)
changes = changed_attributes_messages(feature_flag) changes = changed_attributes_messages(feature_flag)
changes += changed_scopes_messages(feature_flag) changes += changed_strategies_messages(feature_flag)
return if changes.empty? return if changes.empty?
...@@ -56,29 +55,30 @@ module FeatureFlags ...@@ -56,29 +55,30 @@ module FeatureFlags
end end
end end
def changed_scopes_messages(feature_flag) def changed_strategies_messages(feature_flag)
feature_flag.scopes.map do |scope| feature_flag.strategies.map do |strategy|
if scope.new_record? if strategy.new_record?
created_scope_message(scope) created_strategy_message(strategy)
elsif scope.marked_for_destruction? elsif strategy.marked_for_destruction?
deleted_scope_message(scope) deleted_strategy_message(strategy)
else else
updated_scope_message(scope) updated_strategy_message(strategy)
end end
end.compact # updated_scope_message can return nil if nothing has been changed end.compact # updated_strategy_message can return nil if nothing has been changed
end end
def deleted_scope_message(scope) def deleted_strategy_message(strategy)
"Deleted rule #{scope.environment_scope}." scopes = strategy.scopes.map { |scope| scope.environment_scope }.join(', ')
"Deleted strategy #{strategy.name} with environment scopes #{scopes}."
end end
def updated_scope_message(scope) def updated_strategy_message(strategy)
changes = scope.changes.slice(*AUDITABLE_SCOPE_ATTRIBUTES_HUMAN_NAMES.keys) changes = strategy.changes.slice(*AUDITABLE_STRATEGY_ATTRIBUTES_HUMAN_NAMES.keys)
return if changes.empty? return if changes.empty?
message = "Updated rule #{scope.environment_scope} " message = "Updated strategy #{strategy.name} "
message += changes.map do |attribute_name, change| message += changes.map do |attribute_name, change|
name = AUDITABLE_SCOPE_ATTRIBUTES_HUMAN_NAMES[attribute_name] name = AUDITABLE_STRATEGY_ATTRIBUTES_HUMAN_NAMES[attribute_name]
"#{name} from #{change.first} to #{change.second}" "#{name} from #{change.first} to #{change.second}"
end.join(' ') end.join(' ')
......
...@@ -126,6 +126,7 @@ From there, you can see the following actions: ...@@ -126,6 +126,7 @@ From there, you can see the following actions:
- User password required for approvals was updated ([introduced](https://gitlab.com/gitlab-org/gitlab/-/issues/336211) in GitLab 14.2) - User password required for approvals was updated ([introduced](https://gitlab.com/gitlab-org/gitlab/-/issues/336211) in GitLab 14.2)
- Permission to modify merge requests approval rules in merge requests was updated ([introduced](https://gitlab.com/gitlab-org/gitlab/-/issues/336211) in GitLab 14.2) - Permission to modify merge requests approval rules in merge requests was updated ([introduced](https://gitlab.com/gitlab-org/gitlab/-/issues/336211) in GitLab 14.2)
- New approvals requirement when new commits are added to an MR was updated ([introduced](https://gitlab.com/gitlab-org/gitlab/-/issues/336211) in GitLab 14.2) - New approvals requirement when new commits are added to an MR was updated ([introduced](https://gitlab.com/gitlab-org/gitlab/-/issues/336211) in GitLab 14.2)
- When [strategies for feature flags](../operations/feature_flags.md#feature-flag-strategies) are changed ([introduced](https://gitlab.com/gitlab-org/gitlab/-/merge_requests/68408) in GitLab 14.3)
Project events can also be accessed via the [Project Audit Events API](../api/audit_events.md#project-audit-events). Project events can also be accessed via the [Project Audit Events API](../api/audit_events.md#project-audit-events).
......
...@@ -118,7 +118,7 @@ module API ...@@ -118,7 +118,7 @@ module API
put do put do
authorize_update_feature_flag! authorize_update_feature_flag!
exclude_legacy_flags_check! exclude_legacy_flags_check!
render_api_error!('PUT operations are not supported for legacy feature flags', :unprocessable_entity) if feature_flag.legacy_flag? render_api_error!('PUT operations are not supported for legacy feature flags', :unprocessable_entity) unless feature_flag.new_version_flag?
attrs = declared_params(include_missing: false) attrs = declared_params(include_missing: false)
...@@ -207,7 +207,7 @@ module API ...@@ -207,7 +207,7 @@ module API
end end
def exclude_legacy_flags_check! def exclude_legacy_flags_check!
if feature_flag.legacy_flag? unless feature_flag.new_version_flag?
not_found! not_found!
end end
end end
......
# frozen_string_literal: true
FactoryBot.define do
factory :operations_feature_flag_scope, class: 'Operations::FeatureFlagScope' do
association :feature_flag, factory: [:operations_feature_flag, :legacy_flag]
active { true }
strategies { [{ name: "default", parameters: {} }] }
sequence(:environment_scope) { |n| "review/patch-#{n}" }
end
end
...@@ -6,13 +6,5 @@ FactoryBot.define do ...@@ -6,13 +6,5 @@ FactoryBot.define do
project project
active { true } active { true }
version { :new_version_flag } version { :new_version_flag }
trait :legacy_flag do
version { Operations::FeatureFlag.versions['legacy_flag'] }
end
trait :new_version_flag do
version { Operations::FeatureFlag.versions['new_version_flag'] }
end
end end
end end
...@@ -66,20 +66,4 @@ RSpec.describe 'User updates feature flag', :js do ...@@ -66,20 +66,4 @@ RSpec.describe 'User updates feature flag', :js do
end end
end end
end end
context 'with a legacy feature flag' do
let!(:feature_flag) do
create_flag(project, 'ci_live_trace', true,
description: 'For live trace feature',
version: :legacy_flag)
end
let!(:scope) { create_scope(feature_flag, 'review/*', true) }
it 'shows not found error' do
visit(edit_project_feature_flag_path(project, feature_flag))
expect(page).to have_text 'Page Not Found'
end
end
end end
...@@ -72,13 +72,5 @@ RSpec.describe FeatureFlagsFinder do ...@@ -72,13 +72,5 @@ RSpec.describe FeatureFlagsFinder do
subject subject
end end
end end
context 'with a legacy flag' do
let!(:feature_flag_3) { create(:operations_feature_flag, :legacy_flag, name: 'flag-c', project: project) }
it 'returns new flags' do
is_expected.to eq([feature_flag_1, feature_flag_2])
end
end
end end
end end
{ {
"type": "object", "type": "object",
"required" : [ "required": ["id", "name"],
"id", "properties": {
"name"
],
"properties" : {
"id": { "type": "integer" }, "id": { "type": "integer" },
"iid": { "type": ["integer", "null"] }, "iid": { "type": ["integer", "null"] },
"version": { "type": "string" }, "version": { "type": "string" },
......
This diff is collapsed.
...@@ -49,28 +49,7 @@ RSpec.describe Operations::FeatureFlag do ...@@ -49,28 +49,7 @@ RSpec.describe Operations::FeatureFlag do
it { is_expected.to validate_presence_of(:project) } it { is_expected.to validate_presence_of(:project) }
it { is_expected.to validate_presence_of(:name) } it { is_expected.to validate_presence_of(:name) }
it { is_expected.to validate_uniqueness_of(:name).scoped_to(:project_id) } it { is_expected.to validate_uniqueness_of(:name).scoped_to(:project_id) }
it { is_expected.to define_enum_for(:version).with_values(legacy_flag: 1, new_version_flag: 2) } it { is_expected.to define_enum_for(:version).with_values(new_version_flag: 2) }
context 'a version 1 feature flag' do
it 'is valid if associated with Operations::FeatureFlagScope models' do
project = create(:project)
feature_flag = described_class.create!({ name: 'test', project: project, version: 1,
scopes_attributes: [{ environment_scope: '*', active: false }] })
expect(feature_flag).to be_valid
end
it 'is invalid if associated with Operations::FeatureFlags::Strategy models' do
project = create(:project)
feature_flag = described_class.new({ name: 'test', project: project, version: 1,
strategies_attributes: [{ name: 'default', parameters: {} }] })
expect(feature_flag.valid?).to eq(false)
expect(feature_flag.errors.messages).to eq({
version_associations: ["version 1 feature flags may not have strategies"]
})
end
end
context 'a version 2 feature flag' do context 'a version 2 feature flag' do
it 'is invalid if associated with Operations::FeatureFlagScope models' do it 'is invalid if associated with Operations::FeatureFlagScope models' do
...@@ -102,64 +81,9 @@ RSpec.describe Operations::FeatureFlag do ...@@ -102,64 +81,9 @@ RSpec.describe Operations::FeatureFlag do
end end
end end
describe 'feature flag version' do
it 'defaults to 1 if unspecified' do
project = create(:project)
feature_flag = described_class.create!(name: 'my_flag', project: project, active: true)
expect(feature_flag).to be_valid
expect(feature_flag.version_before_type_cast).to eq(1)
end
end
describe 'Scope creation' do
subject { described_class.new(**params) }
let(:project) { create(:project) }
let(:params) do
{ name: 'test', project: project, scopes_attributes: scopes_attributes }
end
let(:scopes_attributes) do
[{ environment_scope: '*', active: false },
{ environment_scope: 'review/*', active: true }]
end
it { is_expected.to be_valid }
context 'when the first scope is not wildcard' do
let(:scopes_attributes) do
[{ environment_scope: 'review/*', active: true },
{ environment_scope: '*', active: false }]
end
it { is_expected.not_to be_valid }
end
end
describe 'the default scope' do describe 'the default scope' do
let_it_be(:project) { create(:project) } let_it_be(:project) { create(:project) }
context 'with a version 1 feature flag' do
it 'creates a default scope' do
feature_flag = described_class.create!({ name: 'test', project: project, scopes_attributes: [], version: 1 })
expect(feature_flag.scopes.count).to eq(1)
expect(feature_flag.scopes.first.environment_scope).to eq('*')
end
it 'allows specifying the default scope in the parameters' do
feature_flag = described_class.create!({ name: 'test', project: project,
scopes_attributes: [{ environment_scope: '*', active: false },
{ environment_scope: 'review/*', active: true }], version: 1 })
expect(feature_flag.scopes.count).to eq(2)
expect(feature_flag.scopes.first.environment_scope).to eq('*')
end
end
context 'with a version 2 feature flag' do context 'with a version 2 feature flag' do
it 'does not create a default scope' do it 'does not create a default scope' do
feature_flag = described_class.create!({ name: 'test', project: project, scopes_attributes: [], version: 2 }) feature_flag = described_class.create!({ name: 'test', project: project, scopes_attributes: [], version: 2 })
...@@ -180,16 +104,6 @@ RSpec.describe Operations::FeatureFlag do ...@@ -180,16 +104,6 @@ RSpec.describe Operations::FeatureFlag do
end end
end end
context 'when the feature flag is active and all scopes are inactive' do
let!(:feature_flag) { create(:operations_feature_flag, :legacy_flag, active: true) }
it 'returns the flag' do
feature_flag.default_scope.update!(active: false)
is_expected.to eq([feature_flag])
end
end
context 'when the feature flag is inactive' do context 'when the feature flag is inactive' do
let!(:feature_flag) { create(:operations_feature_flag, active: false) } let!(:feature_flag) { create(:operations_feature_flag, active: false) }
...@@ -197,16 +111,6 @@ RSpec.describe Operations::FeatureFlag do ...@@ -197,16 +111,6 @@ RSpec.describe Operations::FeatureFlag do
is_expected.to be_empty is_expected.to be_empty
end end
end end
context 'when the feature flag is inactive and all scopes are active' do
let!(:feature_flag) { create(:operations_feature_flag, :legacy_flag, active: false) }
it 'does not return the flag' do
feature_flag.default_scope.update!(active: true)
is_expected.to be_empty
end
end
end end
describe '.disabled' do describe '.disabled' do
...@@ -220,16 +124,6 @@ RSpec.describe Operations::FeatureFlag do ...@@ -220,16 +124,6 @@ RSpec.describe Operations::FeatureFlag do
end end
end end
context 'when the feature flag is active and all scopes are inactive' do
let!(:feature_flag) { create(:operations_feature_flag, :legacy_flag, active: true) }
it 'does not return the flag' do
feature_flag.default_scope.update!(active: false)
is_expected.to be_empty
end
end
context 'when the feature flag is inactive' do context 'when the feature flag is inactive' do
let!(:feature_flag) { create(:operations_feature_flag, active: false) } let!(:feature_flag) { create(:operations_feature_flag, active: false) }
...@@ -237,16 +131,6 @@ RSpec.describe Operations::FeatureFlag do ...@@ -237,16 +131,6 @@ RSpec.describe Operations::FeatureFlag do
is_expected.to eq([feature_flag]) is_expected.to eq([feature_flag])
end end
end end
context 'when the feature flag is inactive and all scopes are active' do
let!(:feature_flag) { create(:operations_feature_flag, :legacy_flag, active: false) }
it 'returns the flag' do
feature_flag.default_scope.update!(active: true)
is_expected.to eq([feature_flag])
end
end
end end
describe '.for_unleash_client' do describe '.for_unleash_client' do
......
...@@ -116,21 +116,6 @@ RSpec.describe API::FeatureFlags do ...@@ -116,21 +116,6 @@ RSpec.describe API::FeatureFlags do
}]) }])
end end
end end
context 'with version 1 and 2 feature flags' do
it 'returns both versions of flags ordered by name' do
create(:operations_feature_flag, project: project, name: 'legacy_flag')
feature_flag = create(:operations_feature_flag, :new_version_flag, project: project, name: 'new_version_flag')
strategy = create(:operations_strategy, feature_flag: feature_flag, name: 'default', parameters: {})
create(:operations_scope, strategy: strategy, environment_scope: 'production')
subject
expect(response).to have_gitlab_http_status(:ok)
expect(response).to match_response_schema('public_api/v4/feature_flags')
expect(json_response.map { |f| f['name'] }).to eq(%w[legacy_flag new_version_flag])
end
end
end end
describe 'GET /projects/:id/feature_flags/:name' do describe 'GET /projects/:id/feature_flags/:name' do
...@@ -185,22 +170,13 @@ RSpec.describe API::FeatureFlags do ...@@ -185,22 +170,13 @@ RSpec.describe API::FeatureFlags do
end end
describe 'POST /projects/:id/feature_flags' do describe 'POST /projects/:id/feature_flags' do
def scope_default
{
environment_scope: '*',
active: false,
strategies: [{ name: 'default', parameters: {} }].to_json
}
end
subject do subject do
post api("/projects/#{project.id}/feature_flags", user), params: params post api("/projects/#{project.id}/feature_flags", user), params: params
end end
let(:params) do let(:params) do
{ {
name: 'awesome-feature', name: 'awesome-feature'
scopes: [scope_default]
} }
end end
...@@ -215,14 +191,14 @@ RSpec.describe API::FeatureFlags do ...@@ -215,14 +191,14 @@ RSpec.describe API::FeatureFlags do
expect(feature_flag.description).to eq(params[:description]) expect(feature_flag.description).to eq(params[:description])
end end
it 'defaults to a version 1 (legacy) feature flag' do it 'defaults to a version 2 (new) feature flag' do
subject subject
expect(response).to have_gitlab_http_status(:created) expect(response).to have_gitlab_http_status(:created)
expect(response).to match_response_schema('public_api/v4/feature_flag') expect(response).to match_response_schema('public_api/v4/feature_flag')
feature_flag = project.operations_feature_flags.last feature_flag = project.operations_feature_flags.last
expect(feature_flag.version).to eq('legacy_flag') expect(feature_flag.version).to eq('new_version_flag')
end end
it_behaves_like 'check user permission' it_behaves_like 'check user permission'
...@@ -232,38 +208,7 @@ RSpec.describe API::FeatureFlags do ...@@ -232,38 +208,7 @@ RSpec.describe API::FeatureFlags do
expect(response).to have_gitlab_http_status(:created) expect(response).to have_gitlab_http_status(:created)
expect(response).to match_response_schema('public_api/v4/feature_flag') expect(response).to match_response_schema('public_api/v4/feature_flag')
expect(json_response['version']).to eq('legacy_flag') expect(json_response['version']).to eq('new_version_flag')
end
context 'with active set to false in the params for a legacy flag' do
let(:params) do
{
name: 'awesome-feature',
version: 'legacy_flag',
active: 'false',
scopes: [scope_default]
}
end
it 'creates an inactive feature flag' do
subject
expect(response).to have_gitlab_http_status(:created)
expect(response).to match_response_schema('public_api/v4/feature_flag')
expect(json_response['active']).to eq(false)
end
end
context 'when no scopes passed in parameters' do
let(:params) { { name: 'awesome-feature' } }
it 'creates a new feature flag with active default scope' do
subject
expect(response).to have_gitlab_http_status(:created)
feature_flag = project.operations_feature_flags.last
expect(feature_flag.default_scope).to be_active
end
end end
context 'when there is a feature flag with the same name already' do context 'when there is a feature flag with the same name already' do
...@@ -278,43 +223,6 @@ RSpec.describe API::FeatureFlags do ...@@ -278,43 +223,6 @@ RSpec.describe API::FeatureFlags do
end end
end end
context 'when create a feature flag with two scopes' do
let(:params) do
{
name: 'awesome-feature',
description: 'this is awesome',
scopes: [
scope_default,
scope_with_user_with_id
]
}
end
let(:scope_with_user_with_id) do
{
environment_scope: 'production',
active: true,
strategies: [{
name: 'userWithId',
parameters: { userIds: 'user:1' }
}].to_json
}
end
it 'creates a new feature flag with two scopes' do
subject
expect(response).to have_gitlab_http_status(:created)
feature_flag = project.operations_feature_flags.last
feature_flag.scopes.ordered.each_with_index do |scope, index|
expect(scope.environment_scope).to eq(params[:scopes][index][:environment_scope])
expect(scope.active).to eq(params[:scopes][index][:active])
expect(scope.strategies).to eq(Gitlab::Json.parse(params[:scopes][index][:strategies]))
end
end
end
context 'when creating a version 2 feature flag' do context 'when creating a version 2 feature flag' do
it 'creates a new feature flag' do it 'creates a new feature flag' do
params = { params = {
...@@ -455,23 +363,6 @@ RSpec.describe API::FeatureFlags do ...@@ -455,23 +363,6 @@ RSpec.describe API::FeatureFlags do
end end
describe 'PUT /projects/:id/feature_flags/:name' do describe 'PUT /projects/:id/feature_flags/:name' do
context 'with a legacy feature flag' do
let!(:feature_flag) do
create(:operations_feature_flag, :legacy_flag, project: project,
name: 'feature1', description: 'old description')
end
it 'returns a 404' do
params = { description: 'new description' }
put api("/projects/#{project.id}/feature_flags/feature1", user), params: params
expect(response).to have_gitlab_http_status(:not_found)
expect(json_response).to eq({ 'message' => '404 Not Found' })
expect(feature_flag.reload.description).to eq('old description')
end
end
context 'with a version 2 feature flag' do context 'with a version 2 feature flag' do
let!(:feature_flag) do let!(:feature_flag) do
create(:operations_feature_flag, :new_version_flag, project: project, active: true, create(:operations_feature_flag, :new_version_flag, project: project, active: true,
...@@ -781,7 +672,7 @@ RSpec.describe API::FeatureFlags do ...@@ -781,7 +672,7 @@ RSpec.describe API::FeatureFlags do
params: params params: params
end end
let!(:feature_flag) { create(:operations_feature_flag, :legacy_flag, project: project) } let!(:feature_flag) { create(:operations_feature_flag, project: project) }
let(:params) { {} } let(:params) { {} }
it 'destroys the feature flag' do it 'destroys the feature flag' do
...@@ -794,7 +685,7 @@ RSpec.describe API::FeatureFlags do ...@@ -794,7 +685,7 @@ RSpec.describe API::FeatureFlags do
subject subject
expect(response).to have_gitlab_http_status(:ok) expect(response).to have_gitlab_http_status(:ok)
expect(json_response['version']).to eq('legacy_flag') expect(json_response['version']).to eq('new_version_flag')
end end
context 'with a version 2 feature flag' do context 'with a version 2 feature flag' do
......
...@@ -176,25 +176,6 @@ RSpec.describe API::Unleash do ...@@ -176,25 +176,6 @@ RSpec.describe API::Unleash do
it_behaves_like 'authenticated request' it_behaves_like 'authenticated request'
context 'with version 1 (legacy) feature flags' do
let(:feature_flag) { create(:operations_feature_flag, :legacy_flag, project: project, name: 'feature1', active: true, version: 1) }
it 'does not return a legacy feature flag' do
create(:operations_feature_flag_scope,
feature_flag: feature_flag,
environment_scope: 'sandbox',
active: true,
strategies: [{ name: "gradualRolloutUserId",
parameters: { groupId: "default", percentage: "50" } }])
headers = { "UNLEASH-INSTANCEID" => client.token, "UNLEASH-APPNAME" => "sandbox" }
get api(features_url), headers: headers
expect(response).to have_gitlab_http_status(:ok)
expect(json_response['features']).to be_empty
end
end
context 'with version 2 feature flags' do context 'with version 2 feature flags' do
it 'does not return a flag without any strategies' do it 'does not return a flag without any strategies' do
create(:operations_feature_flag, project: project, create(:operations_feature_flag, project: project,
......
...@@ -48,8 +48,9 @@ RSpec.describe FeatureFlags::CreateService do ...@@ -48,8 +48,9 @@ RSpec.describe FeatureFlags::CreateService do
{ {
name: 'feature_flag', name: 'feature_flag',
description: 'description', description: 'description',
scopes_attributes: [{ environment_scope: '*', active: true }, version: 'new_version_flag',
{ environment_scope: 'production', active: false }] strategies_attributes: [{ name: 'default', scopes_attributes: [{ environment_scope: '*' }], parameters: {} },
{ name: 'default', parameters: {}, scopes_attributes: [{ environment_scope: 'production' }] }]
} }
end end
...@@ -70,10 +71,10 @@ RSpec.describe FeatureFlags::CreateService do ...@@ -70,10 +71,10 @@ RSpec.describe FeatureFlags::CreateService do
it 'creates audit event' do it 'creates audit event' do
expected_message = 'Created feature flag feature_flag '\ expected_message = 'Created feature flag feature_flag '\
'with description "description". '\ 'with description "description". '\
'Created rule * and set it as active '\ 'Created strategy "default" with scopes '\
'with strategies [{"name"=&gt;"default", "parameters"=&gt;{}}]. '\ '"*". '\
'Created rule production and set it as inactive '\ 'Created strategy "default" with scopes '\
'with strategies [{"name"=&gt;"default", "parameters"=&gt;{}}].' '"production".'
expect { subject }.to change { AuditEvent.count }.by(1) expect { subject }.to change { AuditEvent.count }.by(1)
expect(AuditEvent.last.details[:custom_message]).to eq(expected_message) expect(AuditEvent.last.details[:custom_message]).to eq(expected_message)
......
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