Clarify the default behavior of feature_available? method on a project (project_feature.rb)
The docs (https://docs.gitlab.com/ee/development/feature_flags/development.html) cover the usage of ::Feature.enabled?(feature, user, default_enabled: true) but doesn't cover the behavior of
@project.feature_available?
By default, @project.feature_available?
defaults to true if Feature.disable(<feature>)
has not been called in a rails c
(rails console)(Feature flag not set to false, but the user DOES have permission to the feature otherwise). This leads to confusion because in dev environments other developers won't have the feature flag explicitly turned off.
https://gitlab.com/gitlab-org/gitlab/blob/v12.4.0-rc42-ee/app/models/project_feature.rb#L93
def feature_available?(feature, user)
# This feature might not be behind a feature flag at all, so default to true
return false unless ::Feature.enabled?(feature, user, default_enabled: true)
get_permission(user, feature)
end
Example of confusion:
Summary:
If Developer 1 merged a feature flagged feature to master, and Developer 2 pulls master and did not explicitly set Feature.disable(<feature>)
, they will see the feature enabled by default. If they are not aware of the @project.feature_available
behavior, they may incorrectly assume the feature flag is not working.
In https://gitlab.com/gitlab-org/gitlab/blob/master/ee/app/policies/ee/project_policy.rb#L83 we have:
with_scope :subject
condition(:licenses_list_enabled) do
@subject.feature_available?(:licenses_list)
end
We then have https://gitlab.com/gitlab-org/gitlab/blob/master/ee/app/policies/ee/project_policy.rb#L170:
rule { licenses_list_enabled & can?(:read_software_license_policy) }.enable :read_licenses_list
in the UI we have https://gitlab.com/gitlab-org/gitlab/blob/master/ee%2Fapp%2Fhelpers%2Fee%2Fprojects_helper.rb#L47
if can?(current_user, :read_licenses_list, project)
nav_tabs << :licenses
end
Relevant Slack discussion:
Solution:
Document the default_enabled: true
behavior for @project.feature_available?