readymade 0.2.1 → 0.2.3

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 7626ae0687a31a055b912eaa725f049317bc44c38f18ff51b060f71ac188afba
4
- data.tar.gz: 49de3d0d889bf1ab67e1f424f1c9421b47378e2f5ed10ce6c5cb3e261fcc1e92
3
+ metadata.gz: f26bb52b5176c6325c252ac67735fbd6f21f26ad194d0dbdc9e915e421421840
4
+ data.tar.gz: b0500fc448b0681c6e436ad2f22fd2f43d880542500042a7bb9853a69d58fdd0
5
5
  SHA512:
6
- metadata.gz: 8775ea40ef291da68cbd8e3527bfc5202a29b30a3664b80649070b288d29c92befb6e596ddcc5a81a8b8ef8af32db6f76302576f1a1a405b3fc2121bdbf54fc3
7
- data.tar.gz: 8cbcf0794b7ad7597f306cc885479afd61ee1eabb030770d2610f776218e2b005a1b3397e65064bdd00181aab1af8abe91c783575c1b29e54c6ba9296d212de4
6
+ metadata.gz: 93cde55d0896d28b379fa699846abed6e3d8e72d2dbae8f7027b2813cc4a5fa277d8b1c07f8d0fe1905890cbf0b2fa654caeed7a8b791ff4ada4ac995d0edfd9
7
+ data.tar.gz: b1928db06558f7d28c83cda0827f065f3e8278567647844ab9f768fdf70183b2b1126e6fc016cb93df0d36f258152713372c0f8ef899bfbb026b1d11e35c327f
data/CHANGELOG.md CHANGED
@@ -1,6 +1,12 @@
1
1
  Changelog
2
2
  All notable changes to this project will be documented in this file.
3
3
 
4
+ ## [0.2.3] - 2022-05-03
5
+
6
+ ### Features
7
+
8
+ * Add `Readymade::Model::ApiAttachable` - add base64 format to your ActiveStorage
9
+
4
10
  ## [0.2.1] - 2022-04-21
5
11
 
6
12
  ### Improvements
data/Gemfile.lock CHANGED
@@ -1,7 +1,7 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- readymade (0.2.1)
4
+ readymade (0.2.3)
5
5
 
6
6
  GEM
7
7
  remote: https://rubygems.org/
data/README.md CHANGED
@@ -1,4 +1,6 @@
1
- # Readymade 0.2.1
1
+ # Readymade
2
+
3
+ [![Gem Version](https://badge.fury.io/rb/readymade.png)](https://badge.fury.io/rb/readymade)
2
4
 
3
5
  This gems contains basic components to follow [ABDI architecture](https://github.com/OrestF/OrestF/blob/master/abdi/ABDI_architecture.md)
4
6
 
@@ -149,6 +151,49 @@ class Orders::Operations::Create < Readymade::Operation
149
151
  end
150
152
  ```
151
153
 
154
+ ### Readymade::Controller::Serialization
155
+
156
+ ```ruby
157
+ class MyController < ApplicationController
158
+ include Readymade::Controller::Serialization
159
+ end
160
+ ```
161
+
162
+ Serialization helpers for controllers.
163
+ Dependencies that must be installed on your own:
164
+ - [blueprinter](https://rubygems.org/gems/blueprinter/)
165
+ - [pagy](https://rubygems.org/gems/pagy)
166
+ - [api-pagination](https://rubygems.org/gems/api-pagination)
167
+
168
+ ### Readymade::Model::ApiAttachable
169
+
170
+ Add base64 attachments format for your models
171
+
172
+ ```ruby
173
+ class User < ApplicationRecord
174
+ has_one_attached :avatar
175
+ has_many_attached :images
176
+ include Readymade::Model::ApiAttachable
177
+ # must be included after has_one_attached, has_many_attached declaration
178
+ # api_file = {
179
+ # base64: 'iVBORw0KGgoAAA....',
180
+ # filename: 'my_avatar.png'
181
+ # }
182
+ # record.avatar = api_file 🎉
183
+ end
184
+ ```
185
+
186
+ copy [spec/support/api_attachable.rb](./spec/support/api_attachable.rb)
187
+ ```ruby
188
+ def to_api_file(file)
189
+ { base64: Base64.encode64(file.read), filename: file.original_filename }
190
+ end
191
+ ```
192
+ ```ruby
193
+ # rspec example
194
+ let(:avatar) { Rack::Test::UploadedFile.new(Rails.root.join('spec/support/assets/test-image.png'), 'image/png') }
195
+ let(:params) { { user: attributes_for(:user).merge!(avatar: to_api_file(avatar)) } }
196
+ ```
152
197
 
153
198
  ## Development
154
199
 
@@ -0,0 +1,61 @@
1
+ require 'active_support/concern'
2
+
3
+ module Readymade
4
+ module Model
5
+ module ApiAttachable
6
+ extend ActiveSupport::Concern
7
+ # must be included after has_one_attached, has_many_attached declaration
8
+ # api_file = {
9
+ # base64: 'iVBORw0KGgoAAA....',
10
+ # filename: 'my_avatar.png'
11
+ # }
12
+ # record.avatar = api_file 🎉
13
+
14
+ included do
15
+ has_one_attached_reflections.map(&:name).each do |attachment_method_name|
16
+ define_method("#{attachment_method_name}=") do |attachment_file|
17
+ attachment_file = api_attachment_to_uploaded(attachment_file) if api_attachable_format?(attachment_file)
18
+ super(attachment_file)
19
+ end
20
+ end
21
+
22
+ has_many_attached_reflections.map(&:name).each do |attachment_method_name|
23
+ define_method("#{attachment_method_name}=") do |attachment_file|
24
+ attachment_file = Array.wrap(attachment_file).map do |af|
25
+ api_attachment_to_uploaded(af) if api_attachable_format?(af)
26
+ end
27
+ super(attachment_file)
28
+ end
29
+ end
30
+ end
31
+
32
+ class_methods do
33
+ # rubocop:disable Naming/PredicateName
34
+ def has_one_attached_reflections
35
+ reflect_on_all_attachments.filter { |association| association.instance_of?(ActiveStorage::Reflection::HasOneAttachedReflection) }
36
+ end
37
+
38
+ def has_many_attached_reflections
39
+ reflect_on_all_attachments.filter { |association| association.instance_of?(ActiveStorage::Reflection::HasManyAttachedReflection) }
40
+ end
41
+ # rubocop:enable Naming/PredicateName
42
+ end
43
+
44
+ def api_attachable_format?(attachment_file)
45
+ attachment_file.respond_to?(:key?) && attachment_file.key?('base64') && attachment_file.key?('filename')
46
+ end
47
+
48
+ def api_attachment_to_uploaded(attachment_file)
49
+ ActionDispatch::Http::UploadedFile.new(
50
+ tempfile: Tempfile.new(attachment_file[:filename]).tap do |tf|
51
+ tf.binmode
52
+ tf.write(Base64.decode64(attachment_file[:base64]))
53
+ end,
54
+ filename: attachment_file[:filename],
55
+ type: Mime::Type.lookup_by_extension(File.extname(attachment_file[:filename])[1..]).to_s
56
+ )
57
+ end
58
+ end
59
+ end
60
+ end
61
+
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module Readymade
4
- VERSION = '0.2.1'
4
+ VERSION = '0.2.3'
5
5
  end
data/lib/readymade.rb CHANGED
@@ -1,5 +1,6 @@
1
1
  # frozen_string_literal: true
2
2
 
3
+ require 'readymade/model/api_attachable'
3
4
  require 'readymade/controller/serialization'
4
5
  require 'readymade/action'
5
6
  require 'readymade/form'
data/readymade.gemspec CHANGED
@@ -25,6 +25,7 @@ Gem::Specification.new do |spec|
25
25
  spec.files = Dir.chdir(File.expand_path(__dir__)) do
26
26
  `git ls-files -z`.split("\x0").reject { |f| f.match(%r{^(test|spec|features)/}) }
27
27
  end
28
+ spec.files << 'lib/readymade/model/api_attachable.rb'
28
29
  spec.files << 'lib/readymade/controller/serialization.rb'
29
30
  spec.bindir = 'exe'
30
31
  spec.executables = spec.files.grep(%r{^exe/}) { |f| File.basename(f) }
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: readymade
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.2.1
4
+ version: 0.2.3
5
5
  platform: ruby
6
6
  authors:
7
7
  - OrestF
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2022-04-21 00:00:00.000000000 Z
11
+ date: 2022-05-03 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: byebug
@@ -76,6 +76,7 @@ files:
76
76
  - lib/readymade/controller/serialization.rb
77
77
  - lib/readymade/form.rb
78
78
  - lib/readymade/instant_form.rb
79
+ - lib/readymade/model/api_attachable.rb
79
80
  - lib/readymade/operation.rb
80
81
  - lib/readymade/response.rb
81
82
  - lib/readymade/version.rb