From 8c82ff290b23757cbf44ea9388bf0417c52199af Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Javi=20Mart=C3=ADn?= Date: Wed, 28 Jul 2021 00:25:02 +0200 Subject: [PATCH] Handle CKEditor attachments with Active Storage The code is based on what's generated using CKEditor's code generator. We're doing one minor change to the `Ckeditor::Backend::ActiveStorage` module; we're assigning the data in a `before_validation` instead of a `before_save` callback. Validations with `file_validations` didn't work otherwise; it looks like this backend was written with `active_storage_validations` in mind [1]. Note we don't need to update the `name` column in the attachments table because, when using Active Storage, CKEditor uses both `data` (as attribute accessor) and `storage_data` (as attachment attribute). [1] https://github.com/galetahub/ckeditor/blob/f9e48420ccb6dc/lib/generators/ckeditor/templates/active_record/active_storage/ckeditor/picture.rb#L4 --- app/models/ckeditor/asset.rb | 1 - app/models/ckeditor/picture.rb | 24 +++++++----------------- lib/ckeditor/backend/active_storage.rb | 22 ++++++++-------------- 3 files changed, 15 insertions(+), 32 deletions(-) diff --git a/app/models/ckeditor/asset.rb b/app/models/ckeditor/asset.rb index 494d4fc76..ead24ea61 100644 --- a/app/models/ckeditor/asset.rb +++ b/app/models/ckeditor/asset.rb @@ -1,5 +1,4 @@ class Ckeditor::Asset < ApplicationRecord include Ckeditor::Orm::ActiveRecord::AssetBase include Ckeditor::Backend::ActiveStorage - include Ckeditor::Backend::Paperclip end diff --git a/app/models/ckeditor/picture.rb b/app/models/ckeditor/picture.rb index 8b0846143..eae6dd9de 100644 --- a/app/models/ckeditor/picture.rb +++ b/app/models/ckeditor/picture.rb @@ -1,24 +1,14 @@ class Ckeditor::Picture < Ckeditor::Asset - include HasAttachment + attr_accessor :data + has_one_attached :storage_data - has_attachment :data, - url: "/ckeditor_assets/pictures/:id/:style_:basename.:extension", - path: ":rails_root/public/ckeditor_assets/pictures/:id/:style_:basename.:extension", - styles: { content: "800>", thumb: "118x100#" } - - do_not_validate_attachment_file_type :data - validate :attachment_presence - validates :data, file_content_type: { allow: /^image\/.*/ }, file_size: { less_than: 2.megabytes } + validates :storage_data, file_content_type: { allow: /^image\/.*/ }, file_size: { less_than: 2.megabytes } def url_content - url(:content) + rails_representation_url(storage_data.variant(resize: "800>").processed, only_path: true) end - private - - def attachment_presence - unless data.present? - errors.add(:data, I18n.t("errors.messages.blank")) - end - end + def url_thumb + rails_representation_url(storage_data.variant(resize: "118x100").processed, only_path: true) + end end diff --git a/lib/ckeditor/backend/active_storage.rb b/lib/ckeditor/backend/active_storage.rb index 7ce8aa611..8ff442443 100644 --- a/lib/ckeditor/backend/active_storage.rb +++ b/lib/ckeditor/backend/active_storage.rb @@ -14,9 +14,9 @@ module Ckeditor module ClassMethods def self.extended(base) base.class_eval do - before_save :apply_data + before_validation :apply_data validate do - if data.nil? || storage_file.nil? + if data.nil? || file.nil? errors.add(:data, :not_data_present, message: "data must be present") end end @@ -46,25 +46,19 @@ module Ckeditor protected - def storage_file - @storage_file ||= storage_data + def file + @file ||= storage_data end def blob - @blob ||= ::ActiveStorage::Blob.find(storage_file.attachment.blob_id) + @blob ||= ::ActiveStorage::Blob.find(file.attachment.blob_id) end def apply_data - non_paperclip_data = if data.is_a?(::Paperclip::Attachment) - file.instance_variable_get("@target") - else - data - end - - if non_paperclip_data.is_a?(Ckeditor::Http::QqFile) - storage_data.attach(io: non_paperclip_data, filename: non_paperclip_data.original_filename) + if data.is_a?(Ckeditor::Http::QqFile) + storage_data.attach(io: data, filename: data.original_filename) else - storage_data.attach(non_paperclip_data) + storage_data.attach(data) end self.data_file_name = storage_data.blob.filename