refactor(operation_log): store data in jsonb instead of files
This commit is contained in:
parent
e4bf1bd2db
commit
c0fd080d0e
4 changed files with 50 additions and 20 deletions
|
@ -765,8 +765,8 @@ class Dossier < ApplicationRecord
|
|||
def expired_keep_track_and_destroy!
|
||||
transaction do
|
||||
DeletedDossier.create_from_dossier(self, :expired)
|
||||
dossier_operation_logs.destroy_all
|
||||
log_automatic_dossier_operation(:supprimer, self)
|
||||
dossier_operation_logs.purge_discarded
|
||||
destroy!
|
||||
end
|
||||
true
|
||||
|
@ -1164,7 +1164,7 @@ class Dossier < ApplicationRecord
|
|||
def purge_discarded
|
||||
transaction do
|
||||
DeletedDossier.create_from_dossier(self, hidden_by_reason)
|
||||
dossier_operation_logs.not_deletion.destroy_all
|
||||
dossier_operation_logs.purge_discarded
|
||||
destroy
|
||||
end
|
||||
end
|
||||
|
|
|
@ -37,10 +37,29 @@ class DossierOperationLog < ApplicationRecord
|
|||
belongs_to :bill_signature, optional: true
|
||||
|
||||
scope :not_deletion, -> { where.not(operation: operations.fetch(:supprimer)) }
|
||||
scope :with_data, -> { where.not(data: nil) }
|
||||
scope :brouillon_expired, -> { where(dossier: Dossier.brouillon_expired).not_deletion }
|
||||
scope :en_construction_expired, -> { where(dossier: Dossier.en_construction_expired).not_deletion }
|
||||
scope :termine_expired, -> { where(dossier: Dossier.termine_expired).not_deletion }
|
||||
|
||||
def move_to_cold_storage!
|
||||
if data.present?
|
||||
serialized.attach(
|
||||
io: StringIO.new(data.to_json),
|
||||
filename: "operation-#{digest}.json",
|
||||
content_type: 'application/json',
|
||||
# we don't want to run virus scanner on this file
|
||||
metadata: { virus_scan_result: ActiveStorage::VirusScanner::SAFE }
|
||||
)
|
||||
update!(data: nil)
|
||||
end
|
||||
end
|
||||
|
||||
def self.purge_discarded
|
||||
not_deletion.destroy_all
|
||||
with_data.each(&:move_to_cold_storage!)
|
||||
end
|
||||
|
||||
def self.create_and_serialize(params)
|
||||
dossier = params.fetch(:dossier)
|
||||
|
||||
|
@ -59,24 +78,17 @@ class DossierOperationLog < ApplicationRecord
|
|||
executed_at: Time.zone.now,
|
||||
automatic_operation: !!params[:automatic_operation])
|
||||
|
||||
serialized = {
|
||||
data = {
|
||||
operation: operation_log.operation,
|
||||
dossier_id: operation_log.dossier_id,
|
||||
author: self.serialize_author(params[:author]),
|
||||
subject: self.serialize_subject(params[:subject], operation_log.operation),
|
||||
automatic_operation: operation_log.automatic_operation?,
|
||||
executed_at: operation_log.executed_at.iso8601
|
||||
}.compact.to_json
|
||||
}.compact
|
||||
|
||||
operation_log.digest = Digest::SHA256.hexdigest(serialized)
|
||||
|
||||
operation_log.serialized.attach(
|
||||
io: StringIO.new(serialized),
|
||||
filename: "operation-#{operation_log.digest}.json",
|
||||
content_type: 'application/json',
|
||||
# we don't want to run virus scanner on this file
|
||||
metadata: { virus_scan_result: ActiveStorage::VirusScanner::SAFE }
|
||||
)
|
||||
operation_log.data = data
|
||||
operation_log.digest = Digest::SHA256.hexdigest(data.to_json)
|
||||
|
||||
operation_log.save!
|
||||
end
|
||||
|
|
|
@ -201,14 +201,21 @@ class PiecesJustificativesService
|
|||
|
||||
def self.operation_logs_and_signature_ids(dossiers)
|
||||
dol_id_dossier_id_bill_id = DossierOperationLog
|
||||
.where(dossier: dossiers, data: nil)
|
||||
.pluck(:bill_signature_id, :id, :dossier_id)
|
||||
dol_id_data_bill_id = DossierOperationLog
|
||||
.where(dossier: dossiers)
|
||||
.pluck(:id, :dossier_id, :bill_signature_id)
|
||||
.with_data
|
||||
.pluck(:bill_signature_id, :id, :dossier_id, :data, :digest, :created_at)
|
||||
|
||||
dol_id_dossier_id = dol_id_dossier_id_bill_id
|
||||
.map { |dol_id, dossier_id, _| [dol_id, dossier_id] }
|
||||
.map { |_, dol_id, dossier_id| [dol_id, dossier_id] }
|
||||
.to_h
|
||||
|
||||
bill_ids = dol_id_dossier_id_bill_id.map(&:third).uniq.compact
|
||||
bill_ids = (dol_id_dossier_id_bill_id + dol_id_data_bill_id)
|
||||
.map(&:first)
|
||||
.uniq
|
||||
.compact
|
||||
|
||||
serialized_dols = ActiveStorage::Attachment
|
||||
.includes(:blob)
|
||||
|
@ -217,6 +224,17 @@ class PiecesJustificativesService
|
|||
dossier_id = dol_id_dossier_id[a.record_id]
|
||||
ActiveStorage::DownloadableFile.pj_and_path(dossier_id, a)
|
||||
end
|
||||
serialized_dols += dol_id_data_bill_id.map do |_, id, dossier_id, data, digest, created_at|
|
||||
a = ActiveStorage::FakeAttachment.new(
|
||||
file: StringIO.new(data.to_json),
|
||||
filename: "operation-#{digest}.json",
|
||||
name: 'serialized',
|
||||
id: id,
|
||||
created_at: created_at,
|
||||
record_type: 'DossierOperationLog'
|
||||
)
|
||||
ActiveStorage::DownloadableFile.pj_and_path(dossier_id, a)
|
||||
end
|
||||
|
||||
[serialized_dols, bill_ids]
|
||||
end
|
||||
|
|
|
@ -1043,7 +1043,7 @@ describe Dossier do
|
|||
describe '#accepter!' do
|
||||
let(:dossier) { create(:dossier, :en_instruction, :with_individual) }
|
||||
let(:last_operation) { dossier.dossier_operation_logs.last }
|
||||
let(:operation_serialized) { JSON.parse(last_operation.serialized.download) }
|
||||
let(:operation_serialized) { last_operation.data }
|
||||
let!(:instructeur) { create(:instructeur) }
|
||||
let!(:now) { Time.zone.parse('01/01/2100') }
|
||||
let(:attestation) { Attestation.new }
|
||||
|
@ -1105,7 +1105,7 @@ describe Dossier do
|
|||
describe '#passer_en_instruction!' do
|
||||
let(:dossier) { create(:dossier, :en_construction, en_construction_close_to_expiration_notice_sent_at: Time.zone.now) }
|
||||
let(:last_operation) { dossier.dossier_operation_logs.last }
|
||||
let(:operation_serialized) { JSON.parse(last_operation.serialized.download) }
|
||||
let(:operation_serialized) { last_operation.data }
|
||||
let(:instructeur) { create(:instructeur) }
|
||||
|
||||
before { dossier.passer_en_instruction!(instructeur: instructeur) }
|
||||
|
@ -1123,7 +1123,7 @@ describe Dossier do
|
|||
describe '#passer_automatiquement_en_instruction!' do
|
||||
let(:dossier) { create(:dossier, :en_construction, en_construction_close_to_expiration_notice_sent_at: Time.zone.now) }
|
||||
let(:last_operation) { dossier.dossier_operation_logs.last }
|
||||
let(:operation_serialized) { JSON.parse(last_operation.serialized.download) }
|
||||
let(:operation_serialized) { last_operation.data }
|
||||
let(:instructeur) { create(:instructeur) }
|
||||
|
||||
before { dossier.passer_automatiquement_en_instruction! }
|
||||
|
@ -1300,7 +1300,7 @@ describe Dossier do
|
|||
it { expect(dossier.attestation).to be_nil }
|
||||
it { expect(dossier.termine_close_to_expiration_notice_sent_at).to be_nil }
|
||||
it { expect(last_operation.operation).to eq('repasser_en_instruction') }
|
||||
it { expect(JSON.parse(last_operation.serialized.download)['author']['email']).to eq(instructeur.email) }
|
||||
it { expect(last_operation.data['author']['email']).to eq(instructeur.email) }
|
||||
it { expect(DossierMailer).to have_received(:notify_revert_to_instruction).with(dossier) }
|
||||
|
||||
after { Timecop.return }
|
||||
|
|
Loading…
Reference in a new issue