loggable_activity 0.1.56 → 0.1.59

Sign up to get free protection for your applications and to get access to all the features.
Files changed (71) hide show
  1. checksums.yaml +4 -4
  2. data/.rubocop.yml +10 -1
  3. data/CHANGELOG.md +9 -0
  4. data/GETTING-STARTED.md +8 -47
  5. data/PAYLOAD_EXAMPLE.md +63 -0
  6. data/docs/LoggableActivity/Activity.html +92 -241
  7. data/docs/LoggableActivity/Configuration.html +162 -15
  8. data/docs/LoggableActivity/ConfigurationError.html +148 -0
  9. data/docs/LoggableActivity/DataOwner.html +138 -0
  10. data/docs/LoggableActivity/Encryption.html +18 -14
  11. data/docs/LoggableActivity/EncryptionError.html +47 -1
  12. data/docs/LoggableActivity/EncryptionKey.html +54 -35
  13. data/docs/LoggableActivity/Error.html +48 -0
  14. data/docs/LoggableActivity/Hooks.html +221 -89
  15. data/docs/LoggableActivity/Payload.html +103 -27
  16. data/docs/LoggableActivity/Services/BasePayloadsBuilder.html +442 -0
  17. data/docs/LoggableActivity/Services/DestroyPayloadsBuilder.html +395 -0
  18. data/docs/LoggableActivity/Services/PayloadsBuilder.html +342 -0
  19. data/docs/LoggableActivity/Services/UpdatePayloadsBuilder.html +490 -0
  20. data/docs/LoggableActivity/Services.html +93 -0
  21. data/docs/created.rid +14 -10
  22. data/docs/index.html +10 -2
  23. data/docs/js/navigation.js.gz +0 -0
  24. data/docs/js/search_index.js +1 -1
  25. data/docs/js/search_index.js.gz +0 -0
  26. data/docs/js/searcher.js.gz +0 -0
  27. data/docs/table_of_contents.html +253 -85
  28. data/lib/generators/loggable_activity/install_generator.rb +2 -18
  29. data/lib/generators/loggable_activity/templates/.DS_Store +0 -0
  30. data/lib/generators/loggable_activity/templates/binary_ids/create_loggable_activities.rb +9 -10
  31. data/lib/generators/loggable_activity/templates/create_loggable_activities.rb +16 -13
  32. data/lib/loggable_activity/activity.rb +53 -102
  33. data/lib/loggable_activity/configuration.rb +60 -3
  34. data/lib/loggable_activity/data_owner.rb +18 -0
  35. data/lib/loggable_activity/encryption.rb +14 -14
  36. data/lib/loggable_activity/encryption_key.rb +26 -25
  37. data/lib/loggable_activity/error.rb +34 -0
  38. data/lib/loggable_activity/hooks.rb +78 -43
  39. data/lib/loggable_activity/payload.rb +70 -20
  40. data/lib/loggable_activity/services/base_payloads_builder.rb +127 -0
  41. data/lib/loggable_activity/services/destroy_payloads_builder.rb +127 -0
  42. data/lib/loggable_activity/services/payloads_builder.rb +98 -0
  43. data/lib/loggable_activity/services/update_payloads_builder.rb +170 -0
  44. data/lib/loggable_activity/version.rb +1 -1
  45. data/lib/loggable_activity.rb +6 -6
  46. data/lib/schemas/config_schema.json +90 -0
  47. metadata +37 -26
  48. data/docs/LoggableActivity/PayloadsBuilder.html +0 -441
  49. data/docs/LoggableActivity/UpdatePayloadsBuilder.html +0 -424
  50. data/lib/generators/loggable_activity/install_templates_generator.rb +0 -105
  51. data/lib/generators/loggable_activity/templates/helpers/activity_helper.rb +0 -37
  52. data/lib/generators/loggable_activity/templates/helpers/router.rb +0 -52
  53. data/lib/generators/loggable_activity/templates/helpers/routes_helper.rb +0 -20
  54. data/lib/generators/loggable_activity/templates/views/loggable_activity/templates/default/_create.html.erb +0 -23
  55. data/lib/generators/loggable_activity/templates/views/loggable_activity/templates/default/_create.html.slim +0 -18
  56. data/lib/generators/loggable_activity/templates/views/loggable_activity/templates/default/_destroy.html.erb +0 -18
  57. data/lib/generators/loggable_activity/templates/views/loggable_activity/templates/default/_destroy.html.slim +0 -17
  58. data/lib/generators/loggable_activity/templates/views/loggable_activity/templates/default/_show.html.erb +0 -18
  59. data/lib/generators/loggable_activity/templates/views/loggable_activity/templates/default/_show.html.slim +0 -17
  60. data/lib/generators/loggable_activity/templates/views/loggable_activity/templates/default/_update.html.erb +0 -18
  61. data/lib/generators/loggable_activity/templates/views/loggable_activity/templates/default/_update.html.slim +0 -12
  62. data/lib/generators/loggable_activity/templates/views/loggable_activity/templates/shared/_activity_info.html.erb +0 -12
  63. data/lib/generators/loggable_activity/templates/views/loggable_activity/templates/shared/_activity_info.html.slim +0 -11
  64. data/lib/generators/loggable_activity/templates/views/loggable_activity/templates/shared/_list_attrs.html.erb +0 -8
  65. data/lib/generators/loggable_activity/templates/views/loggable_activity/templates/shared/_list_attrs.html.slim +0 -6
  66. data/lib/generators/loggable_activity/templates/views/loggable_activity/templates/shared/_update_attrs.html.erb +0 -17
  67. data/lib/generators/loggable_activity/templates/views/loggable_activity/templates/shared/_update_attrs.html.slim +0 -14
  68. data/lib/generators/loggable_activity/templates/views/loggable_activity/templates/shared/_updated_relations.html.erb +0 -23
  69. data/lib/generators/loggable_activity/templates/views/loggable_activity/templates/shared/_updated_relations.html.slim +0 -21
  70. data/lib/loggable_activity/payloads_builder.rb +0 -153
  71. data/lib/loggable_activity/update_payloads_builder.rb +0 -127
@@ -1,23 +0,0 @@
1
- <tr>
2
- <td>
3
- <%= render partial: 'loggable_activity/templates/shared/activity_info', locals: { activity: activity } %>
4
- </td>
5
- <td>
6
- <b class="text-secondary"><%= primary_type(activity) %></b>
7
- <br>
8
- <% activity.primary_payload_attrs.each do |k, v| %>
9
- <%= "<i>#{k}:</i> #{v.blank? ? t('loggable.activity.deleted') : v}".html_safe %>
10
- <br>
11
- <% end %>
12
- <br>
13
- <% activity.relations_attrs.each do |relation_attrs| %>
14
- <b class="text-secondary"><%= relation_type(relation_attrs) %></b>
15
- <br>
16
- <%= render partial: 'loggable_activity/templates/shared/list_attrs', locals: { attrs: relation_attrs[:attrs] } %>
17
- <br>
18
- <% end %>
19
- </td>
20
- <td>
21
- <%= link_to 'Delete', demo_activity_log_path(activity), data: { turbo_method: :delete, confirm: 'Are you sure?' }, class: 'btn btn-danger btn-sm' %>
22
- </td>
23
- </tr>
@@ -1,18 +0,0 @@
1
- tr
2
- td
3
- = render partial: 'loggable_activity/templates/shared/activity_info', locals: { activity: activity }
4
- td
5
- b.text-secondary = primary_type(activity)
6
- br
7
- - activity.primary_payload_attrs.each do |k, v|
8
- = "<i>#{k}:</i> #{v.blank? ? t('loggable.activity.deleted') : v}".html_safe
9
- br/
10
- br
11
- - activity.relations_attrs.each do |relation_attrs|
12
- b.text-secondary = relation_type(relation_attrs)
13
- br/
14
- =
15
- = render partial: 'loggable_activity/templates/shared/list_attrs', locals: { attrs: relation_attrs[:attrs] }
16
- br/
17
- td
18
- =< link_to 'Delete', demo_activity_log_path(activity), data: { turbo_method: :delete, confirm: 'Are you sure?' }, class: 'btn btn-danger btn-sm'
@@ -1,18 +0,0 @@
1
- <tr>
2
- <td>
3
- <%= render partial: 'loggable_activity/templates/shared/activity_info', locals: { activity: activity } %>
4
- </td>
5
- <td>
6
- <% update_activity_attrs = activity.update_activity_attrs %>
7
- <% if update_attrs = update_activity_attrs[:update_attrs] %>
8
- <%= render partial: 'loggable_activity/templates/shared/update_attrs', locals: { update_attrs: update_attrs } %>
9
- <% end %>
10
- <% if updated_relations = update_activity_attrs[:updated_relations_attrs] %>
11
- <br>
12
- <%= render partial: 'loggable_activity/templates/shared/updated_relations', locals: { updated_relations: updated_relations } %>
13
- <% end %>
14
- </td>
15
- <td>
16
- <%= link_to 'Delete', demo_activity_log_path(activity), data: { turbo_method: :delete, confirm: 'Are you sure?' }, class: 'btn btn-danger btn-sm' %>
17
- </td>
18
- </tr>
@@ -1,17 +0,0 @@
1
- tr
2
- td
3
- = render partial: 'loggable_activity/templates/shared/activity_info', locals: { activity: activity }
4
- td
5
- b.text-secondary = primary_type(activity)
6
- br/
7
- - activity.primary_payload_attrs.each do |k, v|
8
- = "<i>#{k}:</i> #{v.blank? ? t('loggable.activity.deleted') : v}".html_safe
9
- br/
10
- br/
11
- - activity.relations_attrs.each do |relation_attrs|
12
- b.text-secondary = relation_type(relation_attrs)
13
- br/
14
- = render partial: 'loggable_activity/templates/shared/list_attrs', locals: { attrs: relation_attrs[:attrs] }
15
- br/
16
- td
17
- =< link_to 'Delete', demo_activity_log_path(activity), data: { turbo_method: :delete, confirm: 'Are you sure?' }, class: 'btn btn-danger btn-sm'
@@ -1,18 +0,0 @@
1
- <tr>
2
- <td>
3
- <%= render partial: 'loggable_activity/templates/shared/activity_info', locals: { activity: activity } %>
4
- </td>
5
- <td>
6
- <b class="text-secondary"><%= primary_type(activity) %></b><br/>
7
- <% activity.primary_payload_attrs.each do |k, v| %>
8
- <%= "<i>#{k}:</i> #{v.blank? ? t('loggable.activity.deleted') : v}".html_safe %><br/>
9
- <% end %><br/>
10
- <% activity.relations_attrs.each do |relation_attrs| %>
11
- <b class="text-secondary"><%= relation_type(relation_attrs) %></b><br/>
12
- <%= render partial: 'loggable_activity/templates/shared/list_attrs', locals: { attrs: relation_attrs[:attrs] } %><br/>
13
- <% end %>
14
- </td>
15
- <td>
16
- <%= link_to 'Delete', demo_activity_log_path(activity), data: { turbo_method: :delete, confirm: 'Are you sure?' }, class: 'btn btn-danger btn-sm' %>
17
- </td>
18
- </tr>
@@ -1,17 +0,0 @@
1
- tr
2
- td
3
- = render partial: 'loggable_activity/templates/shared/activity_info', locals: { activity: activity }
4
- td
5
- b.text-secondary = primary_type(activity)
6
- br/
7
- - activity.primary_payload_attrs.each do |k, v|
8
- = "<i>#{k}:</i> #{v.blank? ? t('loggable.activity.deleted') : v}".html_safe
9
- br/
10
- br/
11
- - activity.relations_attrs.each do |relation_attrs|
12
- b.text-secondary = relation_type(relation_attrs)
13
- br/
14
- = render partial: 'loggable_activity/templates/shared/list_attrs', locals: { attrs: relation_attrs[:attrs] }
15
- br/
16
- td
17
- =< link_to 'Delete', demo_activity_log_path(activity), data: { turbo_method: :delete, confirm: 'Are you sure?' }, class: 'btn btn-danger btn-sm'
@@ -1,18 +0,0 @@
1
- <tr>
2
- <td>
3
- <%= render partial: 'loggable_activity/templates/shared/activity_info', locals: { activity: activity } %>
4
- </td>
5
- <td>
6
- <% update_activity_attrs = activity.update_activity_attrs %>
7
- <% if update_attrs = update_activity_attrs[:update_attrs] %>
8
- <%= render partial: 'loggable_activity/templates/shared/update_attrs', locals: { update_attrs: update_attrs } %>
9
- <% end %>
10
- <% if updated_relations = update_activity_attrs[:updated_relations_attrs] %>
11
- <br>
12
- <%= render partial: 'loggable_activity/templates/shared/updated_relations', locals: { updated_relations: updated_relations } %>
13
- <% end %>
14
- </td>
15
- <td>
16
- <%= link_to 'Delete', demo_activity_log_path(activity), data: { turbo_method: :delete, confirm: 'Are you sure?' }, class: 'btn btn-danger btn-sm' %>
17
- </td>
18
- </tr>
@@ -1,12 +0,0 @@
1
- tr
2
- td
3
- = render partial: 'loggable_activity/templates/shared/activity_info', locals: { activity: activity }
4
- td
5
- - update_activity_attrs = activity.update_activity_attrs
6
- - if update_attrs = update_activity_attrs[:update_attrs]
7
- = render partial: 'loggable_activity/templates/shared/update_attrs', locals: { update_attrs: update_attrs }
8
- - if updated_relations = update_activity_attrs[:updated_relations_attrs]
9
- br/
10
- = render partial: 'loggable_activity/templates/shared/updated_relations', locals: { updated_relations: updated_relations }
11
- td
12
- =< link_to 'Delete', demo_activity_log_path(activity), data: { turbo_method: :delete, confirm: 'Are you sure?' }, class: 'btn btn-danger btn-sm'
@@ -1,12 +0,0 @@
1
- <div class="px-4">
2
- <h5><%= t("loggable.activity.#{activity.action}", name: "") %></h5>
3
- <b><%= activity.record_display_name %></b>
4
- <br>
5
- <i>Actor:&nbsp;</i>
6
- <br>
7
- <%= activity.actor_display_name %>
8
- <br>
9
- <i>When:&nbsp;</i>
10
- <br>
11
- <%= I18n.l(activity.created_at, format: :long) %>
12
- </div>
@@ -1,11 +0,0 @@
1
- .px-4
2
- .h5 = t("loggable.activity.#{activity.action}", name: "")
3
- b = activity.record_display_name
4
- br
5
- i Actor:&nbsp;
6
- br
7
- = activity.actor_display_name
8
- br
9
- i When:&nbsp;
10
- br
11
- = I18n.l(activity.created_at, format: :long)
@@ -1,8 +0,0 @@
1
- <% if attrs == :deleted %>
2
- <%= t('loggable.activity.deleted') %>
3
- <% elsif attrs.is_a?(Hash) %>
4
- <% attrs.each do |k, v| %>
5
- <%= "<i>#{k}:</i> #{v.blank? ? t('loggable.activity.deleted') : v}".html_safe %>
6
- <br>
7
- <% end %>
8
- <% end %>
@@ -1,6 +0,0 @@
1
- - if attrs == :deleted
2
- = t('loggable.activity.deleted')
3
- - elsif attrs.is_a?(Hash)
4
- - attrs.each do |k, v|
5
- = "<i>#{k}:</i> #{v.blank? ? t('loggable.activity.deleted') : v}".html_safe
6
- br/
@@ -1,17 +0,0 @@
1
- <b class="text-secondary"><%= update_relation_class(update_attrs) %></b>
2
- <br>
3
- <% if update_attrs[:attrs] == :deleted %>
4
- <%= t('loggable.activity.deleted') %>
5
- <% else %>
6
- <% update_attrs[:attrs].each do |attr| %>
7
- <% attr.each do |key, from_to| %>
8
- <% next if from_to.nil? %>
9
- <i><%= key %></i>
10
- <br>
11
- <%= "from: #{from_to[:from].nil? ? 'Empty' : from_to[:from]}" %>
12
- <br>
13
- <%= "to: #{from_to[:to].nil? ? 'Empty' : from_to[:to]}" %>
14
- <br>
15
- <% end %>
16
- <% end %>
17
- <% end %>
@@ -1,14 +0,0 @@
1
- b.text-secondary = update_relation_class(update_attrs)
2
- br/
3
- - if update_attrs[:attrs] == :deleted
4
- = t('loggable.activity.deleted')
5
- - else
6
- - update_attrs[:attrs].each do |attr|
7
- - attr.each do |key, from_to|
8
- - next if from_to.nil?
9
- i = key
10
- br/
11
- = "from: #{from_to[:from].nil? ? "Empty" : from_to[:from]}"
12
- br/
13
- = "to: #{from_to[:to].nil? ? "Empty" : from_to[:to]}"
14
- br/
@@ -1,23 +0,0 @@
1
- <% updated_relations.each do |relation| %>
2
- <b class="text-secondary"><%= update_relation_class(relation) %></b>
3
- <br>
4
- <% if relation[:previous_attrs].present? %>
5
- <i>From:</i>
6
- <br>
7
- <%= render partial: 'loggable_activity/templates/shared/list_attrs', locals: { attrs: relation[:previous_attrs][:attrs] } %>
8
- <% else %>
9
- <i>From:</i>
10
- <br>
11
- Empty
12
- <br>
13
- <% end %>
14
- <% if relation[:current_attrs].present? %>
15
- <i>To:</i>
16
- <br>
17
- <%= render partial: 'loggable_activity/templates/shared/list_attrs', locals: { attrs: relation[:current_attrs][:attrs] } %>
18
- <% else %>
19
- <i>To:</i>
20
- <br>
21
- Empty
22
- <% end %>
23
- <% end %>
@@ -1,21 +0,0 @@
1
- - updated_relations.each do |relation|
2
- b.text-secondary = update_relation_class(relation)
3
- br/
4
- - if relation[:previous_attrs].present?
5
- i From:
6
- br/
7
- = render partial:'loggable_activity/templates/shared/list_attrs', locals: {attrs: relation[:previous_attrs][:attrs] }
8
- - else
9
- i From:
10
- br/
11
- |Empty
12
- br
13
- - if relation[:current_attrs].present?
14
- i To:
15
- br/
16
- = render partial: 'loggable_activity/templates/shared/list_attrs', locals: { attrs: relation[:current_attrs][:attrs] }
17
- - else
18
- i To:
19
- br/
20
- |Empty
21
-
@@ -1,153 +0,0 @@
1
- # frozen_string_literal: true
2
-
3
- module LoggableActivity
4
- # This module is responsible for building payloads used in loggable activities.
5
- module PayloadsBuilder
6
- # Builds payloads for the loggable activity.
7
- #
8
- # Example:
9
- # build_payloads
10
- #
11
- # Returns:
12
- # #<LoggableActivity::Payload:0x0000000109658718> {
13
- # :id => 129,
14
- # :record_type => "Demo::Club",
15
- # :record_id => 4,
16
- # :encrypted_attrs => {
17
- # "name" => "z/jigjcm3Fb89L7QT8XiNhvVgjtRXKkmg/xohR6wIc0=\n"
18
- # },
19
- # :payload_type => "current_association",
20
- # :data_owner => nil,
21
- # :activity_id => 50,
22
- # :created_at => Wed, 14 Feb 2024 13:21:13.964339000 UTC +00:00,
23
- # :updated_at => Wed, 14 Feb 2024 13:21:13.964339000 UTC +00:00
24
- # }
25
- #
26
- def build_payloads
27
- build_primary_payload
28
- self.class.relations.each do |relation_config|
29
- build_relation_payload(relation_config)
30
- end
31
- @payloads
32
- end
33
-
34
- private
35
-
36
- # Builds the primary payload.
37
- def build_primary_payload
38
- encrypted_attrs = encrypt_attrs(attributes, self.class.loggable_attrs, primary_encryption_key)
39
- @payloads << LoggableActivity::Payload.new(
40
- record: @record,
41
- payload_type: 'primary_payload',
42
- encrypted_attrs:,
43
- data_owner: true,
44
- route: self.class.route
45
- )
46
- end
47
-
48
- # Builds the payload for destroyed records.
49
- def build_destroy_payload
50
- encrypted_attrs = encrypt_attrs(attributes, self.class.loggable_attrs, primary_encryption_key)
51
- encrypted_attrs.transform_values! { '*** DELETED ***' }
52
- @payloads << LoggableActivity::Payload.new(
53
- record: @record,
54
- payload_type: 'primary_payload',
55
- encrypted_attrs:,
56
- data_owner: true,
57
- route: nil
58
- )
59
- end
60
-
61
- # Builds payloads for relations
62
- #
63
- # @param relation_config [Hash] The configuration of the relation.
64
- def build_relation_payload(relation_config)
65
- relation_config.each_key do |key|
66
- case key
67
- when 'belongs_to'
68
- build_payload(relation_config, 'belongs_to')
69
- when 'has_one'
70
- build_payload(relation_config, 'has_one')
71
- when 'has_many'
72
- build_has_many_payloads(relation_config, 'has_many')
73
- end
74
- end
75
- end
76
-
77
- # Builds the payload for a specific relation.
78
- #
79
- # @param relation_config [Hash] The configuration of the relation.
80
- # @param relation_type [String] The type of the relation.
81
- def build_payload(relation_config, relation_type)
82
- associated_record = send(relation_config[relation_type])
83
- return nil if associated_record.nil?
84
-
85
- build_associated_payload(associated_record, relation_config)
86
- end
87
-
88
- # Builds payloads for has_many relations.
89
- def build_has_many_payloads(relation_config, relation_type)
90
- associated_records = send(relation_config[relation_type])
91
- return nil if associated_records.empty?
92
-
93
- associated_records.each do |associated_record|
94
- build_associated_payload(associated_record, relation_config)
95
- end
96
- end
97
-
98
- # Builds the payload for an associated record.
99
- def build_associated_payload(associated_record, relation_config)
100
- associated_loggable_attrs = relation_config['loggable_attrs']
101
- encryption_key = associated_record_encryption_key(associated_record, relation_config['data_owner'])
102
- encrypted_attrs =
103
- encrypt_attrs(
104
- associated_record.attributes,
105
- associated_loggable_attrs,
106
- encryption_key.key
107
- )
108
-
109
- @payloads << LoggableActivity::Payload.new(
110
- record: associated_record,
111
- encrypted_attrs:,
112
- payload_type: 'current_association',
113
- data_owner: relation_config['data_owner'],
114
- route: relation_config['route']
115
- )
116
- end
117
-
118
- # Retrieves the encryption key for the associated record.
119
- #
120
- # @param associated_record [ActiveRecord::Base] The associated record.
121
- # @param data_owner [Boolean] Whether the associated record is the owner of the data.
122
- # @return [LoggableActivity::EncryptionKey] The encryption key for the associated record.
123
- def associated_record_encryption_key(associated_record, data_owner)
124
- if data_owner
125
- LoggableActivity::EncryptionKey.for_record(associated_record, LoggableActivity::EncryptionKey.for_record(self))
126
- else
127
- LoggableActivity::EncryptionKey.for_record(associated_record)
128
- end
129
- end
130
-
131
- # Encrypts attributes.
132
- #
133
- # @param attrs [Hash] The attributes to be encrypted.
134
- # @param loggable_attrs [Array<String>] The loggable attributes.
135
- # @param encryption_key [String] The encryption key.
136
- # @return [Hash] The encrypted attributes.
137
- def encrypt_attrs(attrs, loggable_attrs, encryption_key)
138
- attrs = attrs.slice(*loggable_attrs)
139
- encrypt_attr(attrs, encryption_key)
140
- end
141
-
142
- # Encrypts a single attribute.
143
- #
144
- # @param attrs [Hash] The attributes to be encrypted.
145
- # @param encryption_key [String] The encryption key.
146
- # @return [Hash] The encrypted attributes.
147
- def encrypt_attr(attrs, encryption_key)
148
- attrs.each do |key, value|
149
- attrs[key] = LoggableActivity::Encryption.encrypt(value, encryption_key)
150
- end
151
- end
152
- end
153
- end
@@ -1,127 +0,0 @@
1
- # frozen_string_literal: true
2
-
3
- module LoggableActivity
4
- # This module is responsible for building update payloads used in loggable activities.
5
- module UpdatePayloadsBuilder
6
- # Builds payloads for an activity update event.
7
- def build_update_payloads
8
- @update_payloads = []
9
-
10
- previous_values, current_values = primary_update_attrs
11
- build_primary_update_payload(previous_values, current_values)
12
-
13
- self.class.relations.each do |relation_config|
14
- build_update_relation_payloads(relation_config)
15
- end
16
- @update_payloads
17
- end
18
-
19
- private
20
-
21
- # Fetch the previous and current values of the primary record.
22
- def primary_update_attrs
23
- previous_values = saved_changes.transform_values(&:first)
24
- current_values = saved_changes.transform_values(&:last)
25
-
26
- [previous_values, current_values]
27
- end
28
-
29
- # Builds the primary update payload.
30
- def build_primary_update_payload(previous_values, current_values)
31
- return if previous_values == current_values
32
-
33
- encrypted_update_attrs = encrypted_update_attrs(previous_values, current_values)
34
- @update_payloads << LoggableActivity::Payload.new(
35
- record: @record,
36
- payload_type: 'update_payload',
37
- encrypted_attrs: encrypted_update_attrs,
38
- route: self.class.route
39
- )
40
- end
41
-
42
- # Returns the encrypted attributes for the update payload.
43
- def encrypted_update_attrs(previous_values, current_values)
44
- changes = []
45
- changed_attrs = previous_values.slice(*self.class.loggable_attrs)
46
- changed_attrs.each do |key, from_value|
47
- from = LoggableActivity::Encryption.encrypt(from_value, primary_encryption_key)
48
- to_value = current_values[key]
49
- to = LoggableActivity::Encryption.encrypt(to_value, primary_encryption_key)
50
- changes << { key => { from:, to: } }
51
- end
52
- { changes: }
53
- end
54
-
55
- # Builds update payloads for relations.
56
- def build_update_relation_payloads(relation_config)
57
- relation_config.each_key do |key|
58
- case key
59
- when 'belongs_to'
60
- build_relation_update_for_belongs_to(relation_config)
61
- when 'has_one'
62
- build_relation_update_for_has_one(relation_config)
63
- when 'has_many'
64
- build_relation_update_for_has_many(relation_config)
65
- end
66
- end
67
- end
68
-
69
- # Builds the update payload for a has_many relation.
70
- def build_relation_update_for_has_many(relation_config)
71
- # NOTE: This method is not implemented yet.
72
- # It requires that there is a form where it is possible to change
73
- # the related records. This is not implemented yet. in the Demo app
74
- # puts relation_config['has_many']
75
- end
76
-
77
- # Builds the update payload for a has_one relation.
78
- def build_relation_update_for_has_one(relation_config)
79
- # NOTE: This method is not implemented yet.
80
- # It requires that there is a form where it is possible to change
81
- # the related records. This is not implemented yet. in the Demo app
82
- # puts relation_config['has_one']
83
- end
84
-
85
- # Builds the update payload for a belongs_to relation.
86
- def build_relation_update_for_belongs_to(relation_config)
87
- relation_id = "#{relation_config['belongs_to']}_id"
88
- model_class_name = relation_config['model']
89
- model_class = model_class_name.constantize
90
-
91
- return unless saved_changes.include?(relation_id)
92
-
93
- relation_id_changes = saved_changes[relation_id]
94
- previous_relation_id, current_relation_id = relation_id_changes
95
-
96
- [previous_relation_id, current_relation_id].each_with_index do |id, index|
97
- relation_record = id ? model_class.find_by(id:) : nil
98
- next unless relation_record
99
-
100
- payload_type = index.zero? ? 'previous_association' : 'current_association'
101
- build_relation_update_payload(
102
- relation_config,
103
- relation_record,
104
- payload_type
105
- )
106
- end
107
- end
108
-
109
- # Builds the update payload for a relation.
110
- def build_relation_update_payload(relation_config, record, payload_type)
111
- encryption_key = LoggableActivity::EncryptionKey.for_record(record)&.key
112
- encrypted_attrs = relation_encrypted_attrs(record.attributes, relation_config['loggable_attrs'], encryption_key)
113
-
114
- @update_payloads << LoggableActivity::Payload.new(
115
- record:,
116
- encrypted_attrs:,
117
- payload_type:,
118
- route: relation_config['route']
119
- )
120
- end
121
-
122
- # Returns the encrypted attributes for a relation.
123
- def relation_encrypted_attrs(attrs, loggable_attrs, encryption_key)
124
- encrypt_attrs(attrs, loggable_attrs, encryption_key)
125
- end
126
- end
127
- end