Welcome to mirror list, hosted at ThFree Co, Russian Federation.

gitlab.com/gitlab-org/gitlab-foss.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorGitLab Bot <gitlab-bot@gitlab.com>2022-11-17 14:33:21 +0300
committerGitLab Bot <gitlab-bot@gitlab.com>2022-11-17 14:33:21 +0300
commit7021455bd1ed7b125c55eb1b33c5a01f2bc55ee0 (patch)
tree5bdc2229f5198d516781f8d24eace62fc7e589e9 /app/controllers
parent185b095e93520f96e9cfc31d9c3e69b498cdab7c (diff)
Add latest changes from gitlab-org/gitlab@15-6-stable-eev15.6.0-rc42
Diffstat (limited to 'app/controllers')
-rw-r--r--app/controllers/admin/application_settings_controller.rb6
-rw-r--r--app/controllers/admin/broadcast_messages_controller.rb64
-rw-r--r--app/controllers/admin/groups_controller.rb7
-rw-r--r--app/controllers/admin/users_controller.rb33
-rw-r--r--app/controllers/application_controller.rb9
-rw-r--r--app/controllers/concerns/access_tokens_actions.rb16
-rw-r--r--app/controllers/concerns/authenticates_with_two_factor.rb2
-rw-r--r--app/controllers/concerns/integrations/params.rb4
-rw-r--r--app/controllers/concerns/issuable_actions.rb58
-rw-r--r--app/controllers/concerns/issuable_collections_action.rb1
-rw-r--r--app/controllers/concerns/preferred_language_switcher.rb18
-rw-r--r--app/controllers/concerns/preview_markdown.rb2
-rw-r--r--app/controllers/concerns/product_analytics_tracking.rb2
-rw-r--r--app/controllers/concerns/render_access_tokens.rb31
-rw-r--r--app/controllers/concerns/send_file_upload.rb12
-rw-r--r--app/controllers/concerns/verifies_with_email.rb11
-rw-r--r--app/controllers/concerns/web_hooks/hook_actions.rb8
-rw-r--r--app/controllers/concerns/web_hooks/hook_execution_notice.rb2
-rw-r--r--app/controllers/confirmations_controller.rb1
-rw-r--r--app/controllers/dashboard/projects_controller.rb7
-rw-r--r--app/controllers/explore/groups_controller.rb4
-rw-r--r--app/controllers/graphql_controller.rb3
-rw-r--r--app/controllers/groups/boards_controller.rb2
-rw-r--r--app/controllers/groups/dependency_proxy/application_controller.rb5
-rw-r--r--app/controllers/groups/observability_controller.rb32
-rw-r--r--app/controllers/groups/registry/repositories_controller.rb4
-rw-r--r--app/controllers/groups/settings/access_tokens_controller.rb1
-rw-r--r--app/controllers/groups/settings/ci_cd_controller.rb3
-rw-r--r--app/controllers/groups/settings/packages_and_registries_controller.rb4
-rw-r--r--app/controllers/groups/settings/repository_controller.rb3
-rw-r--r--app/controllers/groups_controller.rb7
-rw-r--r--app/controllers/jira_connect/application_controller.rb26
-rw-r--r--app/controllers/jira_connect/cors_preflight_checks_controller.rb16
-rw-r--r--app/controllers/jira_connect/oauth_application_ids_controller.rb6
-rw-r--r--app/controllers/jira_connect/subscriptions_controller.rb6
-rw-r--r--app/controllers/oauth/authorizations_controller.rb17
-rw-r--r--app/controllers/passwords_controller.rb3
-rw-r--r--app/controllers/profiles/passwords_controller.rb6
-rw-r--r--app/controllers/profiles/personal_access_tokens_controller.rb33
-rw-r--r--app/controllers/projects/alerting/notifications_controller.rb3
-rw-r--r--app/controllers/projects/application_controller.rb6
-rw-r--r--app/controllers/projects/artifacts_controller.rb8
-rw-r--r--app/controllers/projects/boards_controller.rb2
-rw-r--r--app/controllers/projects/commit_controller.rb2
-rw-r--r--app/controllers/projects/environments_controller.rb2
-rw-r--r--app/controllers/projects/google_cloud/configuration_controller.rb2
-rw-r--r--app/controllers/projects/google_cloud/databases_controller.rb9
-rw-r--r--app/controllers/projects/google_cloud/deployments_controller.rb2
-rw-r--r--app/controllers/projects/google_cloud/gcp_regions_controller.rb2
-rw-r--r--app/controllers/projects/google_cloud/service_accounts_controller.rb2
-rw-r--r--app/controllers/projects/graphs_controller.rb2
-rw-r--r--app/controllers/projects/incidents_controller.rb1
-rw-r--r--app/controllers/projects/issues_controller.rb16
-rw-r--r--app/controllers/projects/labels_controller.rb5
-rw-r--r--app/controllers/projects/learn_gitlab_controller.rb1
-rw-r--r--app/controllers/projects/merge_requests/diffs_controller.rb22
-rw-r--r--app/controllers/projects/merge_requests_controller.rb40
-rw-r--r--app/controllers/projects/ml/experiments_controller.rb32
-rw-r--r--app/controllers/projects/notes_controller.rb2
-rw-r--r--app/controllers/projects/packages/infrastructure_registry_controller.rb2
-rw-r--r--app/controllers/projects/pipeline_schedules_controller.rb2
-rw-r--r--app/controllers/projects/pipelines_controller.rb23
-rw-r--r--app/controllers/projects/product_analytics_controller.rb61
-rw-r--r--app/controllers/projects/prometheus/alerts_controller.rb19
-rw-r--r--app/controllers/projects/registry/repositories_controller.rb10
-rw-r--r--app/controllers/projects/settings/access_tokens_controller.rb1
-rw-r--r--app/controllers/projects/settings/ci_cd_controller.rb10
-rw-r--r--app/controllers/projects/settings/repository_controller.rb30
-rw-r--r--app/controllers/projects/starrers_controller.rb10
-rw-r--r--app/controllers/projects/templates_controller.rb4
-rw-r--r--app/controllers/projects/usage_quotas_controller.rb2
-rw-r--r--app/controllers/projects/work_items_controller.rb6
-rw-r--r--app/controllers/projects_controller.rb7
-rw-r--r--app/controllers/registrations_controller.rb26
-rw-r--r--app/controllers/search_controller.rb15
-rw-r--r--app/controllers/sessions_controller.rb2
-rw-r--r--app/controllers/terraform/services_controller.rb2
-rw-r--r--app/controllers/users_controller.rb2
78 files changed, 483 insertions, 387 deletions
diff --git a/app/controllers/admin/application_settings_controller.rb b/app/controllers/admin/application_settings_controller.rb
index b75a7c4a2dd..ec9441c2b9b 100644
--- a/app/controllers/admin/application_settings_controller.rb
+++ b/app/controllers/admin/application_settings_controller.rb
@@ -13,10 +13,6 @@ class Admin::ApplicationSettingsController < Admin::ApplicationController
before_action :disable_query_limiting, only: [:usage_data]
- before_action do
- push_frontend_feature_flag(:ci_variable_settings_graphql)
- end
-
feature_category :not_owned, [ # rubocop:todo Gitlab/AvoidFeatureCategoryNotOwned
:general, :reporting, :metrics_and_profiling, :network,
:preferences, :update, :reset_health_check_token
@@ -84,7 +80,7 @@ class Admin::ApplicationSettingsController < Admin::ApplicationController
format.json do
Gitlab::UsageDataCounters::ServiceUsageDataCounter.count(:download_payload_click)
- render json: service_ping_data.to_json
+ render json: Gitlab::Json.dump(service_ping_data)
end
end
end
diff --git a/app/controllers/admin/broadcast_messages_controller.rb b/app/controllers/admin/broadcast_messages_controller.rb
index edd85414696..bdf0c6aedb9 100644
--- a/app/controllers/admin/broadcast_messages_controller.rb
+++ b/app/controllers/admin/broadcast_messages_controller.rb
@@ -3,39 +3,60 @@
class Admin::BroadcastMessagesController < Admin::ApplicationController
include BroadcastMessagesHelper
- before_action :finder, only: [:edit, :update, :destroy]
+ before_action :find_broadcast_message, only: [:edit, :update, :destroy]
+ before_action :find_broadcast_messages, only: [:index, :create]
+ before_action :push_features, only: [:index, :edit]
feature_category :onboarding
urgency :low
- # rubocop: disable CodeReuse/ActiveRecord
def index
- push_frontend_feature_flag(:vue_broadcast_messages, current_user)
- push_frontend_feature_flag(:role_targeted_broadcast_messages, current_user)
-
- @broadcast_messages = BroadcastMessage.order(ends_at: :desc).page(params[:page])
- @broadcast_message = BroadcastMessage.new
+ @broadcast_message = BroadcastMessage.new
end
- # rubocop: enable CodeReuse/ActiveRecord
def edit
end
def create
@broadcast_message = BroadcastMessage.new(broadcast_message_params)
+ success = @broadcast_message.save
- if @broadcast_message.save
- redirect_to admin_broadcast_messages_path, notice: _('Broadcast Message was successfully created.')
- else
- render :index
+ respond_to do |format|
+ format.json do
+ if success
+ render json: @broadcast_message, status: :ok
+ else
+ render json: { errors: @broadcast_message.errors.full_messages }, status: :bad_request
+ end
+ end
+ format.html do
+ if success
+ redirect_to admin_broadcast_messages_path, notice: _('Broadcast Message was successfully created.')
+ else
+ render :index
+ end
+ end
end
end
def update
- if @broadcast_message.update(broadcast_message_params)
- redirect_to admin_broadcast_messages_path, notice: _('Broadcast Message was successfully updated.')
- else
- render :edit
+ success = @broadcast_message.update(broadcast_message_params)
+
+ respond_to do |format|
+ format.json do
+ if success
+ render json: @broadcast_message, status: :ok
+ else
+ render json: { errors: @broadcast_message.errors.full_messages }, status: :bad_request
+ end
+ end
+ format.html do
+ if success
+ redirect_to admin_broadcast_messages_path, notice: _('Broadcast Message was successfully updated.')
+ else
+ render :edit
+ end
+ end
end
end
@@ -55,10 +76,14 @@ class Admin::BroadcastMessagesController < Admin::ApplicationController
protected
- def finder
+ def find_broadcast_message
@broadcast_message = BroadcastMessage.find(params[:id])
end
+ def find_broadcast_messages
+ @broadcast_messages = BroadcastMessage.order(ends_at: :desc).page(params[:page]) # rubocop: disable CodeReuse/ActiveRecord
+ end
+
def broadcast_message_params
params.require(:broadcast_message)
.permit(%i(
@@ -71,4 +96,9 @@ class Admin::BroadcastMessagesController < Admin::ApplicationController
dismissable
), target_access_levels: []).reverse_merge!(target_access_levels: [])
end
+
+ def push_features
+ push_frontend_feature_flag(:vue_broadcast_messages, current_user)
+ push_frontend_feature_flag(:role_targeted_broadcast_messages, current_user)
+ end
end
diff --git a/app/controllers/admin/groups_controller.rb b/app/controllers/admin/groups_controller.rb
index f3c4244269d..1395d4bb3b7 100644
--- a/app/controllers/admin/groups_controller.rb
+++ b/app/controllers/admin/groups_controller.rb
@@ -38,12 +38,9 @@ class Admin::GroupsController < Admin::ApplicationController
end
def create
- @group = Group.new(group_params)
- @group.name = @group.path.dup unless @group.name
+ @group = ::Groups::CreateService.new(current_user, group_params).execute
- if @group.save
- @group.add_owner(current_user)
- @group.create_namespace_settings
+ if @group.persisted?
redirect_to [:admin, @group], notice: _('Group %{group_name} was successfully created.') % { group_name: @group.name }
else
render "new"
diff --git a/app/controllers/admin/users_controller.rb b/app/controllers/admin/users_controller.rb
index 1a57d271271..2c8b4888d5d 100644
--- a/app/controllers/admin/users_controller.rb
+++ b/app/controllers/admin/users_controller.rb
@@ -26,6 +26,8 @@ class Admin::UsersController < Admin::ApplicationController
end
def show
+ @can_impersonate = can_impersonate_user
+ @impersonation_error_text = @can_impersonate ? nil : impersonation_error_text
end
# rubocop: disable CodeReuse/ActiveRecord
@@ -47,7 +49,7 @@ class Admin::UsersController < Admin::ApplicationController
end
def impersonate
- if can?(user, :log_in) && !impersonation_in_progress?
+ if can_impersonate_user
session[:impersonator_id] = current_user.id
warden.set_user(user, scope: :user)
@@ -59,16 +61,7 @@ class Admin::UsersController < Admin::ApplicationController
redirect_to root_path
else
- flash[:alert] =
- if impersonation_in_progress?
- _("You are already impersonating another user")
- elsif user.blocked?
- _("You cannot impersonate a blocked user")
- elsif user.internal?
- _("You cannot impersonate an internal user")
- else
- _("You cannot impersonate a user who cannot log in")
- end
+ flash[:alert] = impersonation_error_text
redirect_to admin_user_path(user)
end
@@ -378,6 +371,24 @@ class Admin::UsersController < Admin::ApplicationController
def log_impersonation_event
Gitlab::AppLogger.info(_("User %{current_user_username} has started impersonating %{username}") % { current_user_username: current_user.username, username: user.username })
end
+
+ def can_impersonate_user
+ can?(user, :log_in) && !user.password_expired? && !impersonation_in_progress?
+ end
+
+ def impersonation_error_text
+ if impersonation_in_progress?
+ _("You are already impersonating another user")
+ elsif user.blocked?
+ _("You cannot impersonate a blocked user")
+ elsif user.password_expired?
+ _("You cannot impersonate a user with an expired password")
+ elsif user.internal?
+ _("You cannot impersonate an internal user")
+ else
+ _("You cannot impersonate a user who cannot log in")
+ end
+ end
end
Admin::UsersController.prepend_mod_with('Admin::UsersController')
diff --git a/app/controllers/application_controller.rb b/app/controllers/application_controller.rb
index 84efb8b0da8..4de6b5de42a 100644
--- a/app/controllers/application_controller.rb
+++ b/app/controllers/application_controller.rb
@@ -13,6 +13,7 @@ class ApplicationController < ActionController::Base
include EnforcesTwoFactorAuthentication
include WithPerformanceBar
include Gitlab::SearchContext::ControllerConcern
+ include PreferredLanguageSwitcher
include SessionlessAuthentication
include SessionsHelper
include ConfirmEmailWarning
@@ -512,7 +513,13 @@ class ApplicationController < ActionController::Base
end
def set_locale(&block)
- Gitlab::I18n.with_user_locale(current_user, &block)
+ return Gitlab::I18n.with_user_locale(current_user, &block) unless Feature.enabled?(:preferred_language_switcher)
+
+ if current_user
+ Gitlab::I18n.with_user_locale(current_user, &block)
+ else
+ Gitlab::I18n.with_locale(preferred_language, &block)
+ end
end
def set_session_storage(&block)
diff --git a/app/controllers/concerns/access_tokens_actions.rb b/app/controllers/concerns/access_tokens_actions.rb
index 6e43be5594d..fdb08c6572f 100644
--- a/app/controllers/concerns/access_tokens_actions.rb
+++ b/app/controllers/concerns/access_tokens_actions.rb
@@ -13,6 +13,13 @@ module AccessTokensActions
def index
@resource_access_token = PersonalAccessToken.new
set_index_vars
+
+ respond_to do |format|
+ format.html
+ format.json do
+ render json: @active_access_tokens
+ end
+ end
end
# rubocop:enable Gitlab/ModuleWithInstanceVariables
@@ -23,7 +30,7 @@ module AccessTokensActions
if token_response.success?
@resource_access_token = token_response.payload[:access_token]
render json: { new_token: @resource_access_token.token,
- active_access_tokens: active_resource_access_tokens }, status: :ok
+ active_access_tokens: active_access_tokens }, status: :ok
else
render json: { errors: token_response.errors }, status: :unprocessable_entity
end
@@ -62,15 +69,10 @@ module AccessTokensActions
resource.members.load
@scopes = Gitlab::Auth.resource_bot_scopes
- @active_resource_access_tokens = active_resource_access_tokens
+ @active_access_tokens = active_access_tokens
end
# rubocop:enable Gitlab/ModuleWithInstanceVariables
- def active_resource_access_tokens
- tokens = finder(state: 'active', sort: 'expires_at_asc_id_desc').execute.preload_users
- represent(tokens)
- end
-
def finder(options = {})
PersonalAccessTokensFinder.new({ user: bot_users, impersonation: false }.merge(options))
end
diff --git a/app/controllers/concerns/authenticates_with_two_factor.rb b/app/controllers/concerns/authenticates_with_two_factor.rb
index fbaa754124c..817f82085e6 100644
--- a/app/controllers/concerns/authenticates_with_two_factor.rb
+++ b/app/controllers/concerns/authenticates_with_two_factor.rb
@@ -137,7 +137,7 @@ module AuthenticatesWithTwoFactor
session[:credentialRequestOptions] = get_options
session[:challenge] = get_options.challenge
- gon.push(webauthn: { options: get_options.to_json })
+ gon.push(webauthn: { options: Gitlab::Json.dump(get_options) })
end
end
# rubocop: enable CodeReuse/ActiveRecord
diff --git a/app/controllers/concerns/integrations/params.rb b/app/controllers/concerns/integrations/params.rb
index c3ad9d3dff3..30de4a86bec 100644
--- a/app/controllers/concerns/integrations/params.rb
+++ b/app/controllers/concerns/integrations/params.rb
@@ -88,6 +88,10 @@ module Integrations
param_values = return_value[:integration]
if param_values.is_a?(ActionController::Parameters)
+ if action_name == 'update' && integration.chat? && param_values['webhook'] == BaseChatNotification::SECRET_MASK
+ param_values.delete('webhook')
+ end
+
integration.secret_fields.each do |param|
param_values.delete(param) if param_values[param].blank?
end
diff --git a/app/controllers/concerns/issuable_actions.rb b/app/controllers/concerns/issuable_actions.rb
index 7c3401a7e90..bea184e44b9 100644
--- a/app/controllers/concerns/issuable_actions.rb
+++ b/app/controllers/concerns/issuable_actions.rb
@@ -142,43 +142,21 @@ module IssuableActions
end
end
- # rubocop:disable CodeReuse/ActiveRecord
def discussions
- notes = NotesFinder.new(current_user, finder_params_for_issuable).execute
- .inc_relations_for_view
- .includes(:noteable)
- .fresh
+ finder = Issuable::DiscussionsListService.new(current_user, issuable, finder_params_for_issuable)
+ discussion_notes = finder.execute
- if paginated_discussions
- paginated_discussions_by_type = paginated_discussions.records.group_by(&:table_name)
+ response.headers['X-Next-Page-Cursor'] = finder.paginator.cursor_for_next_page if finder.paginator.present? && finder.paginator.has_next_page?
- notes = if paginated_discussions_by_type['notes'].present?
- notes.with_discussion_ids(paginated_discussions_by_type['notes'].map(&:discussion_id))
- else
- notes.none
- end
-
- response.headers['X-Next-Page-Cursor'] = paginated_discussions.cursor_for_next_page if paginated_discussions.has_next_page?
- end
-
- if notes_filter != UserPreference::NOTES_FILTERS[:only_comments]
- notes = ResourceEvents::MergeIntoNotesService.new(issuable, current_user, paginated_notes: paginated_discussions_by_type).execute(notes)
- end
-
- notes = prepare_notes_for_rendering(notes)
- notes = notes.select { |n| n.readable_by?(current_user) }
-
- discussions = Discussion.build_collection(notes, issuable)
-
- if issuable.is_a?(MergeRequest)
- render_mr_discussions(discussions, discussion_serializer, discussion_cache_context)
- elsif issuable.is_a?(Issue)
- render json: discussion_serializer.represent(discussions, context: self) if stale?(etag: [discussion_cache_context, discussions])
+ case issuable
+ when MergeRequest
+ render_mr_discussions(discussion_notes, discussion_serializer, discussion_cache_context)
+ when Issue
+ render json: discussion_serializer.represent(discussion_notes, context: self) if stale?(etag: [discussion_cache_context, discussion_notes])
else
- render json: discussion_serializer.represent(discussions, context: self)
+ render json: discussion_serializer.represent(discussion_notes, context: self)
end
end
- # rubocop:enable CodeReuse/ActiveRecord
private
@@ -199,17 +177,6 @@ module IssuableActions
context: self)
end
- def paginated_discussions
- return if params[:per_page].blank?
- return if issuable.instance_of?(MergeRequest) && Feature.disabled?(:paginated_mr_discussions, project)
-
- strong_memoize(:paginated_discussions) do
- issuable
- .discussion_root_note_ids(notes_filter: notes_filter)
- .keyset_paginate(cursor: params[:cursor], per_page: params[:per_page].to_i)
- end
- end
-
def notes_filter
strong_memoize(:notes_filter) do
notes_filter_param = params[:notes_filter]&.to_i
@@ -325,9 +292,10 @@ module IssuableActions
# rubocop:disable Gitlab/ModuleWithInstanceVariables
def finder_params_for_issuable
{
- target: @issuable,
- notes_filter: notes_filter
- }.tap { |new_params| new_params[:project] = project if respond_to?(:project, true) }
+ notes_filter: notes_filter,
+ cursor: params[:cursor],
+ per_page: params[:per_page]
+ }
end
# rubocop:enable Gitlab/ModuleWithInstanceVariables
end
diff --git a/app/controllers/concerns/issuable_collections_action.rb b/app/controllers/concerns/issuable_collections_action.rb
index e03d1de7bf9..7beb86b51fd 100644
--- a/app/controllers/concerns/issuable_collections_action.rb
+++ b/app/controllers/concerns/issuable_collections_action.rb
@@ -60,7 +60,6 @@ module IssuableCollectionsAction
def finder_options
issue_types = Issue::TYPES_FOR_LIST
- issue_types = issue_types.excluding('task') unless Feature.enabled?(:work_items)
super.merge(
non_archived: true,
diff --git a/app/controllers/concerns/preferred_language_switcher.rb b/app/controllers/concerns/preferred_language_switcher.rb
new file mode 100644
index 00000000000..9711e57cf7a
--- /dev/null
+++ b/app/controllers/concerns/preferred_language_switcher.rb
@@ -0,0 +1,18 @@
+# frozen_string_literal: true
+
+module PreferredLanguageSwitcher
+ extend ActiveSupport::Concern
+
+ private
+
+ def init_preferred_language
+ return unless Feature.enabled?(:preferred_language_switcher)
+
+ cookies[:preferred_language] = preferred_language
+ end
+
+ def preferred_language
+ cookies[:preferred_language].presence_in(Gitlab::I18n.available_locales) ||
+ Gitlab::CurrentSettings.default_preferred_language
+ end
+end
diff --git a/app/controllers/concerns/preview_markdown.rb b/app/controllers/concerns/preview_markdown.rb
index 79b3fa28660..7af114313a1 100644
--- a/app/controllers/concerns/preview_markdown.rb
+++ b/app/controllers/concerns/preview_markdown.rb
@@ -41,7 +41,7 @@ module PreviewMarkdown
case controller_name
when 'wikis' then { pipeline: :wiki, wiki: wiki, page_slug: params[:id] }
when 'snippets' then { skip_project_check: true }
- when 'groups' then { group: group }
+ when 'groups' then { group: group, issuable_reference_expansion_enabled: true }
when 'projects' then projects_filter_params
when 'timeline_events' then timeline_events_filter_params
else {}
diff --git a/app/controllers/concerns/product_analytics_tracking.rb b/app/controllers/concerns/product_analytics_tracking.rb
index 4f96cc5c895..dfa159ccfd7 100644
--- a/app/controllers/concerns/product_analytics_tracking.rb
+++ b/app/controllers/concerns/product_analytics_tracking.rb
@@ -6,6 +6,8 @@ module ProductAnalyticsTracking
extend ActiveSupport::Concern
class_methods do
+ # TODO: Remove once all the events are migrated to #track_custom_event
+ # during https://gitlab.com/groups/gitlab-org/-/epics/8641
def track_event(*controller_actions, name:, conditions: nil, destinations: [:redis_hll], &block)
custom_conditions = [:trackable_html_request?, *conditions]
diff --git a/app/controllers/concerns/render_access_tokens.rb b/app/controllers/concerns/render_access_tokens.rb
new file mode 100644
index 00000000000..b0bbad7e37f
--- /dev/null
+++ b/app/controllers/concerns/render_access_tokens.rb
@@ -0,0 +1,31 @@
+# frozen_string_literal: true
+module RenderAccessTokens
+ extend ActiveSupport::Concern
+
+ def active_access_tokens
+ tokens = finder(state: 'active', sort: 'expires_at_asc_id_desc').execute.preload_users
+
+ if Feature.enabled?('access_token_pagination')
+ tokens = tokens.page(page)
+ add_pagination_headers(tokens)
+ end
+
+ represent(tokens)
+ end
+
+ def add_pagination_headers(relation)
+ Gitlab::Pagination::OffsetHeaderBuilder.new(
+ request_context: self,
+ per_page: relation.limit_value,
+ page: relation.current_page,
+ next_page: relation.next_page,
+ prev_page: relation.prev_page,
+ total: relation.total_count,
+ params: params.permit(:page, :per_page)
+ ).execute
+ end
+
+ def page
+ (params[:page] || 1).to_i
+ end
+end
diff --git a/app/controllers/concerns/send_file_upload.rb b/app/controllers/concerns/send_file_upload.rb
index c8369c465b8..c91edb74d6b 100644
--- a/app/controllers/concerns/send_file_upload.rb
+++ b/app/controllers/concerns/send_file_upload.rb
@@ -30,7 +30,17 @@ module SendFileUpload
headers.store(*Gitlab::Workhorse.send_url(file_upload.url(**redirect_params)))
head :ok
else
- redirect_to file_upload.url(**redirect_params)
+ redirect_to cdn_fronted_url(file_upload, redirect_params)
+ end
+ end
+
+ def cdn_fronted_url(file, redirect_params)
+ if file.respond_to?(:cdn_enabled_url)
+ result = file.cdn_enabled_url(request.remote_ip, redirect_params[:query])
+ Gitlab::ApplicationContext.push(artifact_used_cdn: result.used_cdn)
+ result.url
+ else
+ file.url(**redirect_params)
end
end
diff --git a/app/controllers/concerns/verifies_with_email.rb b/app/controllers/concerns/verifies_with_email.rb
index 782cae53c3f..ac1475597ff 100644
--- a/app/controllers/concerns/verifies_with_email.rb
+++ b/app/controllers/concerns/verifies_with_email.rb
@@ -8,7 +8,7 @@ module VerifiesWithEmail
include ActionView::Helpers::DateHelper
included do
- prepend_before_action :verify_with_email, only: :create, unless: -> { two_factor_enabled? }
+ prepend_before_action :verify_with_email, only: :create, unless: -> { skip_verify_with_email? }
skip_before_action :required_signup_info, only: :successful_verification
end
@@ -55,6 +55,10 @@ module VerifiesWithEmail
private
+ def skip_verify_with_email?
+ two_factor_enabled? || Gitlab::Qa.request?(request.user_agent)
+ end
+
def find_verification_user
return unless session[:verification_user_id]
@@ -84,10 +88,7 @@ module VerifiesWithEmail
def send_verification_instructions_email(user, token)
return unless user.can?(:receive_notifications)
- Notify.verification_instructions_email(
- user.id,
- token: token,
- expires_in: Users::EmailVerification::ValidateTokenService::TOKEN_VALID_FOR_MINUTES).deliver_later
+ Notify.verification_instructions_email(user.email, token: token).deliver_later
log_verification(user, :instructions_sent)
end
diff --git a/app/controllers/concerns/web_hooks/hook_actions.rb b/app/controllers/concerns/web_hooks/hook_actions.rb
index ea11f13c7ef..75065ef9d24 100644
--- a/app/controllers/concerns/web_hooks/hook_actions.rb
+++ b/app/controllers/concerns/web_hooks/hook_actions.rb
@@ -20,7 +20,7 @@ module WebHooks
unless hook.valid?
self.hooks = relation.select(&:persisted?)
- flash[:alert] = hook.errors.full_messages.join.html_safe
+ flash[:alert] = hook.errors.full_messages.to_sentence.html_safe
end
redirect_to action: :index
@@ -53,6 +53,8 @@ module WebHooks
ps = params.require(:hook).permit(*permitted).to_h
+ ps.delete(:token) if action_name == 'update' && ps[:token] == WebHook::SECRET_MASK
+
ps[:url_variables] = ps[:url_variables].to_h { [_1[:key], _1[:value].presence] } if ps.key?(:url_variables)
if action_name == 'update' && ps.key?(:url_variables)
@@ -64,7 +66,9 @@ module WebHooks
end
def hook_param_names
- %i[enable_ssl_verification token url push_events_branch_filter]
+ param_names = %i[enable_ssl_verification token url push_events_branch_filter]
+ param_names.push(:branch_filter_strategy) if Feature.enabled?(:enhanced_webhook_support_regex)
+ param_names
end
def destroy_hook(hook)
diff --git a/app/controllers/concerns/web_hooks/hook_execution_notice.rb b/app/controllers/concerns/web_hooks/hook_execution_notice.rb
index d651313b30d..69b140723e3 100644
--- a/app/controllers/concerns/web_hooks/hook_execution_notice.rb
+++ b/app/controllers/concerns/web_hooks/hook_execution_notice.rb
@@ -5,7 +5,7 @@ module WebHooks
private
def set_hook_execution_notice(result)
- http_status = result[:http_status]
+ http_status = result.payload[:http_status]
message = result[:message]
if http_status && http_status >= 200 && http_status < 400
diff --git a/app/controllers/confirmations_controller.rb b/app/controllers/confirmations_controller.rb
index 713231cbc6f..6dd4d72bbc7 100644
--- a/app/controllers/confirmations_controller.rb
+++ b/app/controllers/confirmations_controller.rb
@@ -6,6 +6,7 @@ class ConfirmationsController < Devise::ConfirmationsController
include OneTrustCSP
include GoogleAnalyticsCSP
+ skip_before_action :required_signup_info
prepend_before_action :check_recaptcha, only: :create
before_action :load_recaptcha, only: :new
diff --git a/app/controllers/dashboard/projects_controller.rb b/app/controllers/dashboard/projects_controller.rb
index 0e4592259d8..89d362c88a4 100644
--- a/app/controllers/dashboard/projects_controller.rb
+++ b/app/controllers/dashboard/projects_controller.rb
@@ -66,11 +66,10 @@ class Dashboard::ProjectsController < Dashboard::ApplicationController
end
def load_projects(finder_params)
- @total_user_projects_count = ProjectsFinder.new(params: { non_public: true, without_deleted: true, not_aimed_for_deletion: true }, current_user: current_user).execute
- @total_starred_projects_count = ProjectsFinder.new(params: { starred: true, without_deleted: true, not_aimed_for_deletion: true }, current_user: current_user).execute
+ @total_user_projects_count = ProjectsFinder.new(params: { non_public: true, not_aimed_for_deletion: true }, current_user: current_user).execute
+ @total_starred_projects_count = ProjectsFinder.new(params: { starred: true, not_aimed_for_deletion: true }, current_user: current_user).execute
finder_params[:use_cte] = true if use_cte_for_finder?
- finder_params[:without_deleted] = true
projects = ProjectsFinder.new(params: finder_params, current_user: current_user).execute
@@ -93,7 +92,7 @@ class Dashboard::ProjectsController < Dashboard::ApplicationController
def load_events
projects = ProjectsFinder
- .new(params: params.merge(non_public: true, without_deleted: true), current_user: current_user)
+ .new(params: params.merge(non_public: true, not_aimed_for_deletion: true), current_user: current_user)
.execute
@events = EventCollection
diff --git a/app/controllers/explore/groups_controller.rb b/app/controllers/explore/groups_controller.rb
index 97791b43d41..ac355b861b3 100644
--- a/app/controllers/explore/groups_controller.rb
+++ b/app/controllers/explore/groups_controller.rb
@@ -7,6 +7,8 @@ class Explore::GroupsController < Explore::ApplicationController
urgency :low
def index
- render_group_tree GroupsFinder.new(current_user).execute
+ user = Feature.enabled?(:generic_explore_groups, current_user, type: :experiment) ? nil : current_user
+
+ render_group_tree GroupsFinder.new(user).execute
end
end
diff --git a/app/controllers/graphql_controller.rb b/app/controllers/graphql_controller.rb
index 67eeb43d5a2..5ffd525c170 100644
--- a/app/controllers/graphql_controller.rb
+++ b/app/controllers/graphql_controller.rb
@@ -190,7 +190,8 @@ class GraphqlController < ApplicationController
current_user: current_user,
is_sessionless_user: api_user,
request: request,
- scope_validator: ::Gitlab::Auth::ScopeValidator.new(api_user, request_authenticator)
+ scope_validator: ::Gitlab::Auth::ScopeValidator.new(api_user, request_authenticator),
+ remove_deprecated: Gitlab::Utils.to_boolean(params[:remove_deprecated], default: false)
}
end
diff --git a/app/controllers/groups/boards_controller.rb b/app/controllers/groups/boards_controller.rb
index 14b70df0feb..e1ba86220c7 100644
--- a/app/controllers/groups/boards_controller.rb
+++ b/app/controllers/groups/boards_controller.rb
@@ -7,7 +7,7 @@ class Groups::BoardsController < Groups::ApplicationController
before_action do
push_frontend_feature_flag(:board_multi_select, group)
- push_frontend_feature_flag(:realtime_labels, group)
+ push_frontend_feature_flag(:apollo_boards, group)
experiment(:prominent_create_board_btn, subject: current_user) do |e|
e.control {}
e.candidate {}
diff --git a/app/controllers/groups/dependency_proxy/application_controller.rb b/app/controllers/groups/dependency_proxy/application_controller.rb
index f7337a3cdb1..300a82eed78 100644
--- a/app/controllers/groups/dependency_proxy/application_controller.rb
+++ b/app/controllers/groups/dependency_proxy/application_controller.rb
@@ -21,10 +21,11 @@ module Groups
user_or_deploy_token = ::DependencyProxy::AuthTokenService.user_or_deploy_token_from_jwt(token)
- if user_or_deploy_token.is_a?(User)
+ case user_or_deploy_token
+ when User
@authentication_result = Gitlab::Auth::Result.new(user_or_deploy_token, nil, :user, [])
sign_in(user_or_deploy_token)
- elsif user_or_deploy_token.is_a?(DeployToken)
+ when DeployToken
@authentication_result = Gitlab::Auth::Result.new(user_or_deploy_token, nil, :deploy_token, [])
end
end
diff --git a/app/controllers/groups/observability_controller.rb b/app/controllers/groups/observability_controller.rb
index 5b6503494c4..4b1f2b582ce 100644
--- a/app/controllers/groups/observability_controller.rb
+++ b/app/controllers/groups/observability_controller.rb
@@ -9,35 +9,41 @@ module Groups
default_frame_src = p.directives['frame-src'] || p.directives['default-src']
# When ObservabilityUI is not authenticated, it needs to be able to redirect to the GL sign-in page, hence 'self'
- frame_src_values = Array.wrap(default_frame_src) | [ObservabilityController.observability_url, "'self'"]
+ frame_src_values = Array.wrap(default_frame_src) | [observability_url, "'self'"]
p.frame_src(*frame_src_values)
end
- before_action :check_observability_allowed, only: :index
+ before_action :check_observability_allowed
- def index
- # Format: https://observe.gitlab.com/-/GROUP_ID
- @observability_iframe_src = "#{ObservabilityController.observability_url}/-/#{@group.id}"
+ def dashboards
+ render_observability
+ end
- # Uncomment below for testing with local GDK
- # @observability_iframe_src = "#{ObservabilityController.observability_url}/9970?groupId=14485840"
+ def manage
+ render_observability
+ end
- render layout: 'group', locals: { base_layout: 'layouts/fullscreen' }
+ def explore
+ render_observability
end
private
+ def render_observability
+ render 'observability', layout: 'group', locals: { base_layout: 'layouts/fullscreen' }
+ end
+
def self.observability_url
- return ENV['OVERRIDE_OBSERVABILITY_URL'] if ENV['OVERRIDE_OBSERVABILITY_URL']
- # TODO Make observability URL configurable https://gitlab.com/gitlab-org/opstrace/opstrace-ui/-/issues/80
- return "https://staging.observe.gitlab.com" if Gitlab.staging?
+ Gitlab::Observability.observability_url
+ end
- "https://observe.gitlab.com"
+ def observability_url
+ self.class.observability_url
end
def check_observability_allowed
- return render_404 unless self.class.observability_url.present?
+ return render_404 unless observability_url.present?
render_404 unless can?(current_user, :read_observability, @group)
end
diff --git a/app/controllers/groups/registry/repositories_controller.rb b/app/controllers/groups/registry/repositories_controller.rb
index bb2d08e487a..cb7bf001918 100644
--- a/app/controllers/groups/registry/repositories_controller.rb
+++ b/app/controllers/groups/registry/repositories_controller.rb
@@ -8,10 +8,6 @@ module Groups
before_action :verify_container_registry_enabled!
before_action :authorize_read_container_image!
- before_action do
- push_frontend_feature_flag(:container_registry_show_shortened_path, group)
- end
-
feature_category :container_registry
urgency :low
diff --git a/app/controllers/groups/settings/access_tokens_controller.rb b/app/controllers/groups/settings/access_tokens_controller.rb
index f01b2b779e3..d86ddcfe2d0 100644
--- a/app/controllers/groups/settings/access_tokens_controller.rb
+++ b/app/controllers/groups/settings/access_tokens_controller.rb
@@ -3,6 +3,7 @@
module Groups
module Settings
class AccessTokensController < Groups::ApplicationController
+ include RenderAccessTokens
include AccessTokensActions
layout 'group_settings'
diff --git a/app/controllers/groups/settings/ci_cd_controller.rb b/app/controllers/groups/settings/ci_cd_controller.rb
index e164a834519..b1afac1f1c7 100644
--- a/app/controllers/groups/settings/ci_cd_controller.rb
+++ b/app/controllers/groups/settings/ci_cd_controller.rb
@@ -10,9 +10,6 @@ module Groups
before_action :define_variables, only: [:show]
before_action :push_licensed_features, only: [:show]
before_action :assign_variables_to_gon, only: [:show]
- before_action do
- push_frontend_feature_flag(:ci_variable_settings_graphql, @group)
- end
feature_category :continuous_integration
urgency :low
diff --git a/app/controllers/groups/settings/packages_and_registries_controller.rb b/app/controllers/groups/settings/packages_and_registries_controller.rb
index 411b8577c3f..ec4a0b312ee 100644
--- a/app/controllers/groups/settings/packages_and_registries_controller.rb
+++ b/app/controllers/groups/settings/packages_and_registries_controller.rb
@@ -7,6 +7,10 @@ module Groups
before_action :authorize_admin_group!
before_action :verify_packages_enabled!
+ before_action do
+ push_frontend_feature_flag(:maven_central_request_forwarding, group)
+ end
+
feature_category :package_registry
urgency :low
diff --git a/app/controllers/groups/settings/repository_controller.rb b/app/controllers/groups/settings/repository_controller.rb
index cb62ea2a543..ecd5d814fb6 100644
--- a/app/controllers/groups/settings/repository_controller.rb
+++ b/app/controllers/groups/settings/repository_controller.rb
@@ -8,9 +8,6 @@ module Groups
before_action :authorize_create_deploy_token!, only: :create_deploy_token
before_action :authorize_access!, only: :show
before_action :define_deploy_token_variables, if: -> { can?(current_user, :create_deploy_token, @group) }
- before_action do
- push_frontend_feature_flag(:ajax_new_deploy_token, @group)
- end
feature_category :continuous_delivery
urgency :low
diff --git a/app/controllers/groups_controller.rb b/app/controllers/groups_controller.rb
index 269342a6c22..3f516c24a69 100644
--- a/app/controllers/groups_controller.rb
+++ b/app/controllers/groups_controller.rb
@@ -35,6 +35,7 @@ class GroupsController < Groups::ApplicationController
before_action :track_experiment_event, only: [:new]
before_action only: :issues do
+ push_frontend_feature_flag(:or_issuable_queries, group)
push_force_frontend_feature_flag(:work_items, group.work_items_feature_flag_enabled?)
end
@@ -111,7 +112,7 @@ class GroupsController < Groups::ApplicationController
def details
respond_to do |format|
format.html do
- render_details_html
+ redirect_to group_path(group)
end
format.atom do
@@ -235,10 +236,6 @@ class GroupsController < Groups::ApplicationController
render 'groups/show', locals: { trial: params[:trial] }
end
- def render_details_html
- render 'groups/show'
- end
-
def render_details_view_atom
load_events
render layout: 'xml', template: 'groups/show'
diff --git a/app/controllers/jira_connect/application_controller.rb b/app/controllers/jira_connect/application_controller.rb
index e26d69314cd..b9f0ea795e1 100644
--- a/app/controllers/jira_connect/application_controller.rb
+++ b/app/controllers/jira_connect/application_controller.rb
@@ -3,6 +3,11 @@
class JiraConnect::ApplicationController < ApplicationController
include Gitlab::Utils::StrongMemoize
+ CORS_ALLOWED_METHODS = {
+ '/-/jira_connect/oauth_application_id' => %i[GET OPTIONS],
+ '/-/jira_connect/subscriptions/*' => %i[DELETE OPTIONS]
+ }.freeze
+
skip_before_action :authenticate_user!
skip_before_action :verify_authenticity_token
before_action :verify_atlassian_jwt!
@@ -60,4 +65,25 @@ class JiraConnect::ApplicationController < ApplicationController
def auth_token
params[:jwt] || request.headers['Authorization']&.split(' ', 2)&.last
end
+
+ def cors_allowed_methods
+ CORS_ALLOWED_METHODS[resource]
+ end
+
+ def resource
+ request.path.gsub(%r{/\d+$}, '/*')
+ end
+
+ def set_cors_headers
+ return unless allow_cors_request?
+
+ response.set_header('Access-Control-Allow-Origin', Gitlab::CurrentSettings.jira_connect_proxy_url)
+ response.set_header('Access-Control-Allow-Methods', cors_allowed_methods.join(', '))
+ end
+
+ def allow_cors_request?
+ return false if cors_allowed_methods.nil?
+
+ !Gitlab.com? && Gitlab::CurrentSettings.jira_connect_proxy_url.present?
+ end
end
diff --git a/app/controllers/jira_connect/cors_preflight_checks_controller.rb b/app/controllers/jira_connect/cors_preflight_checks_controller.rb
new file mode 100644
index 00000000000..3f30c1e04df
--- /dev/null
+++ b/app/controllers/jira_connect/cors_preflight_checks_controller.rb
@@ -0,0 +1,16 @@
+# frozen_string_literal: true
+
+module JiraConnect
+ class CorsPreflightChecksController < ApplicationController
+ feature_category :integrations
+
+ skip_before_action :verify_atlassian_jwt!
+ before_action :set_cors_headers
+
+ def index
+ return render_404 unless allow_cors_request?
+
+ render plain: '', content_type: 'text/plain'
+ end
+ end
+end
diff --git a/app/controllers/jira_connect/oauth_application_ids_controller.rb b/app/controllers/jira_connect/oauth_application_ids_controller.rb
index a84b47f4c8b..3e788e2282e 100644
--- a/app/controllers/jira_connect/oauth_application_ids_controller.rb
+++ b/app/controllers/jira_connect/oauth_application_ids_controller.rb
@@ -1,11 +1,11 @@
# frozen_string_literal: true
module JiraConnect
- class OauthApplicationIdsController < ::ApplicationController
+ class OauthApplicationIdsController < ApplicationController
feature_category :integrations
- skip_before_action :authenticate_user!
- skip_before_action :verify_authenticity_token
+ skip_before_action :verify_atlassian_jwt!
+ before_action :set_cors_headers
def show
if show_application_id?
diff --git a/app/controllers/jira_connect/subscriptions_controller.rb b/app/controllers/jira_connect/subscriptions_controller.rb
index 9305f46c39e..9a732cadd94 100644
--- a/app/controllers/jira_connect/subscriptions_controller.rb
+++ b/app/controllers/jira_connect/subscriptions_controller.rb
@@ -27,6 +27,7 @@ class JiraConnect::SubscriptionsController < JiraConnect::ApplicationController
before_action :verify_qsh_claim!, only: :index
before_action :allow_self_managed_content_security_policy, only: :index
before_action :authenticate_user!, only: :create
+ before_action :set_cors_headers
def index
@subscriptions = current_jira_installation.subscriptions.preload_namespace_route
@@ -64,7 +65,7 @@ class JiraConnect::SubscriptionsController < JiraConnect::ApplicationController
private
def allow_self_managed_content_security_policy
- return unless Feature.enabled?(:jira_connect_oauth_self_managed)
+ return unless Feature.enabled?(:jira_connect_oauth_self_managed_setting)
return unless current_jira_installation.instance_url?
@@ -83,7 +84,8 @@ class JiraConnect::SubscriptionsController < JiraConnect::ApplicationController
def allowed_instance_connect_src
[
Gitlab::Utils.append_path(current_jira_installation.instance_url, '/-/jira_connect/'),
- Gitlab::Utils.append_path(current_jira_installation.instance_url, '/api/')
+ Gitlab::Utils.append_path(current_jira_installation.instance_url, '/api/'),
+ Gitlab::Utils.append_path(current_jira_installation.instance_url, '/oauth/token')
]
end
end
diff --git a/app/controllers/oauth/authorizations_controller.rb b/app/controllers/oauth/authorizations_controller.rb
index bf8b61db2e5..43bf895ea76 100644
--- a/app/controllers/oauth/authorizations_controller.rb
+++ b/app/controllers/oauth/authorizations_controller.rb
@@ -4,7 +4,7 @@ class Oauth::AuthorizationsController < Doorkeeper::AuthorizationsController
include InitializesCurrentUserMode
include Gitlab::Utils::StrongMemoize
- before_action :verify_confirmed_email!
+ before_action :verify_confirmed_email!, :verify_admin_allowed!
layout 'profile'
@@ -97,4 +97,19 @@ class Oauth::AuthorizationsController < Doorkeeper::AuthorizationsController
pre_auth.error = :unconfirmed_email
render "doorkeeper/authorizations/error"
end
+
+ def verify_admin_allowed!
+ render "doorkeeper/authorizations/forbidden" if disallow_connect?
+ end
+
+ def disallow_connect?
+ # we're disabling Cop/UserAdmin as OAuth tokens don't seem to respect admin mode
+ current_user&.admin? && Gitlab::CurrentSettings.disable_admin_oauth_scopes && dangerous_scopes? # rubocop:disable Cop/UserAdmin
+ end
+
+ def dangerous_scopes?
+ doorkeeper_application&.includes_scope?(*::Gitlab::Auth::API_SCOPE, *::Gitlab::Auth::READ_API_SCOPE,
+ *::Gitlab::Auth::ADMIN_SCOPES, *::Gitlab::Auth::REPOSITORY_SCOPES,
+ *::Gitlab::Auth::REGISTRY_SCOPES) && !doorkeeper_application&.trusted?
+ end
end
diff --git a/app/controllers/passwords_controller.rb b/app/controllers/passwords_controller.rb
index ead5d7c9026..1216353be36 100644
--- a/app/controllers/passwords_controller.rb
+++ b/app/controllers/passwords_controller.rb
@@ -2,6 +2,7 @@
class PasswordsController < Devise::PasswordsController
include GitlabRecaptcha
+ include Gitlab::Tracking::Helpers::WeakPasswordErrorEvent
skip_before_action :require_no_authentication, only: [:edit, :update]
@@ -41,6 +42,8 @@ class PasswordsController < Devise::PasswordsController
resource.password_automatically_set = false
resource.password_expires_at = nil
resource.save(validate: false) if resource.changed?
+ else
+ track_weak_password_error(@user, self.class.name, 'create')
end
end
end
diff --git a/app/controllers/profiles/passwords_controller.rb b/app/controllers/profiles/passwords_controller.rb
index 5eb0f80ddc9..738c41207d5 100644
--- a/app/controllers/profiles/passwords_controller.rb
+++ b/app/controllers/profiles/passwords_controller.rb
@@ -1,6 +1,8 @@
# frozen_string_literal: true
class Profiles::PasswordsController < Profiles::ApplicationController
+ include Gitlab::Tracking::Helpers::WeakPasswordErrorEvent
+
skip_before_action :check_password_expiration, only: [:new, :create]
skip_before_action :check_two_factor_requirement, only: [:new, :create]
@@ -27,6 +29,7 @@ class Profiles::PasswordsController < Profiles::ApplicationController
redirect_to root_path, notice: _('Password successfully changed')
else
+ track_weak_password_error(@user, self.class.name, 'create')
render :new
end
end
@@ -48,6 +51,7 @@ class Profiles::PasswordsController < Profiles::ApplicationController
flash[:notice] = _('Password was successfully updated. Please sign in again.')
redirect_to new_user_session_path
else
+ track_weak_password_error(@user, self.class.name, 'update')
@user.reset
render 'edit'
end
@@ -94,3 +98,5 @@ class Profiles::PasswordsController < Profiles::ApplicationController
}
end
end
+
+Profiles::PasswordsController.prepend_mod
diff --git a/app/controllers/profiles/personal_access_tokens_controller.rb b/app/controllers/profiles/personal_access_tokens_controller.rb
index 4cf26d3e1e2..1663aa61f62 100644
--- a/app/controllers/profiles/personal_access_tokens_controller.rb
+++ b/app/controllers/profiles/personal_access_tokens_controller.rb
@@ -1,6 +1,8 @@
# frozen_string_literal: true
class Profiles::PersonalAccessTokensController < Profiles::ApplicationController
+ include RenderAccessTokens
+
feature_category :authentication_and_authorization
before_action :check_personal_access_tokens_enabled
@@ -16,7 +18,7 @@ class Profiles::PersonalAccessTokensController < Profiles::ApplicationController
respond_to do |format|
format.html
format.json do
- render json: @active_personal_access_tokens
+ render json: @active_access_tokens
end
end
end
@@ -30,7 +32,7 @@ class Profiles::PersonalAccessTokensController < Profiles::ApplicationController
if result.success?
render json: { new_token: @personal_access_token.token,
- active_access_tokens: active_personal_access_tokens }, status: :ok
+ active_access_tokens: active_access_tokens }, status: :ok
else
render json: { errors: result.errors }, status: :unprocessable_entity
end
@@ -56,36 +58,13 @@ class Profiles::PersonalAccessTokensController < Profiles::ApplicationController
def set_index_vars
@scopes = Gitlab::Auth.available_scopes_for(current_user)
- @active_personal_access_tokens = active_personal_access_tokens
+ @active_access_tokens = active_access_tokens
end
- def active_personal_access_tokens
- tokens = finder(state: 'active', sort: 'expires_at_asc_id_desc').execute
-
- if Feature.enabled?('access_token_pagination')
- tokens = tokens.page(page)
- add_pagination_headers(tokens)
- end
-
+ def represent(tokens)
::PersonalAccessTokenSerializer.new.represent(tokens)
end
- def add_pagination_headers(relation)
- Gitlab::Pagination::OffsetHeaderBuilder.new(
- request_context: self,
- per_page: relation.limit_value,
- page: relation.current_page,
- next_page: relation.next_page,
- prev_page: relation.prev_page,
- total: relation.total_count,
- params: params.permit(:page)
- ).execute
- end
-
- def page
- (params[:page] || 1).to_i
- end
-
def check_personal_access_tokens_enabled
render_404 if Gitlab::CurrentSettings.personal_access_tokens_disabled?
end
diff --git a/app/controllers/projects/alerting/notifications_controller.rb b/app/controllers/projects/alerting/notifications_controller.rb
index f3283c88740..89e8a261288 100644
--- a/app/controllers/projects/alerting/notifications_controller.rb
+++ b/app/controllers/projects/alerting/notifications_controller.rb
@@ -18,8 +18,9 @@ module Projects
def create
token = extract_alert_manager_token(request)
result = notify_service.execute(token, integration)
+ has_something_to_return = result.success? && result.http_status != :created
- if result.success?
+ if has_something_to_return
render json: AlertManagement::AlertSerializer.new.represent(result.payload[:alerts]), code: result.http_status
else
head result.http_status
diff --git a/app/controllers/projects/application_controller.rb b/app/controllers/projects/application_controller.rb
index 2256471047d..25b83aed78a 100644
--- a/app/controllers/projects/application_controller.rb
+++ b/app/controllers/projects/application_controller.rb
@@ -38,9 +38,9 @@ class Projects::ApplicationController < ApplicationController
if build.debug_mode?
access_denied!(
_('You must have developer or higher permissions in the associated project to view job logs when debug trace ' \
- "is enabled. To disable debug trace, set the 'CI_DEBUG_TRACE' variable to 'false' in your pipeline " \
- 'configuration or CI/CD settings. If you need to view this job log, a project maintainer or owner must add ' \
- 'you to the project with developer permissions or higher.')
+ "is enabled. To disable debug trace, set the 'CI_DEBUG_TRACE' and 'CI_DEBUG_SERVICES' variables to 'false' " \
+ 'in your pipeline configuration or CI/CD settings. If you must view this job log, a project maintainer ' \
+ 'or owner must add you to the project with developer permissions or higher.')
)
else
access_denied!(_('The current user is not authorized to access the job log.'))
diff --git a/app/controllers/projects/artifacts_controller.rb b/app/controllers/projects/artifacts_controller.rb
index 40e89a06b46..c3dcde38d09 100644
--- a/app/controllers/projects/artifacts_controller.rb
+++ b/app/controllers/projects/artifacts_controller.rb
@@ -4,6 +4,7 @@ class Projects::ArtifactsController < Projects::ApplicationController
include ExtractsPath
include RendersBlob
include SendFileUpload
+ include Gitlab::Ci::Artifacts::Logger
urgency :low, [:browse, :file, :latest_succeeded]
@@ -26,12 +27,6 @@ class Projects::ArtifactsController < Projects::ApplicationController
# It should be removed only after resolving the underlying performance
# issues: https://gitlab.com/gitlab-org/gitlab/issues/32281
return head :no_content unless Feature.enabled?(:artifacts_management_page, @project)
-
- finder = Ci::JobArtifactsFinder.new(@project, artifacts_params)
- all_artifacts = finder.execute
-
- @artifacts = all_artifacts.page(params[:page]).per(MAX_PER_PAGE)
- @total_size = all_artifacts.total_size
end
def destroy
@@ -47,6 +42,7 @@ class Projects::ArtifactsController < Projects::ApplicationController
def download
return render_404 unless artifacts_file
+ log_artifacts_filesize(artifacts_file.model)
send_upload(artifacts_file, attachment: artifacts_file.filename, proxy: params[:proxy])
end
diff --git a/app/controllers/projects/boards_controller.rb b/app/controllers/projects/boards_controller.rb
index 6a6701ead15..84872d1e978 100644
--- a/app/controllers/projects/boards_controller.rb
+++ b/app/controllers/projects/boards_controller.rb
@@ -7,7 +7,7 @@ class Projects::BoardsController < Projects::ApplicationController
before_action :check_issues_available!
before_action do
push_frontend_feature_flag(:board_multi_select, project)
- push_frontend_feature_flag(:realtime_labels, project&.group)
+ push_frontend_feature_flag(:apollo_boards, project)
experiment(:prominent_create_board_btn, subject: current_user) do |e|
e.control {}
e.candidate {}
diff --git a/app/controllers/projects/commit_controller.rb b/app/controllers/projects/commit_controller.rb
index 2b2764d2e34..870320a79d9 100644
--- a/app/controllers/projects/commit_controller.rb
+++ b/app/controllers/projects/commit_controller.rb
@@ -86,7 +86,7 @@ class Projects::CommitController < Projects::ApplicationController
respond_to do |format|
format.json do
- render json: @merge_requests.to_json
+ render json: Gitlab::Json.dump(@merge_requests)
end
end
end
diff --git a/app/controllers/projects/environments_controller.rb b/app/controllers/projects/environments_controller.rb
index 4f037cc843e..67f2f85ce65 100644
--- a/app/controllers/projects/environments_controller.rb
+++ b/app/controllers/projects/environments_controller.rb
@@ -183,7 +183,7 @@ class Projects::EnvironmentsController < Projects::ApplicationController
def metrics
respond_to do |format|
format.html do
- redirect_to project_metrics_dashboard_path(project, environment: environment )
+ redirect_to project_metrics_dashboard_path(project, environment: environment)
end
format.json do
# Currently, this acts as a hint to load the metrics details into the cache
diff --git a/app/controllers/projects/google_cloud/configuration_controller.rb b/app/controllers/projects/google_cloud/configuration_controller.rb
index 06a6674d578..e109ab95d39 100644
--- a/app/controllers/projects/google_cloud/configuration_controller.rb
+++ b/app/controllers/projects/google_cloud/configuration_controller.rb
@@ -15,7 +15,7 @@ module Projects
gcpRegions: gcp_regions,
revokeOauthUrl: revoke_oauth_url
}
- @js_data = js_data.to_json
+ @js_data = Gitlab::Json.dump(js_data)
track_event(:render_page)
end
diff --git a/app/controllers/projects/google_cloud/databases_controller.rb b/app/controllers/projects/google_cloud/databases_controller.rb
index 77ee830fd24..b511a85b0b8 100644
--- a/app/controllers/projects/google_cloud/databases_controller.rb
+++ b/app/controllers/projects/google_cloud/databases_controller.rb
@@ -17,7 +17,8 @@ module Projects
cloudsqlInstances: ::GoogleCloud::GetCloudsqlInstancesService.new(project).execute,
emptyIllustrationUrl: ActionController::Base.helpers.image_path('illustrations/pipelines_empty.svg')
}
- @js_data = js_data.to_json
+
+ @js_data = Gitlab::Json.dump(js_data)
track_event(:render_page)
end
@@ -27,7 +28,7 @@ module Projects
@title = title(product)
- @js_data = {
+ js_data = {
gcpProjects: gcp_projects,
refs: refs,
cancelPath: project_google_cloud_databases_path(project),
@@ -35,7 +36,9 @@ module Projects
formDescription: description(product),
databaseVersions: Projects::GoogleCloud::CloudsqlHelper::VERSIONS[product],
tiers: Projects::GoogleCloud::CloudsqlHelper::TIERS
- }.to_json
+ }
+
+ @js_data = Gitlab::Json.dump(js_data)
track_event(:render_form)
render template: 'projects/google_cloud/databases/cloudsql_form', formats: :html
diff --git a/app/controllers/projects/google_cloud/deployments_controller.rb b/app/controllers/projects/google_cloud/deployments_controller.rb
index f6cc8d5eafb..041486eb2fb 100644
--- a/app/controllers/projects/google_cloud/deployments_controller.rb
+++ b/app/controllers/projects/google_cloud/deployments_controller.rb
@@ -11,7 +11,7 @@ class Projects::GoogleCloud::DeploymentsController < Projects::GoogleCloud::Base
enableCloudRunUrl: project_google_cloud_deployments_cloud_run_path(project),
enableCloudStorageUrl: project_google_cloud_deployments_cloud_storage_path(project)
}
- @js_data = js_data.to_json
+ @js_data = Gitlab::Json.dump(js_data)
track_event(:render_page)
end
diff --git a/app/controllers/projects/google_cloud/gcp_regions_controller.rb b/app/controllers/projects/google_cloud/gcp_regions_controller.rb
index 2f0bc05030f..c51261721b2 100644
--- a/app/controllers/projects/google_cloud/gcp_regions_controller.rb
+++ b/app/controllers/projects/google_cloud/gcp_regions_controller.rb
@@ -14,7 +14,7 @@ class Projects::GoogleCloud::GcpRegionsController < Projects::GoogleCloud::BaseC
refs: refs,
cancelPath: project_google_cloud_configuration_path(project)
}
- @js_data = js_data.to_json
+ @js_data = Gitlab::Json.dump(js_data)
track_event(:render_form)
end
diff --git a/app/controllers/projects/google_cloud/service_accounts_controller.rb b/app/controllers/projects/google_cloud/service_accounts_controller.rb
index 89d624764df..7b029e25ea2 100644
--- a/app/controllers/projects/google_cloud/service_accounts_controller.rb
+++ b/app/controllers/projects/google_cloud/service_accounts_controller.rb
@@ -14,7 +14,7 @@ class Projects::GoogleCloud::ServiceAccountsController < Projects::GoogleCloud::
refs: refs,
cancelPath: project_google_cloud_configuration_path(project)
}
- @js_data = js_data.to_json
+ @js_data = Gitlab::Json.dump(js_data)
track_event(:render_form)
end
diff --git a/app/controllers/projects/graphs_controller.rb b/app/controllers/projects/graphs_controller.rb
index 47557133ac8..6da70b5e157 100644
--- a/app/controllers/projects/graphs_controller.rb
+++ b/app/controllers/projects/graphs_controller.rb
@@ -104,7 +104,7 @@ class Projects::GraphsController < Projects::ApplicationController
}
end
- render json: @log.to_json
+ render json: Gitlab::Json.dump(@log)
end
def tracking_namespace_source
diff --git a/app/controllers/projects/incidents_controller.rb b/app/controllers/projects/incidents_controller.rb
index 089ee860ea6..599505dcb6d 100644
--- a/app/controllers/projects/incidents_controller.rb
+++ b/app/controllers/projects/incidents_controller.rb
@@ -9,7 +9,6 @@ class Projects::IncidentsController < Projects::ApplicationController
before_action do
push_force_frontend_feature_flag(:work_items, @project&.work_items_feature_flag_enabled?)
push_force_frontend_feature_flag(:work_items_mvc_2, @project&.work_items_mvc_2_feature_flag_enabled?)
- push_frontend_feature_flag(:work_items_hierarchy, @project)
end
feature_category :incident_management
diff --git a/app/controllers/projects/issues_controller.rb b/app/controllers/projects/issues_controller.rb
index 5b1117c0224..ee845cd001e 100644
--- a/app/controllers/projects/issues_controller.rb
+++ b/app/controllers/projects/issues_controller.rb
@@ -1,7 +1,6 @@
# frozen_string_literal: true
class Projects::IssuesController < Projects::ApplicationController
- include RendersNotes
include ToggleSubscriptionAction
include IssuableActions
include ToggleAwardEmoji
@@ -49,11 +48,14 @@ class Projects::IssuesController < Projects::ApplicationController
push_force_frontend_feature_flag(:work_items, project&.work_items_feature_flag_enabled?)
end
+ before_action only: :index do
+ push_frontend_feature_flag(:or_issuable_queries, project)
+ end
+
before_action only: :show do
push_frontend_feature_flag(:issue_assignees_widget, project)
- push_frontend_feature_flag(:realtime_labels, project)
+ push_frontend_feature_flag(:work_items_mvc, project&.group)
push_force_frontend_feature_flag(:work_items_mvc_2, project&.work_items_mvc_2_feature_flag_enabled?)
- push_frontend_feature_flag(:work_items_hierarchy, project)
push_frontend_feature_flag(:epic_widget_edit_confirmation, project)
push_force_frontend_feature_flag(:work_items_create_from_markdown, project&.work_items_create_from_markdown_feature_flag_enabled?)
end
@@ -405,7 +407,6 @@ class Projects::IssuesController < Projects::ApplicationController
options = super
options[:issue_types] = Issue::TYPES_FOR_LIST
- options[:issue_types] = options[:issue_types].excluding('task') unless project.work_items_feature_flag_enabled?
if service_desk?
options.reject! { |key| key == 'author_username' || key == 'author_id' }
@@ -432,10 +433,13 @@ class Projects::IssuesController < Projects::ApplicationController
def create_vulnerability_issue_feedback(issue); end
def redirect_if_task
- return render_404 if issue.task? && !project.work_items_feature_flag_enabled?
return unless issue.task?
- redirect_to project_work_items_path(project, issue.id, params: request.query_parameters)
+ if Feature.enabled?(:use_iid_in_work_items_path, project.group)
+ redirect_to project_work_items_path(project, issue.iid, params: request.query_parameters.merge(iid_path: true))
+ else
+ redirect_to project_work_items_path(project, issue.id, params: request.query_parameters)
+ end
end
end
diff --git a/app/controllers/projects/labels_controller.rb b/app/controllers/projects/labels_controller.rb
index 8ec2cbb41e9..14f2e372bc5 100644
--- a/app/controllers/projects/labels_controller.rb
+++ b/app/controllers/projects/labels_controller.rb
@@ -68,9 +68,10 @@ class Projects::LabelsController < Projects::ApplicationController
def generate
Gitlab::IssuesLabels.generate(@project)
- if params[:redirect] == 'issues'
+ case params[:redirect]
+ when 'issues'
redirect_to project_issues_path(@project)
- elsif params[:redirect] == 'merge_requests'
+ when 'merge_requests'
redirect_to project_merge_requests_path(@project)
else
redirect_to project_labels_path(@project)
diff --git a/app/controllers/projects/learn_gitlab_controller.rb b/app/controllers/projects/learn_gitlab_controller.rb
index 61e4a1812ba..6fe009c8a28 100644
--- a/app/controllers/projects/learn_gitlab_controller.rb
+++ b/app/controllers/projects/learn_gitlab_controller.rb
@@ -23,7 +23,6 @@ class Projects::LearnGitlabController < Projects::ApplicationController
experiment(:invite_for_help_continuous_onboarding, namespace: project.namespace) do |e|
e.candidate {}
- e.publish_to_database
end
end
diff --git a/app/controllers/projects/merge_requests/diffs_controller.rb b/app/controllers/projects/merge_requests/diffs_controller.rb
index 418e7233e21..c88dbc70ed5 100644
--- a/app/controllers/projects/merge_requests/diffs_controller.rb
+++ b/app/controllers/projects/merge_requests/diffs_controller.rb
@@ -38,16 +38,13 @@ class Projects::MergeRequests::DiffsController < Projects::MergeRequests::Applic
diffs = @compare.diffs_in_batch(params[:page], params[:per_page], diff_options: diff_options_hash)
unfoldable_positions = @merge_request.note_positions_for_paths(diffs.diff_file_paths, current_user).unfoldable
- diffs.unfold_diff_files(unfoldable_positions)
- diffs.write_cache
-
options = {
merge_request: @merge_request,
commit: commit,
diff_view: diff_view,
merge_ref_head_diff: render_merge_ref_head_diff?,
pagination_data: diffs.pagination_data,
- allow_tree_conflicts: display_merge_conflicts_in_diff?
+ merge_conflicts_in_diff: display_merge_conflicts_in_diff?
}
# NOTE: Any variables that would affect the resulting json needs to be added to the cache_context to avoid stale cache issues.
@@ -60,10 +57,19 @@ class Projects::MergeRequests::DiffsController < Projects::MergeRequests::Applic
params[:page],
params[:per_page],
options[:merge_ref_head_diff],
- options[:allow_tree_conflicts]
+ options[:merge_conflicts_in_diff]
]
- return unless stale?(etag: [cache_context + diff_options_hash.fetch(:paths, []), diffs])
+ if Feature.enabled?(:check_etags_diffs_batch_before_write_cache, merge_request.project) && !stale?(etag: [cache_context + diff_options_hash.fetch(:paths, []), diffs])
+ return
+ end
+
+ diffs.unfold_diff_files(unfoldable_positions)
+ diffs.write_cache
+
+ if Feature.disabled?(:check_etags_diffs_batch_before_write_cache, merge_request.project) && !stale?(etag: [cache_context + diff_options_hash.fetch(:paths, []), diffs])
+ return
+ end
render json: PaginatedDiffSerializer.new(current_user: current_user).represent(diffs, options)
end
@@ -75,7 +81,7 @@ class Projects::MergeRequests::DiffsController < Projects::MergeRequests::Applic
options = additional_attributes.merge(
only_context_commits: show_only_context_commits?,
merge_ref_head_diff: render_merge_ref_head_diff?,
- allow_tree_conflicts: display_merge_conflicts_in_diff?
+ merge_conflicts_in_diff: display_merge_conflicts_in_diff?
)
render json: DiffsMetadataSerializer.new(project: @merge_request.project, current_user: current_user)
@@ -104,7 +110,7 @@ class Projects::MergeRequests::DiffsController < Projects::MergeRequests::Applic
options = additional_attributes.merge(
diff_view: "inline",
merge_ref_head_diff: render_merge_ref_head_diff?,
- allow_tree_conflicts: display_merge_conflicts_in_diff?
+ merge_conflicts_in_diff: display_merge_conflicts_in_diff?
)
options[:context_commits] = @merge_request.recent_context_commits
diff --git a/app/controllers/projects/merge_requests_controller.rb b/app/controllers/projects/merge_requests_controller.rb
index 9c139733248..4ba79d43f27 100644
--- a/app/controllers/projects/merge_requests_controller.rb
+++ b/app/controllers/projects/merge_requests_controller.rb
@@ -3,7 +3,6 @@
class Projects::MergeRequestsController < Projects::MergeRequests::ApplicationController
include ToggleSubscriptionAction
include IssuableActions
- include RendersNotes
include RendersCommits
include RendersAssignees
include ToggleAwardEmoji
@@ -32,18 +31,15 @@ class Projects::MergeRequestsController < Projects::MergeRequests::ApplicationCo
before_action :check_user_can_push_to_source_branch!, only: [:rebase]
before_action only: [:show] do
- push_frontend_feature_flag(:merge_request_widget_graphql, project)
push_frontend_feature_flag(:core_security_mr_widget_counts, project)
- push_frontend_feature_flag(:refactor_code_quality_extension, project)
- push_frontend_feature_flag(:refactor_mr_widget_test_summary, project)
push_frontend_feature_flag(:issue_assignees_widget, @project)
- push_frontend_feature_flag(:realtime_labels, project)
push_frontend_feature_flag(:refactor_security_extension, @project)
push_frontend_feature_flag(:refactor_code_quality_inline_findings, project)
push_frontend_feature_flag(:moved_mr_sidebar, project)
push_frontend_feature_flag(:paginated_mr_discussions, project)
push_frontend_feature_flag(:mr_review_submit_comment, project)
push_frontend_feature_flag(:mr_experience_survey, project)
+ push_frontend_feature_flag(:realtime_reviewers, project)
end
before_action do
@@ -123,12 +119,13 @@ class Projects::MergeRequestsController < Projects::MergeRequests::ApplicationCo
@commits_count = @merge_request.commits_count + @merge_request.context_commits_count
@diffs_count = get_diffs_count
@issuable_sidebar = serializer.represent(@merge_request, serializer: 'sidebar')
- @current_user_data = UserSerializer.new(project: @project).represent(current_user, {}, MergeRequestCurrentUserEntity).to_json
+ @current_user_data = Gitlab::Json.dump(UserSerializer.new(project: @project).represent(current_user, {}, MergeRequestCurrentUserEntity))
@show_whitespace_default = current_user.nil? || current_user.show_whitespace_in_diffs
@file_by_file_default = current_user&.view_diffs_file_by_file
@coverage_path = coverage_reports_project_merge_request_path(@project, @merge_request, format: :json) if @merge_request.has_coverage_reports?
@update_current_user_path = expose_path(api_v4_user_preferences_path)
@endpoint_metadata_url = endpoint_metadata_url(@project, @merge_request)
+ @endpoint_diff_batch_url = endpoint_diff_batch_url(@project, @merge_request)
set_pipeline_variables
@@ -179,15 +176,15 @@ class Projects::MergeRequestsController < Projects::MergeRequests::ApplicationCo
@merge_request.recent_context_commits
)
- # Get commits from repository
- # or from cache if already merged
- @commits =
- set_commits_for_rendering(
- @merge_request.recent_commits(load_from_gitaly: true).with_latest_pipeline(@merge_request.source_branch).with_markdown_cache,
- commits_count: @merge_request.commits_count
- )
+ per_page = [(params[:per_page] || MergeRequestDiff::COMMITS_SAFE_SIZE).to_i, MergeRequestDiff::COMMITS_SAFE_SIZE].min
+ recent_commits = @merge_request.recent_commits(load_from_gitaly: true, limit: per_page, page: params[:page]).with_latest_pipeline(@merge_request.source_branch).with_markdown_cache
+ @next_page = recent_commits.next_page
+ @commits = set_commits_for_rendering(
+ recent_commits,
+ commits_count: @merge_request.commits_count
+ )
- render json: { html: view_to_html_string('projects/merge_requests/_commits') }
+ render json: { html: view_to_html_string('projects/merge_requests/_commits'), next_page: @next_page }
end
def pipelines
@@ -535,7 +532,7 @@ class Projects::MergeRequestsController < Projects::MergeRequests::ApplicationCo
render json: '', status: :no_content
when :parsed
- render json: report_comparison[:data].to_json, status: :ok
+ render json: Gitlab::Json.dump(report_comparison[:data]), status: :ok
when :error
render json: { status_reason: report_comparison[:status_reason] }, status: :bad_request
else
@@ -553,12 +550,23 @@ class Projects::MergeRequestsController < Projects::MergeRequests::ApplicationCo
return render_404 unless can?(current_user, :read_build, merge_request.actual_head_pipeline)
end
+ def show_whitespace
+ current_user&.show_whitespace_in_diffs ? '0' : '1'
+ end
+
def endpoint_metadata_url(project, merge_request)
- params = request.query_parameters.merge(view: 'inline', diff_head: true, w: current_user&.show_whitespace_in_diffs ? '0' : '1')
+ params = request.query_parameters.merge(view: 'inline', diff_head: true, w: show_whitespace)
diffs_metadata_project_json_merge_request_path(project, merge_request, 'json', params)
end
+ def endpoint_diff_batch_url(project, merge_request)
+ per_page = current_user&.view_diffs_file_by_file ? '1' : '5'
+ params = request.query_parameters.merge(view: 'inline', diff_head: true, w: show_whitespace, page: '0', per_page: per_page)
+
+ diffs_batch_project_json_merge_request_path(project, merge_request, 'json', params)
+ end
+
def convert_date_to_epoch(date)
Date.strptime(date, "%Y-%m-%d")&.to_time&.to_i if date
rescue Date::Error, TypeError
diff --git a/app/controllers/projects/ml/experiments_controller.rb b/app/controllers/projects/ml/experiments_controller.rb
new file mode 100644
index 00000000000..749586791ac
--- /dev/null
+++ b/app/controllers/projects/ml/experiments_controller.rb
@@ -0,0 +1,32 @@
+# frozen_string_literal: true
+
+module Projects
+ module Ml
+ class ExperimentsController < ::Projects::ApplicationController
+ include Projects::Ml::ExperimentsHelper
+ before_action :check_feature_flag
+
+ feature_category :mlops
+
+ MAX_PER_PAGE = 20
+
+ def index
+ @experiments = ::Ml::Experiment.by_project_id(@project.id).page(params[:page]).per(MAX_PER_PAGE)
+ end
+
+ def show
+ @experiment = ::Ml::Experiment.by_project_id_and_iid(@project.id, params[:id])
+
+ return redirect_to project_ml_experiments_path(@project) unless @experiment.present?
+
+ @candidates = @experiment.candidates&.including_metrics_and_params
+ end
+
+ private
+
+ def check_feature_flag
+ render_404 unless Feature.enabled?(:ml_experiment_tracking, @project)
+ end
+ end
+ end
+end
diff --git a/app/controllers/projects/notes_controller.rb b/app/controllers/projects/notes_controller.rb
index d24b232293b..9d3506d49b0 100644
--- a/app/controllers/projects/notes_controller.rb
+++ b/app/controllers/projects/notes_controller.rb
@@ -58,7 +58,7 @@ class Projects::NotesController < Projects::ApplicationController
def outdated_line_change
diff_lines = Rails.cache.fetch(['note', note.id, 'oudated_line_change'], expires_in: 7.days) do
- ::MergeRequests::OutdatedDiscussionDiffLinesService.new(project: note.noteable.source_project, note: note).execute.to_json
+ Gitlab::Json.dump(::MergeRequests::OutdatedDiscussionDiffLinesService.new(project: note.noteable.source_project, note: note).execute)
end
render json: diff_lines
diff --git a/app/controllers/projects/packages/infrastructure_registry_controller.rb b/app/controllers/projects/packages/infrastructure_registry_controller.rb
index f1410bf6043..733df9fdb45 100644
--- a/app/controllers/projects/packages/infrastructure_registry_controller.rb
+++ b/app/controllers/projects/packages/infrastructure_registry_controller.rb
@@ -5,7 +5,7 @@ module Projects
class InfrastructureRegistryController < Projects::ApplicationController
include PackagesAccess
- feature_category :infrastructure_as_code
+ feature_category :package_registry
urgency :low
def show
diff --git a/app/controllers/projects/pipeline_schedules_controller.rb b/app/controllers/projects/pipeline_schedules_controller.rb
index ca787785901..31030d958df 100644
--- a/app/controllers/projects/pipeline_schedules_controller.rb
+++ b/app/controllers/projects/pipeline_schedules_controller.rb
@@ -98,7 +98,7 @@ class Projects::PipelineSchedulesController < Projects::ApplicationController
def schedule_params
params.require(:schedule)
.permit(:description, :cron, :cron_timezone, :ref, :active,
- variables_attributes: [:id, :variable_type, :key, :secret_value, :_destroy] )
+ variables_attributes: [:id, :variable_type, :key, :secret_value, :_destroy])
end
def authorize_play_pipeline_schedule!
diff --git a/app/controllers/projects/pipelines_controller.rb b/app/controllers/projects/pipelines_controller.rb
index 01f7bb9e2cf..7d1a75ae449 100644
--- a/app/controllers/projects/pipelines_controller.rb
+++ b/app/controllers/projects/pipelines_controller.rb
@@ -140,21 +140,13 @@ class Projects::PipelinesController < Projects::ApplicationController
end
def builds
- if Feature.enabled?(:pipeline_tabs_vue, project)
- redirect_to pipeline_path(@pipeline, tab: 'builds')
- else
- render_show
- end
+ render_show
end
def dag
respond_to do |format|
format.html do
- if Feature.enabled?(:pipeline_tabs_vue, project)
- redirect_to pipeline_path(@pipeline, tab: 'dag')
- else
- render_show
- end
+ render_show
end
format.json do
render json: Ci::DagPipelineSerializer
@@ -165,9 +157,7 @@ class Projects::PipelinesController < Projects::ApplicationController
end
def failures
- if Feature.enabled?(:pipeline_tabs_vue, project)
- redirect_to pipeline_path(@pipeline, tab: 'failures')
- elsif @pipeline.failed_builds.present?
+ if @pipeline.failed_builds.present?
render_show
else
redirect_to pipeline_path(@pipeline)
@@ -222,11 +212,7 @@ class Projects::PipelinesController < Projects::ApplicationController
def test_report
respond_to do |format|
format.html do
- if Feature.enabled?(:pipeline_tabs_vue, project)
- redirect_to pipeline_path(@pipeline, tab: 'test_report')
- else
- render_show
- end
+ render_show
end
format.json do
render json: TestReportSerializer
@@ -352,7 +338,6 @@ class Projects::PipelinesController < Projects::ApplicationController
experiment(:runners_availability_section, namespace: project.root_ancestor) do |e|
e.candidate {}
- e.publish_to_database
end
end
diff --git a/app/controllers/projects/product_analytics_controller.rb b/app/controllers/projects/product_analytics_controller.rb
deleted file mode 100644
index 8085b0a6334..00000000000
--- a/app/controllers/projects/product_analytics_controller.rb
+++ /dev/null
@@ -1,61 +0,0 @@
-# frozen_string_literal: true
-
-class Projects::ProductAnalyticsController < Projects::ApplicationController
- before_action :feature_enabled!, only: [:index, :setup, :test, :graphs]
- before_action :authorize_read_product_analytics!
- before_action :tracker_variables, only: [:setup, :test]
-
- feature_category :product_analytics
-
- def index
- @events = product_analytics_events.order_by_time.page(params[:page])
- end
-
- def setup
- end
-
- def test
- @event = product_analytics_events.try(:first)
- end
-
- def graphs
- @graphs = []
- @timerange = 30
-
- requested_graphs = %w(platform os_timezone br_lang doc_charset)
-
- requested_graphs.each do |graph|
- @graphs << ProductAnalytics::BuildGraphService
- .new(project, { graph: graph, timerange: @timerange })
- .execute
- end
-
- @activity_graph = ProductAnalytics::BuildActivityGraphService
- .new(project, { timerange: @timerange })
- .execute
- end
-
- private
-
- def product_analytics_events
- @project.product_analytics_events
- end
-
- def tracker_variables
- # We use project id as Snowplow appId
- @project_id = @project.id.to_s
-
- # Snowplow remembers values like appId and platform between reloads.
- # That is why we have to rename the tracker with a random integer.
- @random = rand(999999)
-
- # Generate random platform every time a tracker is rendered.
- @platform = %w(web mob app)[(@random % 3)]
- end
-
- def feature_enabled!
- render_404 unless Feature.enabled?(:product_analytics, @project)
- end
-end
-
-Projects::ProductAnalyticsController.prepend_mod_with('Projects::ProductAnalyticsController')
diff --git a/app/controllers/projects/prometheus/alerts_controller.rb b/app/controllers/projects/prometheus/alerts_controller.rb
index c3dc17694d9..27ac64e5758 100644
--- a/app/controllers/projects/prometheus/alerts_controller.rb
+++ b/app/controllers/projects/prometheus/alerts_controller.rb
@@ -23,11 +23,7 @@ module Projects
token = extract_alert_manager_token(request)
result = notify_service.execute(token)
- if result.success?
- render json: AlertManagement::AlertSerializer.new.represent(result.payload[:alerts]), code: result.http_status
- else
- head result.http_status
- end
+ head result.http_status
end
private
@@ -37,19 +33,6 @@ module Projects
.new(project, params.permit!)
end
- def serialize_as_json(alert_obj)
- serializer.represent(alert_obj)
- end
-
- def serializer
- PrometheusAlertSerializer
- .new(project: project, current_user: current_user)
- end
-
- def alerts
- alerts_finder.execute
- end
-
def alert
@alert ||= alerts_finder(metric: params[:id]).execute.first || render_404
end
diff --git a/app/controllers/projects/registry/repositories_controller.rb b/app/controllers/projects/registry/repositories_controller.rb
index 87cb8e4781f..ffe95bf4fee 100644
--- a/app/controllers/projects/registry/repositories_controller.rb
+++ b/app/controllers/projects/registry/repositories_controller.rb
@@ -8,10 +8,6 @@ module Projects
before_action :authorize_update_container_image!, only: [:destroy]
- before_action do
- push_frontend_feature_flag(:container_registry_show_shortened_path, project)
- end
-
def index
respond_to do |format|
format.html { ensure_root_container_repository! }
@@ -26,7 +22,11 @@ module Projects
def destroy
image.delete_scheduled!
- DeleteContainerRepositoryWorker.perform_async(current_user.id, image.id) # rubocop:disable CodeReuse/Worker
+
+ unless Feature.enabled?(:container_registry_delete_repository_with_cron_worker)
+ DeleteContainerRepositoryWorker.perform_async(current_user.id, image.id) # rubocop:disable CodeReuse/Worker
+ end
+
track_package_event(:delete_repository, :container)
respond_to do |format|
diff --git a/app/controllers/projects/settings/access_tokens_controller.rb b/app/controllers/projects/settings/access_tokens_controller.rb
index bac35583a97..0884816ef62 100644
--- a/app/controllers/projects/settings/access_tokens_controller.rb
+++ b/app/controllers/projects/settings/access_tokens_controller.rb
@@ -3,6 +3,7 @@
module Projects
module Settings
class AccessTokensController < Projects::ApplicationController
+ include RenderAccessTokens
include AccessTokensActions
layout 'project_settings'
diff --git a/app/controllers/projects/settings/ci_cd_controller.rb b/app/controllers/projects/settings/ci_cd_controller.rb
index cda6c8abea7..8aef1c3d24d 100644
--- a/app/controllers/projects/settings/ci_cd_controller.rb
+++ b/app/controllers/projects/settings/ci_cd_controller.rb
@@ -11,10 +11,6 @@ module Projects
before_action :authorize_admin_pipeline!
before_action :check_builds_available!
before_action :define_variables
- before_action do
- push_frontend_feature_flag(:ajax_new_deploy_token, @project)
- push_frontend_feature_flag(:ci_variable_settings_graphql, @project)
- end
helper_method :highlight_badge
@@ -23,9 +19,11 @@ module Projects
def show
if Feature.enabled?(:ci_pipeline_triggers_settings_vue_ui, @project)
- @triggers_json = ::Ci::TriggerSerializer.new.represent(
+ triggers = ::Ci::TriggerSerializer.new.represent(
@project.triggers, current_user: current_user, project: @project
- ).to_json
+ )
+
+ @triggers_json = Gitlab::Json.dump(triggers)
end
render
diff --git a/app/controllers/projects/settings/repository_controller.rb b/app/controllers/projects/settings/repository_controller.rb
index 43c6451577a..90988645d3a 100644
--- a/app/controllers/projects/settings/repository_controller.rb
+++ b/app/controllers/projects/settings/repository_controller.rb
@@ -6,11 +6,8 @@ module Projects
layout 'project_settings'
before_action :authorize_admin_project!
before_action :define_variables, only: [:create_deploy_token]
- before_action do
- push_frontend_feature_flag(:ajax_new_deploy_token, @project)
- end
- feature_category :source_code_management, [:show, :cleanup]
+ feature_category :source_code_management, [:show, :cleanup, :update]
feature_category :continuous_delivery, [:create_deploy_token]
urgency :low, [:show, :create_deploy_token]
@@ -60,6 +57,19 @@ module Projects
end
end
+ def update
+ result = ::Projects::UpdateService.new(@project, current_user, project_params).execute
+
+ if result[:status] == :success
+ flash[:notice] = _("Project settings were successfully updated.")
+ else
+ flash[:alert] = result[:message]
+ @project.reset
+ end
+
+ redirect_to project_settings_repository_path(project)
+ end
+
private
def render_show
@@ -97,6 +107,18 @@ module Projects
params.require(:deploy_token).permit(:name, :expires_at, :read_repository, :read_registry, :write_registry, :read_package_registry, :write_package_registry, :username)
end
+ def project_params
+ params.require(:project).permit(project_params_attributes)
+ end
+
+ def project_params_attributes
+ [
+ :issue_branch_template,
+ :default_branch,
+ :autoclose_referenced_issues
+ ]
+ end
+
def access_levels_options
{
create_access_levels: levels_for_dropdown,
diff --git a/app/controllers/projects/starrers_controller.rb b/app/controllers/projects/starrers_controller.rb
index bc857648a06..06996e8e5fc 100644
--- a/app/controllers/projects/starrers_controller.rb
+++ b/app/controllers/projects/starrers_controller.rb
@@ -11,14 +11,8 @@ class Projects::StarrersController < Projects::ApplicationController
@starrers = UsersStarProjectsFinder.new(@project, params, current_user: @current_user).execute
@sort = params[:sort].presence || sort_value_name
@starrers = @starrers.preload_users.sort_by_attribute(@sort).page(params[:page])
- @public_count = @project.starrers.with_public_profile.size
- @total_count = @project.starrers.size
+ @public_count = @project.starrers.active.with_public_profile.size
+ @total_count = @project.starrers.active.size
@private_count = @total_count - @public_count
end
-
- private
-
- def has_starred_project?(starrers)
- starrers.first { |starrer| starrer.user_id == current_user.id }
- end
end
diff --git a/app/controllers/projects/templates_controller.rb b/app/controllers/projects/templates_controller.rb
index 6d06b05c1e9..ed5fb838670 100644
--- a/app/controllers/projects/templates_controller.rb
+++ b/app/controllers/projects/templates_controller.rb
@@ -12,7 +12,7 @@ class Projects::TemplatesController < Projects::ApplicationController
templates = @template_type.template_subsets(project)
respond_to do |format|
- format.json { render json: templates.to_json }
+ format.json { render json: Gitlab::Json.dump(templates) }
end
end
@@ -20,7 +20,7 @@ class Projects::TemplatesController < Projects::ApplicationController
template = @template_type.find(params[:key], project)
respond_to do |format|
- format.json { render json: template.to_json }
+ format.json { render json: Gitlab::Json.dump(template) }
end
end
diff --git a/app/controllers/projects/usage_quotas_controller.rb b/app/controllers/projects/usage_quotas_controller.rb
index 07a3c010f4f..d3757eaf481 100644
--- a/app/controllers/projects/usage_quotas_controller.rb
+++ b/app/controllers/projects/usage_quotas_controller.rb
@@ -5,7 +5,7 @@ class Projects::UsageQuotasController < Projects::ApplicationController
layout "project_settings"
- feature_category :utilization
+ feature_category :subscription_cost_management
urgency :low
def index
diff --git a/app/controllers/projects/work_items_controller.rb b/app/controllers/projects/work_items_controller.rb
index b794785f285..a7e59a28fb7 100644
--- a/app/controllers/projects/work_items_controller.rb
+++ b/app/controllers/projects/work_items_controller.rb
@@ -4,13 +4,9 @@ class Projects::WorkItemsController < Projects::ApplicationController
before_action do
push_force_frontend_feature_flag(:work_items, project&.work_items_feature_flag_enabled?)
push_force_frontend_feature_flag(:work_items_mvc_2, project&.work_items_mvc_2_feature_flag_enabled?)
- push_frontend_feature_flag(:work_items_hierarchy, project)
+ push_frontend_feature_flag(:use_iid_in_work_items_path, project)
end
feature_category :team_planning
urgency :low
-
- def index
- render_404 unless project&.work_items_feature_flag_enabled?
- end
end
diff --git a/app/controllers/projects_controller.rb b/app/controllers/projects_controller.rb
index b7b6e6534fb..a5dacbf7f2f 100644
--- a/app/controllers/projects_controller.rb
+++ b/app/controllers/projects_controller.rb
@@ -46,7 +46,6 @@ class ProjectsController < Projects::ApplicationController
push_force_frontend_feature_flag(:work_items, @project&.work_items_feature_flag_enabled?)
push_force_frontend_feature_flag(:work_items_mvc_2, @project&.work_items_mvc_2_feature_flag_enabled?)
push_frontend_feature_flag(:package_registry_access_level)
- push_frontend_feature_flag(:work_items_hierarchy, @project)
end
before_action only: :edit do
@@ -343,7 +342,7 @@ class ProjectsController < Projects::ApplicationController
options['Commits'] = [ref]
end
- render json: options.to_json
+ render json: Gitlab::Json.dump(options)
rescue Gitlab::Git::CommandError
render json: { error: _('Unable to load refs') }, status: :service_unavailable
end
@@ -440,7 +439,7 @@ class ProjectsController < Projects::ApplicationController
def operations_feature_attributes
if Feature.enabled?(:split_operations_visibility_permissions, project)
%i[
- environments_access_level feature_flags_access_level monitor_access_level
+ environments_access_level feature_flags_access_level monitor_access_level infrastructure_access_level
]
else
%i[operations_access_level]
@@ -465,7 +464,6 @@ class ProjectsController < Projects::ApplicationController
:build_timeout_human_readable,
:resolve_outdated_diff_discussions,
:container_registry_enabled,
- :default_branch,
:description,
:emails_disabled,
:external_authorization_classification_label,
@@ -491,7 +489,6 @@ class ProjectsController < Projects::ApplicationController
:merge_method,
:initialize_with_sast,
:initialize_with_readme,
- :autoclose_referenced_issues,
:ci_separated_caches,
:suggestion_commit_message,
:packages_enabled,
diff --git a/app/controllers/registrations_controller.rb b/app/controllers/registrations_controller.rb
index 31fe30f3f06..995303a631a 100644
--- a/app/controllers/registrations_controller.rb
+++ b/app/controllers/registrations_controller.rb
@@ -8,12 +8,15 @@ class RegistrationsController < Devise::RegistrationsController
include OneTrustCSP
include BizibleCSP
include GoogleAnalyticsCSP
+ include PreferredLanguageSwitcher
include RegistrationsTracking
+ include Gitlab::Tracking::Helpers::WeakPasswordErrorEvent
layout 'devise'
prepend_before_action :check_captcha, only: :create
before_action :ensure_destroy_prerequisites_met, only: [:destroy]
+ before_action :init_preferred_language, only: :new
before_action :load_recaptcha, only: :new
before_action :set_invite_params, only: :new
before_action only: [:create] do
@@ -33,15 +36,15 @@ class RegistrationsController < Devise::RegistrationsController
def create
set_user_state
- token = set_custom_confirmation_token
+ set_custom_confirmation_token
super do |new_user|
accept_pending_invitations if new_user.persisted?
persist_accepted_terms_if_required(new_user)
set_role_required(new_user)
- track_experiment_event(new_user)
- send_custom_confirmation_instructions(new_user, token)
+ send_custom_confirmation_instructions
+ track_weak_password_error(new_user, self.class.name, 'create')
if pending_approval?
NotificationService.new.new_instance_access_request(new_user)
@@ -127,7 +130,7 @@ class RegistrationsController < Devise::RegistrationsController
# after user confirms and comes back, he will be redirected
store_location_for(:redirect, users_sign_up_welcome_path(glm_tracking_params))
- return identity_verification_redirect_path if custom_confirmation_enabled?(resource)
+ return identity_verification_redirect_path if custom_confirmation_enabled?
users_almost_there_path(email: resource.email)
end
@@ -189,7 +192,8 @@ class RegistrationsController < Devise::RegistrationsController
def resource
@resource ||= Users::RegistrationsBuildService
- .new(current_user, sign_up_params.merge({ skip_confirmation: registered_with_invite_email? }))
+ .new(current_user, sign_up_params.merge({ skip_confirmation: registered_with_invite_email?,
+ preferred_language: preferred_language }))
.execute
end
@@ -239,19 +243,11 @@ class RegistrationsController < Devise::RegistrationsController
current_user
end
- def track_experiment_event(new_user)
- # Track signed up event to relate it with click "Sign up" button events from
- # the experimental logged out header with marketing links. This allows us to
- # have a funnel of visitors clicking on the header and those visitors
- # signing up and becoming users
- experiment(:logged_out_marketing_header, actor: new_user).track(:signed_up) if new_user.persisted?
- end
-
def identity_verification_redirect_path
# overridden by EE module
end
- def custom_confirmation_enabled?(resource)
+ def custom_confirmation_enabled?
# overridden by EE module
end
@@ -259,7 +255,7 @@ class RegistrationsController < Devise::RegistrationsController
# overridden by EE module
end
- def send_custom_confirmation_instructions(user, token)
+ def send_custom_confirmation_instructions
# overridden by EE module
end
end
diff --git a/app/controllers/search_controller.rb b/app/controllers/search_controller.rb
index 7d4dd04c6d4..5351e3e9e77 100644
--- a/app/controllers/search_controller.rb
+++ b/app/controllers/search_controller.rb
@@ -9,7 +9,11 @@ class SearchController < ApplicationController
RESCUE_FROM_TIMEOUT_ACTIONS = [:count, :show, :autocomplete, :aggregations].freeze
- track_event :show, name: 'i_search_total', destinations: [:redis_hll, :snowplow]
+ track_custom_event :show,
+ name: 'i_search_total',
+ label: 'redis_hll_counters.search.search_total_unique_counts_monthly',
+ action: 'executed',
+ destinations: [:redis_hll, :snowplow]
def self.search_rate_limited_endpoints
%i[show count autocomplete]
@@ -108,7 +112,7 @@ class SearchController < ApplicationController
@ref = params[:project_ref] if params[:project_ref].present?
@filter = params[:filter]
- render json: search_autocomplete_opts(term, filter: @filter).to_json
+ render json: Gitlab::Json.dump(search_autocomplete_opts(term, filter: @filter))
end
def opensearch
@@ -140,8 +144,7 @@ class SearchController < ApplicationController
def check_single_commit_result?
return false if params[:force_search_results]
return false unless @project.present?
- # download_code project policy grants user the read_commit ability
- return false unless Ability.allowed?(current_user, :download_code, @project)
+ return false unless Ability.allowed?(current_user, :read_code, @project)
query = params[:search].strip.downcase
return false unless Commit.valid_hash?(query)
@@ -243,6 +246,10 @@ class SearchController < ApplicationController
search_service.project&.namespace || search_service.group
end
+ def tracking_project_source
+ search_service.project
+ end
+
def search_type
'basic'
end
diff --git a/app/controllers/sessions_controller.rb b/app/controllers/sessions_controller.rb
index 5c969c437f4..c20a9aa4485 100644
--- a/app/controllers/sessions_controller.rb
+++ b/app/controllers/sessions_controller.rb
@@ -13,6 +13,7 @@ class SessionsController < Devise::SessionsController
include BizibleCSP
include VerifiesWithEmail
include GoogleAnalyticsCSP
+ include PreferredLanguageSwitcher
skip_before_action :check_two_factor_requirement, only: [:destroy]
skip_before_action :check_password_expiration, only: [:destroy]
@@ -30,6 +31,7 @@ class SessionsController < Devise::SessionsController
prepend_before_action :ensure_password_authentication_enabled!, if: -> { action_name == 'create' && password_based_login? }
before_action :auto_sign_in_with_provider, only: [:new]
+ before_action :init_preferred_language, only: :new
before_action :store_unauthenticated_sessions, only: [:new]
before_action :save_failed_login, if: :action_new_and_failed_login?
before_action :load_recaptcha
diff --git a/app/controllers/terraform/services_controller.rb b/app/controllers/terraform/services_controller.rb
index e7b9a94fd8e..7ebe1d9ba98 100644
--- a/app/controllers/terraform/services_controller.rb
+++ b/app/controllers/terraform/services_controller.rb
@@ -3,7 +3,7 @@
class Terraform::ServicesController < ApplicationController
skip_before_action :authenticate_user!
- feature_category :infrastructure_as_code
+ feature_category :package_registry
def index
render json: { 'modules.v1' => "/api/#{::API::API.version}/packages/terraform/modules/v1/" }
diff --git a/app/controllers/users_controller.rb b/app/controllers/users_controller.rb
index c35aa8e4346..0f03333d793 100644
--- a/app/controllers/users_controller.rb
+++ b/app/controllers/users_controller.rb
@@ -274,8 +274,6 @@ class UsersController < ApplicationController
def finder_params
{
- # don't display projects pending deletion
- without_deleted: true,
# don't display projects marked for deletion
not_aimed_for_deletion: true
}