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

base_query_builder.rb « aggregated « cycle_analytics « analytics « gitlab « lib - gitlab.com/gitlab-org/gitlab-foss.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
blob: fc0e4ab5a0de4dd3c32f98e0977c363d22c432e5 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
# frozen_string_literal: true

module Gitlab
  module Analytics
    module CycleAnalytics
      module Aggregated
        # rubocop: disable CodeReuse/ActiveRecord
        class BaseQueryBuilder
          include StageQueryHelpers

          MODEL_CLASSES = {
            MergeRequest.to_s => ::Analytics::CycleAnalytics::MergeRequestStageEvent,
            Issue.to_s => ::Analytics::CycleAnalytics::IssueStageEvent
          }.freeze

          # Allowed params:
          # * from - stage end date filter start date
          # * to - stage end date filter to date
          # * author_username
          # * milestone_title
          # * label_name (array)
          # * assignee_username (array)
          # * project_ids (array)
          def initialize(stage:, params: {})
            @stage = stage
            @params = params
            @root_ancestor = stage.namespace.root_ancestor
            @stage_event_model = MODEL_CLASSES.fetch(stage.subject_class.to_s)
          end

          def build
            query = base_query
            query = filter_by_stage_parent(query)
            query = filter_author(query)
            query = filter_milestone_ids(query)
            query = filter_label_names(query)
            filter_assignees(query)
          end

          def build_sorted_query
            direction = params[:direction] || :desc

            if params[:sort] == :duration
              build.order_by_duration(direction)
            else
              build.order_by_end_event(direction)
            end
          end

          def filter_author(query)
            return query if params[:author_username].blank?

            user = find_user(params[:author_username])
            return query.none if user.blank?

            query.authored(user)
          end

          def filter_milestone_ids(query)
            return query if params[:milestone_title].blank?

            milestone = find_milestone(params[:milestone_title])
            return query.none if milestone.blank?

            query.with_milestone_id(milestone.id)
          end

          def filter_label_names(query)
            return query if params[:label_name].blank?

            LabelFilter.new(
              stage: stage,
              params: params,
              project: nil,
              group: root_ancestor
            ).filter(query)
          end

          def filter_assignees(query)
            return query if params[:assignee_username].blank?

            Issuables::AssigneeFilter
              .new(params: { assignee_username: params[:assignee_username] })
              .filter(query)
          end

          def filter_by_stage_parent(query)
            query.by_project_id(stage.namespace.project.id)
          end

          def base_query
            query = stage_event_model
              .by_stage_event_hash_id(stage.stage_event_hash_id)

            from = params[:from] || 30.days.ago
            if in_progress?
              query = query
                .end_event_is_not_happened_yet
                .opened_state
                .start_event_timestamp_after(from)
              query = query.start_event_timestamp_before(params[:to]) if params[:to]
            else
              query = query.end_event_timestamp_after(from)
              query = query.end_event_timestamp_before(params[:to]) if params[:to]
            end

            query
          end

          private

          attr_reader :stage, :params, :root_ancestor, :stage_event_model

          def find_milestone(title)
            MilestonesFinder
              .new(group_ids: root_ancestor.self_and_descendant_ids, project_ids: root_ancestor.all_projects.select(:id), title: title)
              .execute
              .first
          end

          def find_user(username)
            User.by_username(username).first
          end
        end
        # rubocop: enable CodeReuse/ActiveRecord
      end
    end
  end
end
Gitlab::Analytics::CycleAnalytics::Aggregated::BaseQueryBuilder.prepend_mod_with('Gitlab::Analytics::CycleAnalytics::Aggregated::BaseQueryBuilder')