render_turbo_stream 0.1.9 → 0.1.11

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: b699433559bcb2f6c79f10a8df305584db96042dd43de7999eb17b00cf87ffc9
4
- data.tar.gz: 3c85d56f2991b7bb8676b2864caee8eb20c271161fc38d4c378d206838007648
3
+ metadata.gz: fbc78913dcbad95c4f8de2b0188ab6eff2db1ac2390590a491427af071f2fa55
4
+ data.tar.gz: c2d381f27a631862490811f5c140f91245370ad3b1b82e3ba41771707adae732
5
5
  SHA512:
6
- metadata.gz: 243377679364d09d0c3ced284dbdcbc72be83dc0f16d18f8d54f0c2f8c71c6e2d9b613cab3e493a6a4f8454fcfa29a837da5ffc624b5c77b3399e1fa3a2cdae3
7
- data.tar.gz: ed18eee7081e7ebc1ea98fd4159d0876a1edee0116c34e4dd18362c214834dc8e37fca5af3b411f6f0bac33e86606f5f5dda6b537d3cbf529db87dafb3bdf180
6
+ metadata.gz: 5873014fd22b2b1d4d2ded650f37bdc5f6e865ada01608c82ad2c891199c1e342bb6e7a4d94319c6e92c0cfea196fb19230cdebc931915fb2b2e420cc3ab1653
7
+ data.tar.gz: 854105573f8b7a5b8f34ac031d93c4e0a01eb2f5b4263a1495cfac17d53a391431c0ec5a339a5666e4ec8340d029218c2914501fba1a65869508185661d0eab9
data/README.md CHANGED
@@ -1,14 +1,14 @@
1
1
  # RenderTurboStream
2
2
 
3
- Creating a gem currently is not possible because of [rails issue](https://github.com/rails/rails/issues/47954)
3
+ The machine gun for your turbo-stream partials.
4
4
 
5
- So, applying this idea is currently only possible by copy and paste a method and a view, see below.
5
+ Creating a gem from this is in work, see [rails issue](https://github.com/rails/rails/issues/47954)
6
6
 
7
- Working consistently by turbo_stream means: shooting a lot of partials to the html which always needs the same attributes: ID, partial and maybe some locals. This gem is a attempt to serialize that, especially for `update` and `create` action.
7
+ Defining templates like `update.turbo_stream.haml` annoyed me.
8
8
 
9
- Logic is better placed inside the controller, instead of the view and it's boring to write always the same `ifs` inside the `update.turbo_stream.haml`. So this gem holds a `.turbo_stream.html.erb` view that loops through all the partials that should be rendered.
9
+ Working consistently by turbo_stream means: shooting many partials to the frontend which always needs the same attributes: ID, partial and maybe some locals. This gem serializes that: Partials can be steered directly from the controller.
10
10
 
11
- In 90% of cases you have just define your partials, like `_form.haml` and steer them from the controller directly, without a `.turbo_stream.haml` view.
11
+ Currently it is only possible by copy and paste the code, see below.
12
12
 
13
13
  ## Installation
14
14
 
@@ -24,36 +24,74 @@ The corresponding partials for flashes could look [like this](https://gitlab.com
24
24
 
25
25
  ## Usage
26
26
 
27
+ `turbo_stream_save` is a special method for streamline `update` or `create` functions for `turbo_stream`, which could look like so:
28
+
27
29
  ```ruby
28
30
  def create
29
31
  @customer = Customer.new(customer_params)
30
32
 
31
- render_turbo_stream(
33
+ turbo_stream_save(
32
34
  @customer.save,
33
- redirect_on_success_to: edit_customer_path(@customer),
34
- id: 'customer-form-wrapper',
35
- partial: 'customer_form',
35
+ redirect_on_success_to: edit_customer_path(@customer)
36
36
  )
37
37
 
38
38
  end
39
39
  ```
40
40
 
41
- and its done!
41
+ This sets a status, generates a flash message and performs `stream_partials`, which could result like that:
42
+
43
+ ```ruby
44
+ stream_partials(
45
+ [
46
+ {
47
+ id: 'form',
48
+ partial: 'form'
49
+ },
50
+ {
51
+ id: 'flash-wrapper',
52
+ partial: 'layouts/flashes',
53
+ action: :prepend
54
+ }
55
+ ]
56
+ )
57
+ ```
42
58
 
43
- in 90% use cases it should be enough and not necessary writing any code inside `update.turbo_stream.haml` or `create.turbo_stream.haml`
59
+ The `stream_partial` method is nothing else than a singular of `stream_partials`
60
+
61
+ ```ruby
62
+ stream_partial(
63
+ id,
64
+ partial: nil, #=> default: id.gsub('-','_')
65
+ locals: {},
66
+ action: nil #=> default: :replace
67
+ )
68
+ ```
44
69
 
45
70
  ## Testing
46
71
 
47
- Testing by regular `rspec` request specs the controller is rendering classic html templates, not turbo_stream. For that html templates are rendered, but only with hints so that your test can check which action is done.
72
+ For system testing you need capybara.
48
73
 
49
- It has 3 cases of output with its resulting status codes which can be checked by rspec:
74
+ For enabling request specs:
75
+ If `request.format` is not `turbo_stream` the method responds as `json` with status:
50
76
 
51
77
  Success and redirection: `302`
52
-
53
78
  Success without redirection: `200`
54
-
55
79
  Save Action failed: `422` `:unprocessable_entity`
56
80
 
81
+ Testing the `response.body` by rspec could look like this:
82
+
83
+ ```ruby
84
+ it 'update failed' do
85
+ a = FactoryBot.create(:article)
86
+ patch article_path(a, params: invalid_params)
87
+ expect(response.status).to eq(422)
88
+ h = JSON.parse(response.body)
89
+ expect(h['form']['partial']).to eq('articles/form')
90
+ expect(h['flash-box']['partial']).to eq('layouts/flash')
91
+ expect(h.keys.length).to eq(2)
92
+ end
93
+ ```
94
+
57
95
  ## Parameters
58
96
 
59
97
  `save_action` (first parameter, boolean) true if successful
@@ -84,7 +122,7 @@ Save Action failed: `422` `:unprocessable_entity`
84
122
 
85
123
  gem `turbo_power` (is included, used for redirection)
86
124
 
87
- **Translations used**
125
+ **Translations**
88
126
 
89
127
  `activerecord.success.successfully_created`
90
128
 
@@ -94,6 +132,8 @@ gem `turbo_power` (is included, used for redirection)
94
132
 
95
133
  `activerecord.errors.messages.could_not_update`
96
134
 
135
+ example value: `"%<model_name>s successfully created"`
136
+
97
137
  .. and Model Name Translations
98
138
 
99
139
  **Flash configuration**
@@ -0,0 +1,4 @@
1
+ module RenderTurboStream
2
+ class ApplicationController < ActionController::Base
3
+ end
4
+ end
@@ -0,0 +1,52 @@
1
+ <% error = false %>
2
+ <% control = [] %>
3
+ <% local_assigns[:streams].each do |s| %>
4
+ <% ctl = { partial: s[:partial], id: s[:id] } %>
5
+ <% info = { id: s[:id], partial: s[:partial], locals: s[:locals] } %>
6
+
7
+ <% if !s[:id] %>
8
+ <% Rails.logger.error(" ERROR RENDER TURBO STREAM => MISSING ID => #{s}") %>
9
+ <% error = true %>
10
+
11
+ <% elsif !s[:partial].present? %>
12
+ <% Rails.logger.error(" ERROR RENDER TURBO STREAM => MISSING PARTIAL => #{s}") %>
13
+ <% error = true %>
14
+ <% ctl[:partial] = nil %>
15
+
16
+ <% elsif s[:action].to_sym == :replace %>
17
+ <% ctl[:action] = :replace %>
18
+ <% Rails.logger.debug(" • render-turbo-stream REPLACE => #{info}") %>
19
+ <%= turbo_stream.replace s[:id] do %>
20
+ <%= render s[:partial], locals: s[:locals] %>
21
+ <% end %>
22
+
23
+ <% elsif s[:action].to_sym == :prepend %>
24
+ <% ctl[:action] = :prepend %>
25
+ <% Rails.logger.debug(" • render-turbo-stream PREPEND => #{info}") %>
26
+ <%= turbo_stream.prepend s[:id] do %>
27
+ <%= render s[:partial], locals: s[:locals] %>
28
+ <% end %>
29
+
30
+ <% elsif s[:action].to_sym == :append %>
31
+ <% ctl[:action] = :append %>
32
+ <% Rails.logger.debug(" • render-turbo-stream APPEND => #{info}") %>
33
+ <%= turbo_stream.prepend s[:id] do %>
34
+ <%= render s[:partial], locals: s[:locals] %>
35
+ <% end %>
36
+
37
+ <% else %>
38
+ <% ctl[:action] = :UNKNOWN %>
39
+ <% Rails.logger.fatal(" ERROR render-turbo-stream => UNKNOWN ACTION => #{s}") %>
40
+ <% error = true %>
41
+ <% end %>
42
+
43
+ <% control.push(ctl) %>
44
+
45
+ <% end %>
46
+
47
+ <% if error %>
48
+ <% Rails.logger.error(" RENDER TURBO STREAM HAD ERRORS, REPEATING WHOLE ARRAY: ") %>
49
+ <% control.each do |c| %>
50
+ <% Rails.logger.error(" #{c}") %>
51
+ <% end %>
52
+ <% end %>
@@ -0,0 +1 @@
1
+ <%= turbo_stream.redirect_to local_assigns[:url] %>
@@ -0,0 +1,5 @@
1
+ module RenderTurboStream
2
+ class Engine < ::Rails::Engine
3
+ isolate_namespace RenderTurboStream
4
+ end
5
+ end
@@ -1,3 +1,3 @@
1
1
  module RenderTurboStream
2
- VERSION = "0.1.9"
2
+ VERSION = "0.1.11"
3
3
  end
@@ -1,12 +1,162 @@
1
1
  require "render_turbo_stream/version"
2
2
  require "render_turbo_stream/railtie"
3
+ require 'render_turbo_stream/engine'
3
4
 
4
5
  module RenderTurboStream
5
- # Your code goes here...
6
- def testmethod
7
- render template: 'layouts/render', layout: false
8
- respond_to do |format|
9
- format.turbo_stream { render template: 'layouts/render', layout: false }
6
+
7
+ def turbo_stream_save(
8
+ save_action,
9
+ redirect_on_success_to: nil,
10
+ object: nil,
11
+ id: 'form', # if nil: no partial is rendered
12
+ partial: nil, # default: same like ID
13
+ action: 'replace',
14
+ locals: {},
15
+ streams_on_success: [
16
+ {
17
+ id: nil,
18
+ partial: 'form',
19
+ locals: {},
20
+ action: 'replace'
21
+ }
22
+ ],
23
+ streams_on_error: [
24
+ {
25
+ id: nil,
26
+ partial: 'form',
27
+ locals: {},
28
+ action: 'replace'
29
+ }
30
+ ],
31
+ add_flash_alerts: [], #=> array of strings
32
+ add_flash_notices: [], #=> array of strings
33
+ flashes_on_success: [], #=> array of strings
34
+ flashes_on_error: [] #=> array of strings
35
+ )
36
+
37
+ unless object
38
+ object = eval("@#{controller_name.classify.underscore}")
39
+ end
40
+
41
+ #== Streams / Partials
42
+
43
+ streams = [(id ? { id: id, partial: partial, locals: locals, action: action } : nil)]
44
+
45
+ if save_action
46
+ response.status = 200
47
+ streams += streams_on_success.select { |s| s[:id].present? }
48
+ else
49
+ response.status = :unprocessable_entity
50
+ streams += streams_on_error.select { |s| s[:id].present? }
51
+ end
52
+
53
+ #== FLASHES
54
+
55
+ model_name = object.model_name.human
56
+ if save_action
57
+ flash_notices = if flashes_on_success.present?
58
+ flashes_on_success
59
+ elsif action_name == 'create'
60
+ [format(I18n.t('activerecord.success.successfully_created'), model_name: model_name)]
61
+ elsif action_name == 'update'
62
+ [format(I18n.t('activerecord.success.successfully_updated'), model_name: model_name)]
63
+ end
64
+ flash_alerts = []
65
+ else
66
+ flash_alerts = if flashes_on_error.present?
67
+ flashes_on_error
68
+ elsif action_name == 'create'
69
+ [format(I18n.t('activerecord.errors.messages.could_not_create'), model_name: model_name)]
70
+ elsif action_name == 'update'
71
+ [format(I18n.t('activerecord.errors.messages.could_not_update'), model_name: model_name)]
72
+ end
73
+ flash_notices = []
74
+ end
75
+ flash_notices += add_flash_notices
76
+ flash_alerts += add_flash_alerts
77
+ _flash_id = Rails.configuration.x.render_turbo_stream.flash_id
78
+ flash_id = (_flash_id ? _flash_id : "ERROR, MISSING CONFIG => config.x.render_turbo_stream.flash_id")
79
+ flash_partial = Rails.configuration.x.render_turbo_stream.flash_partial
80
+ flash_action = Rails.configuration.x.render_turbo_stream.flash_action
81
+ flash_notices.each do |notice|
82
+ # inside the flash partial has to be a loop that handles all theese flashes
83
+ flash_stream = {
84
+ id: flash_id,
85
+ partial: flash_partial,
86
+ action: flash_action,
87
+ locals: { success: true, message: notice }
88
+ }
89
+ streams.push(flash_stream)
90
+ end
91
+ flash_alerts.each do |alert|
92
+ # inside the flash partial has to be a loop that handles all theese flashes
93
+ flash_stream = {
94
+ id: flash_id,
95
+ partial: flash_partial,
96
+ action: flash_action,
97
+ locals: { success: false, message: alert }
98
+ }
99
+ streams.push(flash_stream)
10
100
  end
101
+
102
+ #== render
103
+
104
+ if save_action && redirect_on_success_to.present?
105
+ response.status = 302
106
+ flash[:alert] = flash_alerts
107
+ flash[:notice] = flash_notices
108
+ if request.format.to_sym == :turbo_stream
109
+ render template: 'render_turbo_stream_redirect', locals: { url: redirect_on_success_to }, layout: false
110
+ else
111
+ render json: { redirected_to: redirect_on_success_to }
112
+ end
113
+ else
114
+ flash.now[:alert] = flash_alerts
115
+ flash.now[:notice] = flash_notices
116
+ stream_partials(streams)
117
+ end
118
+ end
119
+
120
+ def stream_partials(array)
121
+
122
+ ary = []
123
+ array.dup.each do |props|
124
+ part = (props[:partial].present? ? props[:partial] : props[:id]).gsub('-', '_')
125
+ partial = (part.to_s.include?('/') ? part : [controller_path, part].join('/'))
126
+ r = props
127
+ r[:action] = (props[:action].present? ? props[:action] : :replace)
128
+ r[:partial] = partial
129
+ ary.push(r)
130
+ end
131
+
132
+ if request.format.to_sym == :turbo_stream
133
+ render template: 'render_turbo_stream_partials', locals: { streams: ary }, layout: false
134
+ else
135
+ check = {}
136
+ ary.each do |a|
137
+ b = a.dup
138
+ b.delete(:id)
139
+ check[a[:id]] = b
140
+ end
141
+ render json: check
142
+ end
143
+ end
144
+
145
+ def stream_partial(
146
+ id,
147
+ partial: nil, #=> default: id
148
+ action: :replace,
149
+ locals: {}
150
+ )
151
+ stream_partials(
152
+ [
153
+ {
154
+ id: id,
155
+ partial: partial,
156
+ action: action,
157
+ locals: locals
158
+ }
159
+ ]
160
+ )
11
161
  end
12
162
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: render_turbo_stream
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.9
4
+ version: 0.1.11
5
5
  platform: ruby
6
6
  authors:
7
7
  - christian
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2023-04-15 00:00:00.000000000 Z
11
+ date: 2023-04-17 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: rails
@@ -24,7 +24,7 @@ dependencies:
24
24
  - - ">="
25
25
  - !ruby/object:Gem::Version
26
26
  version: 7.0.4.3
27
- description: 'NOT USABLE AS GEM see: Homepage / README'
27
+ description: Coming soon
28
28
  email:
29
29
  - christian@sedlmair.ch
30
30
  executables: []
@@ -33,7 +33,11 @@ extra_rdoc_files: []
33
33
  files:
34
34
  - README.md
35
35
  - Rakefile
36
+ - app/controllers/render_turbo_stream/application_controller.rb
37
+ - app/views/render_turbo_stream_partials.turbo_stream.erb
38
+ - app/views/render_turbo_stream_redirect.turbo_stream.erb
36
39
  - lib/render_turbo_stream.rb
40
+ - lib/render_turbo_stream/engine.rb
37
41
  - lib/render_turbo_stream/railtie.rb
38
42
  - lib/render_turbo_stream/version.rb
39
43
  - lib/tasks/render_turbo_stream_tasks.rake
@@ -62,5 +66,5 @@ requirements: []
62
66
  rubygems_version: 3.4.12
63
67
  signing_key:
64
68
  specification_version: 4
65
- summary: 'NOT USABLE AS GEM see: Homepage / README'
69
+ summary: Coming soon
66
70
  test_files: []