From 8c7f4e9d5f36cff46365a7f8c4b9c21578c1e781 Mon Sep 17 00:00:00 2001 From: GitLab Bot Date: Thu, 18 Jun 2020 11:18:50 +0000 Subject: Add latest changes from gitlab-org/gitlab@13-1-stable-ee --- app/finders/admin/runners_finder.rb | 71 ----------------- .../ci/daily_build_group_report_results_finder.rb | 20 +++-- app/finders/ci/runners_finder.rb | 92 ++++++++++++++++++++++ app/finders/events_finder.rb | 5 +- app/finders/issuable_finder.rb | 2 +- app/finders/issuable_finder/params.rb | 10 ++- app/finders/labels_finder.rb | 9 ++- app/finders/milestones_finder.rb | 6 +- app/finders/notes_finder.rb | 2 +- app/finders/resource_label_event_finder.rb | 41 ---------- app/finders/resource_milestone_event_finder.rb | 69 ++++++++++++++++ app/finders/uploader_finder.rb | 34 ++++++++ app/finders/users_finder.rb | 19 ++++- 13 files changed, 245 insertions(+), 135 deletions(-) delete mode 100644 app/finders/admin/runners_finder.rb create mode 100644 app/finders/ci/runners_finder.rb delete mode 100644 app/finders/resource_label_event_finder.rb create mode 100644 app/finders/resource_milestone_event_finder.rb create mode 100644 app/finders/uploader_finder.rb (limited to 'app/finders') diff --git a/app/finders/admin/runners_finder.rb b/app/finders/admin/runners_finder.rb deleted file mode 100644 index b2799565f57..00000000000 --- a/app/finders/admin/runners_finder.rb +++ /dev/null @@ -1,71 +0,0 @@ -# frozen_string_literal: true - -class Admin::RunnersFinder < UnionFinder - NUMBER_OF_RUNNERS_PER_PAGE = 30 - - def initialize(params:) - @params = params - end - - def execute - search! - filter_by_status! - filter_by_runner_type! - filter_by_tag_list! - sort! - paginate! - - @runners.with_tags - end - - def sort_key - if @params[:sort] == 'contacted_asc' - 'contacted_asc' - else - 'created_date' - end - end - - private - - def search! - @runners = - if @params[:search].present? - Ci::Runner.search(@params[:search]) - else - Ci::Runner.all - end - end - - def filter_by_status! - filter_by!(:status_status, Ci::Runner::AVAILABLE_STATUSES) - end - - def filter_by_runner_type! - filter_by!(:type_type, Ci::Runner::AVAILABLE_TYPES) - end - - def filter_by_tag_list! - tag_list = @params[:tag_name].presence - - if tag_list - @runners = @runners.tagged_with(tag_list) - end - end - - def sort! - @runners = @runners.order_by(sort_key) - end - - def paginate! - @runners = @runners.page(@params[:page]).per(NUMBER_OF_RUNNERS_PER_PAGE) - end - - def filter_by!(scope_name, available_scopes) - scope = @params[scope_name] - - if scope.present? && available_scopes.include?(scope) - @runners = @runners.public_send(scope) # rubocop:disable GitlabSecurity/PublicSend - end - end -end diff --git a/app/finders/ci/daily_build_group_report_results_finder.rb b/app/finders/ci/daily_build_group_report_results_finder.rb index 3c3c24c1479..774f08d1ff2 100644 --- a/app/finders/ci/daily_build_group_report_results_finder.rb +++ b/app/finders/ci/daily_build_group_report_results_finder.rb @@ -14,21 +14,25 @@ module Ci end def execute - return none unless can?(current_user, :download_code, project) + return none unless can?(current_user, :read_build_report_results, project) Ci::DailyBuildGroupReportResult.recent_results( - { - project_id: project, - ref_path: ref_path, - date: start_date..end_date - }, - limit: @limit + query_params, + limit: limit ) end private - attr_reader :current_user, :project, :ref_path, :start_date, :end_date + attr_reader :current_user, :project, :ref_path, :start_date, :end_date, :limit + + def query_params + { + project_id: project, + ref_path: ref_path, + date: start_date..end_date + } + end def none Ci::DailyBuildGroupReportResult.none diff --git a/app/finders/ci/runners_finder.rb b/app/finders/ci/runners_finder.rb new file mode 100644 index 00000000000..1b76211c524 --- /dev/null +++ b/app/finders/ci/runners_finder.rb @@ -0,0 +1,92 @@ +# frozen_string_literal: true + +module Ci + class RunnersFinder < UnionFinder + include Gitlab::Allowable + + NUMBER_OF_RUNNERS_PER_PAGE = 30 + + def initialize(current_user:, group: nil, params:) + @params = params + @group = group + @current_user = current_user + end + + def execute + search! + filter_by_status! + filter_by_runner_type! + filter_by_tag_list! + sort! + paginate! + + @runners.with_tags + + rescue Gitlab::Access::AccessDeniedError + Ci::Runner.none + end + + def sort_key + if @params[:sort] == 'contacted_asc' + 'contacted_asc' + else + 'created_date' + end + end + + private + + def search! + @group ? group_runners : all_runners + + @runners = @runners.search(@params[:search]) if @params[:search].present? + end + + def all_runners + raise Gitlab::Access::AccessDeniedError unless @current_user&.admin? + + @runners = Ci::Runner.all + end + + def group_runners + raise Gitlab::Access::AccessDeniedError unless can?(@current_user, :admin_group, @group) + + # Getting all runners from the group itself and all its descendants + descendant_projects = Project.for_group_and_its_subgroups(@group) + + @runners = Ci::Runner.belonging_to_group_or_project(@group.self_and_descendants, descendant_projects) + end + + def filter_by_status! + filter_by!(:status_status, Ci::Runner::AVAILABLE_STATUSES) + end + + def filter_by_runner_type! + filter_by!(:type_type, Ci::Runner::AVAILABLE_TYPES) + end + + def filter_by_tag_list! + tag_list = @params[:tag_name].presence + + if tag_list + @runners = @runners.tagged_with(tag_list) + end + end + + def sort! + @runners = @runners.order_by(sort_key) + end + + def paginate! + @runners = @runners.page(@params[:page]).per(NUMBER_OF_RUNNERS_PER_PAGE) + end + + def filter_by!(scope_name, available_scopes) + scope = @params[scope_name] + + if scope.present? && available_scopes.include?(scope) + @runners = @runners.public_send(scope) # rubocop:disable GitlabSecurity/PublicSend + end + end + end +end diff --git a/app/finders/events_finder.rb b/app/finders/events_finder.rb index 9c56451fd44..52612f1f8aa 100644 --- a/app/finders/events_finder.rb +++ b/app/finders/events_finder.rb @@ -72,9 +72,10 @@ class EventsFinder # rubocop: disable CodeReuse/ActiveRecord def by_action(events) - return events unless Event::ACTIONS[params[:action]] + safe_action = Event.actions[params[:action]] + return events unless safe_action - events.where(action: Event::ACTIONS[params[:action]]) + events.where(action: safe_action) end # rubocop: enable CodeReuse/ActiveRecord diff --git a/app/finders/issuable_finder.rb b/app/finders/issuable_finder.rb index 7014f2ec205..5cdc22fd873 100644 --- a/app/finders/issuable_finder.rb +++ b/app/finders/issuable_finder.rb @@ -451,7 +451,7 @@ class IssuableFinder if params.filter_by_no_label? items.without_label elsif params.filter_by_any_label? - items.any_label + items.any_label(params[:sort]) else items.with_label(params.label_names, params[:sort]) end diff --git a/app/finders/issuable_finder/params.rb b/app/finders/issuable_finder/params.rb index adf9f1ca9d8..5b48d0817e3 100644 --- a/app/finders/issuable_finder/params.rb +++ b/app/finders/issuable_finder/params.rb @@ -105,7 +105,7 @@ class IssuableFinder end def project? - params[:project_id].present? + project_id.present? end def group @@ -132,15 +132,19 @@ class IssuableFinder def project strong_memoize(:project) do - next nil unless params[:project_id].present? + next nil unless project? - project = Project.find(params[:project_id]) + project = project_id.is_a?(Project) ? project_id : Project.find(project_id) project = nil unless Ability.allowed?(current_user, :"read_#{klass.to_ability_name}", project) project end end + def project_id + params[:project_id] + end + def projects strong_memoize(:projects) do next [project] if project? diff --git a/app/finders/labels_finder.rb b/app/finders/labels_finder.rb index 027cdc4fc78..e726772fba4 100644 --- a/app/finders/labels_finder.rb +++ b/app/finders/labels_finder.rb @@ -46,7 +46,6 @@ class LabelsFinder < UnionFinder end else if group? - group = Group.find(params[:group_id]) label_ids << Label.where(group_id: group_ids_for(group)) end @@ -123,7 +122,11 @@ class LabelsFinder < UnionFinder end def group? - params[:group_id].present? + params[:group].present? || params[:group_id].present? + end + + def group + strong_memoize(:group) { params[:group].presence || Group.find(params[:group_id]) } end def project? @@ -169,7 +172,7 @@ class LabelsFinder < UnionFinder ProjectsFinder.new(params: { non_archived: true }, current_user: current_user).execute # rubocop: disable CodeReuse/Finder end - @projects = @projects.in_namespace(params[:group_id]) if group? + @projects = @projects.in_namespace(group.id) if group? @projects = @projects.where(id: params[:project_ids]) if projects? @projects = @projects.reorder(nil) diff --git a/app/finders/milestones_finder.rb b/app/finders/milestones_finder.rb index cfe648d9f79..8f0cdf3b255 100644 --- a/app/finders/milestones_finder.rb +++ b/app/finders/milestones_finder.rb @@ -58,10 +58,8 @@ class MilestonesFinder Milestone.filter_by_state(items, params[:state]) end - # rubocop: disable CodeReuse/ActiveRecord def order(items) - order_statement = Gitlab::Database.nulls_last_order('due_date', 'ASC') - items.reorder(order_statement).order('title ASC') + sort_by = params[:sort].presence || 'due_date_asc' + items.sort_by_attribute(sort_by) end - # rubocop: enable CodeReuse/ActiveRecord end diff --git a/app/finders/notes_finder.rb b/app/finders/notes_finder.rb index e798db561bf..8e57014f66e 100644 --- a/app/finders/notes_finder.rb +++ b/app/finders/notes_finder.rb @@ -148,7 +148,7 @@ class NotesFinder # Searches for notes matching the given query. # - # This method uses ILIKE on PostgreSQL and LIKE on MySQL. + # This method uses ILIKE on PostgreSQL. # def search(notes) query = @params[:search] diff --git a/app/finders/resource_label_event_finder.rb b/app/finders/resource_label_event_finder.rb deleted file mode 100644 index 9aafd6e91b9..00000000000 --- a/app/finders/resource_label_event_finder.rb +++ /dev/null @@ -1,41 +0,0 @@ -# frozen_string_literal: true - -class ResourceLabelEventFinder - include FinderMethods - - MAX_PER_PAGE = 100 - - attr_reader :params, :current_user, :eventable - - def initialize(current_user, eventable, params = {}) - @current_user = current_user - @eventable = eventable - @params = params - end - - def execute - events = eventable.resource_label_events.inc_relations - events = events.page(page).per(per_page) - events = visible_to_user(events) - - Kaminari.paginate_array(events) - end - - private - - def visible_to_user(events) - ResourceLabelEvent.preload_label_subjects(events) - - events.select do |event| - Ability.allowed?(current_user, :read_label, event) - end - end - - def per_page - [params[:per_page], MAX_PER_PAGE].compact.min - end - - def page - params[:page] || 1 - end -end diff --git a/app/finders/resource_milestone_event_finder.rb b/app/finders/resource_milestone_event_finder.rb new file mode 100644 index 00000000000..7af34f0a4bc --- /dev/null +++ b/app/finders/resource_milestone_event_finder.rb @@ -0,0 +1,69 @@ +# frozen_string_literal: true + +class ResourceMilestoneEventFinder + include FinderMethods + + MAX_PER_PAGE = 100 + + attr_reader :params, :current_user, :eventable + + def initialize(current_user, eventable, params = {}) + @current_user = current_user + @eventable = eventable + @params = params + end + + def execute + Kaminari.paginate_array(visible_events) + end + + private + + def visible_events + @visible_events ||= visible_to_user(events) + end + + def events + @events ||= eventable.resource_milestone_events.include_relations.page(page).per(per_page) + end + + def visible_to_user(events) + events.select { |event| visible_for_user?(event) } + end + + def visible_for_user?(event) + milestone = event_milestones[event.milestone_id] + return if milestone.blank? + + parent = milestone.parent + parent_availabilities[key_for_parent(parent)] + end + + def parent_availabilities + @parent_availabilities ||= relevant_parents.to_h do |parent| + [key_for_parent(parent), Ability.allowed?(current_user, :read_milestone, parent)] + end + end + + def key_for_parent(parent) + "#{parent.class.name}_#{parent.id}" + end + + def event_milestones + @milestones ||= events.map(&:milestone).uniq.to_h do |milestone| + [milestone.id, milestone] + end + end + + def relevant_parents + @relevant_parents ||= event_milestones.map { |_id, milestone| milestone.parent } + end + + def per_page + [params[:per_page], MAX_PER_PAGE].compact.min + end + + def page + params[:page] || 1 + end +end diff --git a/app/finders/uploader_finder.rb b/app/finders/uploader_finder.rb new file mode 100644 index 00000000000..0d1de0d56fd --- /dev/null +++ b/app/finders/uploader_finder.rb @@ -0,0 +1,34 @@ +# frozen_string_literal: true + +class UploaderFinder + # Instantiates a a new FileUploader + # FileUploader can be opened via .open agnostic of storage type + # Arguments correspond to Upload.secret, Upload.model_type and Upload.file_path + # Returns a FileUploader with uploaded file retrieved into the object state + def initialize(project, secret, file_path) + @project = project + @secret = secret + @file_path = file_path + end + + def execute + prevent_path_traversal_attack! + retrieve_file_state! + + uploader + rescue ::Gitlab::Utils::PathTraversalAttackError + nil # no-op if for incorrect files + end + + def prevent_path_traversal_attack! + Gitlab::Utils.check_path_traversal!(@file_path) + end + + def retrieve_file_state! + uploader.retrieve_from_store!(@file_path) + end + + def uploader + @uploader ||= FileUploader.new(@project, secret: @secret) + end +end diff --git a/app/finders/users_finder.rb b/app/finders/users_finder.rb index ebb686c2aa7..f87e0c67604 100644 --- a/app/finders/users_finder.rb +++ b/app/finders/users_finder.rb @@ -15,6 +15,8 @@ # blocked: boolean # external: boolean # without_projects: boolean +# sort: string +# id: integer # class UsersFinder include CreatedAtFilter @@ -30,6 +32,7 @@ class UsersFinder def execute users = User.all.order_id_desc users = by_username(users) + users = by_id(users) users = by_search(users) users = by_blocked(users) users = by_active(users) @@ -40,7 +43,7 @@ class UsersFinder users = by_without_projects(users) users = by_custom_attributes(users) - users + order(users) end private @@ -51,6 +54,12 @@ class UsersFinder users.by_username(params[:username]) end + def by_id(users) + return users unless params[:id] + + users.id_in(params[:id]) + end + def by_search(users) return users unless params[:search].present? @@ -102,6 +111,14 @@ class UsersFinder users.without_projects end + + # rubocop: disable CodeReuse/ActiveRecord + def order(users) + return users unless params[:sort] + + users.order_by(params[:sort]) + end + # rubocop: enable CodeReuse/ActiveRecord end UsersFinder.prepend_if_ee('EE::UsersFinder') -- cgit v1.2.3