Project

General

Profile

Feature #34040 » draft.patch

Mizuki ISHIKAWA, 2021-09-02 07:21

View differences:

app/controllers/issues_controller.rb
72 72
                      :title => "#{@project || Setting.app_title}: #{l(:label_issue_plural)}")
73 73
        end
74 74
        format.csv do
75
          @issues = @query.issues(:limit => Setting.issues_export_limit.to_i)
75
          @issues = @query.issues(:limit => Setting.issues_export_limit.to_i, :with_notes => (params[:with_notes] == '1'))
76 76
          send_data(query_to_csv(@issues, @query, params[:csv]),
77 77
                    :type => 'text/csv; header=present', :filename => 'issues.csv')
78 78
        end
app/helpers/queries_helper.rb
320 320
    columns = query.columns
321 321

  
322 322
    Redmine::Export::CSV.generate(:encoding => params[:encoding]) do |csv|
323
      journal_columns = IssueQuery.journal_columns if params[:with_notes] == '1'
324

  
323 325
      # csv header fields
324
      csv << columns.map {|c| c.caption.to_s}
326
      csv << columns.map {|c| c.caption.to_s} + (journal_columns || []).map{|c| c.caption.to_s}
325 327
      # csv lines
326 328
      items.each do |item|
327
        csv << columns.map {|c| csv_content(c, item)}
329
        if journal_columns
330
          item.journals_with_notes.each_with_index do |journal, index|
331
            if index == 0
332
              csv << columns.map {|c| csv_content(c, item)} + journal_columns.map {|c| csv_content(c, journal)}
333
            else
334
              csv << columns.map {|c| csv_content(c, item) if c.name == :id } + journal_columns.map {|c| csv_content(c, journal)}
335
            end
336
          end
337
        else
338
          csv << columns.map {|c| csv_content(c, item)}
339
        end
328 340
      end
329 341
    end
330 342
  end
app/models/issue.rb
262 262
    @total_estimated_hours = nil
263 263
    @last_updated_by = nil
264 264
    @last_notes = nil
265
    @journals_with_notes = nil
265 266
    base_reload(*args)
266 267
  end
267 268

  
......
1166 1167
  def last_notes
1167 1168
    if @last_notes
1168 1169
      @last_notes
1170
    elsif @journals_with_notes.first.notes
1171
      @journals_with_notes.first.notes
1169 1172
    else
1170 1173
      journals.where.not(notes: '').reorder(:id => :desc).first.try(:notes)
1171 1174
    end
1172 1175
  end
1173 1176

  
1177
  def journals_with_notes
1178
    if @journals_with_notes
1179
      @journals_with_notes
1180
    else
1181
      journals.where.not(notes: '').reorder(:id => :asc)
1182
    end
1183
  end
1184

  
1174 1185
  # Preloads relations for a collection of issues
1175 1186
  def self.load_relations(issues)
1176 1187
    if issues.any?
......
1261 1272
  end
1262 1273

  
1263 1274
  # Preloads visible last notes for a collection of issues
1264
  def self.load_visible_last_notes(issues, user=User.current)
1275
  def self.load_visible_last_notes(issues, user=User.current, has_notes=false)
1265 1276
    if issues.any?
1277
      if has_notes
1278
        issues.each do |issue|
1279
          issue.instance_variable_set("@last_notes", issue.journals_with_notes.last.notes)
1280
        end
1281
        return
1282
      end
1283

  
1266 1284
      issue_ids = issues.map(&:id)
1267 1285
      journal_ids = Journal.joins(issue: :project).
1268 1286
        where(:journalized_type => 'Issue', :journalized_id => issue_ids).
......
1280 1298
    end
1281 1299
  end
1282 1300

  
1301
  # Preloads visible journals_with_notes for a collection of issues
1302
  def self.load_visible_journals_with_notes(issues, user=User.current)
1303
    if issues.any?
1304
      issue_ids = issues.map(&:id)
1305
      journals = Journal.joins(issue: :project).
1306
        where(:journalized_type => 'Issue', :journalized_id => issue_ids).
1307
        where(Journal.visible_notes_condition(user, :skip_pre_condition => true)).
1308
        where.not(notes: '').
1309
        reorder(id: :asc)
1310

  
1311
      issues.each do |issue|
1312
        issue.instance_variable_set("@journals_with_notes", journals.where(journalized_id: issue.id))
1313
      end
1314
    end
1315
  end
1316

  
1283 1317
  # Finds an issue relation given its id.
1284 1318
  def find_relation(relation_id)
1285 1319
    IssueRelation.where("issue_to_id = ? OR issue_from_id = ?", id, id).find(relation_id)
app/models/issue_query.rb
323 323
    @available_columns
324 324
  end
325 325

  
326
  def self.journal_columns
327
    columns =
328
      [
329
        QueryColumn.new(:id, :caption => :label_notes_id, :inline => false),
330
        QueryColumn.new(:notes, :caption => :field_notes, :inline => false),
331
        QueryColumn.new(:user, :caption => :label_notes_author, :inline => false),
332
        QueryColumn.new(:created_on, :caption => :label_notes_created_on, :inline => false)
333
      ]
334
    if User.current.allowed_to?(:set_notes_private, nil, :global => true)
335
      columns << QueryColumn.new(:private_notes, :caption => :field_private_notes, :inline => false)
336
    end
337
  end
338

  
326 339
  def default_columns_names
327 340
    @default_columns_names ||= begin
328 341
      default_columns = Setting.issue_list_default_columns.map(&:to_sym)
......
405 418
    if has_column?(:relations)
406 419
      Issue.load_visible_relations(issues)
407 420
    end
421
    if options[:with_notes]
422
      Issue.load_visible_journals_with_notes(issues)
423
    end
408 424
    if has_column?(:last_notes)
409
      Issue.load_visible_last_notes(issues)
425
      Issue.load_visible_last_notes(issues, User.current, options[:with_notes])
410 426
    end
411 427
    issues
412 428
  rescue ::ActiveRecord::StatementInvalid => e
app/views/issues/index.html.erb
55 55
      <% @query.available_block_columns.each do |column| %>
56 56
        <label><%= check_box_tag 'c[]', column.name, @query.has_column?(column), :id => nil %> <%= column.caption %></label>
57 57
      <% end %>
58
      <label><%= check_box_tag 'with_notes', '1', false, id: nil %> <%= l(:label_all_notes) %></label>
58 59
    </fieldset>
59 60
  <% end %>
60 61
  <%= export_csv_encoding_select_tag %>
config/locales/en.yml
1121 1121
  label_display_type_board: Board
1122 1122
  label_my_bookmarks: My bookmarks
1123 1123
  label_assign_to_me: Assign to me
1124
  label_all_notes: All notes
1125
  label_notes_id: Notes-#
1126
  label_notes_author: Notes author
1127
  label_notes_created_on: Notes created
1124 1128

  
1125 1129
  button_login: Login
1126 1130
  button_submit: Submit
(1-1/5)