Project

General

Profile

Feature #12388 » 0001-wip.patch

Marius BĂLTEANU, 2026-07-12 01:40

View differences:

app/assets/stylesheets/application.css
2071 2071
}
2072 2072

  
2073 2073
.journals h4.journal-header .update-info {
2074
  font-size: 0.9em;
2075
}
2076

  
2077
.journals h4.journal-header span.update-info {
2074 2078
  color: var(--oc-gray-6);
2075 2079
  font-size: 0.9em;
2076 2080
}
app/controllers/journals_controller.rb
18 18
# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
19 19

  
20 20
class JournalsController < ApplicationController
21
  before_action :find_journal, :only => [:edit, :update, :diff]
21
  before_action :find_journal, :only => [:edit, :update, :diff, :history]
22 22
  before_action :find_issue, :only => [:new]
23 23
  before_action :find_optional_project, :only => [:index]
24
  before_action :authorize, :only => [:new, :edit, :update, :diff]
24
  before_action :authorize, :only => [:new, :edit, :update, :diff, :history]
25 25
  accept_atom_auth :index
26 26
  accept_api_auth :update
27 27
  menu_item :issues
......
64 64
    @diff = Redmine::Helpers::Diff.new(@detail.value, @detail.old_value)
65 65
  end
66 66

  
67
  def history
68
    @issue = @journal.issue
69
    @details = @journal.details.where(property: 'attr', prop_key: 'notes').reorder(id: :desc)
70
    respond_to do |format|
71
      format.js
72
    end
73
  end
74

  
67 75
  def new
68 76
    @journal = Journal.visible.find(params[:journal_id]) if params[:journal_id]
69 77
    @content = if @journal
app/helpers/journals_helper.rb
82 82
  def render_journal_update_info(journal)
83 83
    return if journal.created_on == journal.updated_on
84 84

  
85
    content_tag('span', "· #{l(:label_edited)}", :title => l(:label_time_by_author, :time => format_time(journal.updated_on), :author => journal.updated_by), :class => 'update-info')
85
    notes_details = journal.details.select {|d| d.property == 'attr' && d.prop_key == 'notes'}
86
    if notes_details.any?
87
      link_to("· #{l(:label_edited)}",
88
              history_journal_path(journal),
89
              :remote => true,
90
              :class => 'update-info',
91
              :title => l(:label_time_by_author, :time => format_time(journal.updated_on), :author => journal.updated_by))
92
    else
93
      # Only show Edited label, no link since there is nothing to show in note history view
94
      content_tag('span', "· #{l(:label_edited)}", :title => l(:label_time_by_author, :time => format_time(journal.updated_on), :author => journal.updated_by), :class => 'update-info')
95
    end
86 96
  end
87 97
end
app/models/journal.rb
125 125
        detail.custom_field && detail.custom_field.visible_by?(project, user)
126 126
      elsif detail.property == 'relation'
127 127
        Issue.find_by_id(detail.value || detail.old_value).try(:visible?, user)
128
      elsif detail.property == 'attr' && detail.prop_key == 'notes'
129
        false
128 130
      else
129 131
        true
130 132
      end
......
268 270

  
269 271
  # Generates journal details for attribute and custom field changes
270 272
  def journalize_changes
273
    if !new_record? && notes_changed?
274
      add_attribute_detail('notes', notes_was, notes)
275
    end
276

  
271 277
    # attributes changes
272 278
    if @attributes_before_change
273 279
      attrs = (journalized.journalized_attribute_names + @attributes_before_change.keys).uniq
app/views/issues/tabs/_history.html.erb
22 22
        </span>
23 23
      </h4>
24 24
      <div class="journal-content">
25
        <% if journal.details.any? %>
25
        <% if journal.visible_details.any? %>
26 26
          <ul class="journal-details">
27 27
            <% details_to_strings(journal.visible_details).each do |string| %>
28 28
              <li><%= string %></li>
app/views/journals/_history.html.erb
1
<h3 class="title"><%= l(:label_history) %></h3>
2

  
3
<div class="journal-history journals" style="max-height: 400px; overflow-y: auto;">
4
  <% @details.each_with_index do |detail, index| %>
5
    <div class="journal-history-version">
6
      <h4 class="journal-header">
7
        <span class="journal-info">
8
            <%= avatar(@journal.user) %>
9
            <%= authoring @journal.created_on, @journal.user, :label => :label_updated_time_by %>
10
        </span>
11
        <span class="journal-meta">
12
          #<%= @details.size - index %>
13
        </span>
14
      </h4>
15
      <pre class="text-diff"><%= Redmine::Helpers::Diff.new(detail.value, detail.old_value).to_html %></pre>
16
    </div>
17
  <% end %>
18
</div>
19

  
20
<p class="buttons">
21
  <%= link_to_function l(:button_close), "hideModal(this);" %>
22
</p>
app/views/journals/history.js.erb
1
$('#ajax-modal').html('<%= escape_javascript(render :partial => 'history') %>');
2
showModal('ajax-modal', '650px');
app/views/journals/update.js.erb
8 8
  $("#journal-<%= @journal.id %>-notes").show();
9 9
  $("#journal-<%= @journal.id %>-form").remove();
10 10
  var journal_header = $("#change-<%= @journal.id %>>div.note>h4.journal-header>.journal-info");
11
  var journal_updated_info = journal_header.find("span.update-info");
11
  var journal_updated_info = journal_header.find(".update-info");
12 12
  if (journal_updated_info.length > 0) {
13 13
    journal_updated_info.replaceWith('<%= escape_javascript(render_journal_update_info(@journal)) %>');
14 14
  } else {
config/routes.rb
65 65
  resources :journals, :only => [:edit, :update] do
66 66
    member do
67 67
      get 'diff'
68
      get 'history'
68 69
    end
69 70
  end
70 71

  
lib/redmine/preparation.rb
59 59
                                        :auto_complete => [:issues],
60 60
                                        :context_menus => [:issues],
61 61
                                        :versions => [:index, :show, :status_by],
62
                                        :journals => [:index, :diff],
62
                                        :journals => [:index, :diff, :history],
63 63
                                        :queries => :index,
64 64
                                        :reports => [:issue_report, :issue_report_details]},
65 65
                         :read => true
(1-1/3)