cable_ready 1.1.0 → 2.0.0

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
  SHA1:
3
- metadata.gz: 4af592b2c92fa517e06a99e0f7c352be90c65ca7
4
- data.tar.gz: 6f471df22a630daed758c14b8a141dfc4584a3bc
3
+ metadata.gz: eb33a9f637a13e5bd1e3ba0f4c3e055374eca77c
4
+ data.tar.gz: 3e0c94b32558dc2c2681a781ead7ce7981b9199b
5
5
  SHA512:
6
- metadata.gz: e33789c536e4d878808de59eac1db026224bb0c61eb948d3adc13ff93f0768ed3adc7f0dd971c51f13b82765c5e1bbb443e5f0b8c311b543d6f092b7109b814d
7
- data.tar.gz: 005ce8accba916cf3e297d5262c4e51c1ddd1eba242a8e189c4548055c68492b977c4640046d8aaa66bef40522101a3af16496c006dffd8c85ab84eef4912aef
6
+ metadata.gz: 65766bf66feb0e160540d56da5a959f29ce3a0da2105fa987ba665a0d14502ffc3a33cd88d9d4e63dccaff471f70686d6aeb0739fa8b99637453a3eba0a8828d
7
+ data.tar.gz: aa229c109604d6b21cc64666ee8a13bcfe66157e49467e82f296fc3aedb5dc4f701560c49ce52404ef934437e06054c8e2aeeb3c12c07ecdf515e6c16d6cb343
data/Gemfile.lock CHANGED
@@ -1,7 +1,7 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- cable_ready (1.1.0)
4
+ cable_ready (2.0.0)
5
5
  activesupport (>= 5.0.0)
6
6
 
7
7
  GEM
data/README.md CHANGED
@@ -1,16 +1,65 @@
1
- [![Lines of Code](http://img.shields.io/badge/lines_of_code-98-brightgreen.svg?style=flat)](http://blog.codinghorror.com/the-best-code-is-no-code-at-all/)
1
+ [![Lines of Code](http://img.shields.io/badge/lines_of_code-112-brightgreen.svg?style=flat)](http://blog.codinghorror.com/the-best-code-is-no-code-at-all/)
2
2
  [![Code Status](http://img.shields.io/codeclimate/github/hopsoft/cable_ready.svg?style=flat)](https://codeclimate.com/github/hopsoft/cable_ready)
3
3
  [![Dependency Status](http://img.shields.io/gemnasium/hopsoft/cable_ready.svg?style=flat)](https://gemnasium.com/hopsoft/cable_ready)
4
4
 
5
5
  # CableReady
6
6
 
7
+ ## Server Rendered SPAs :joy:
8
+
7
9
  CableReady provides a standard interface for invoking common client-side DOM operations
8
10
  from the server via [ActionCable](http://guides.rubyonrails.org/action_cable_overview.html).
9
11
 
10
- Learn more about CableReady by reading through & running the [CableReady Test](https://github.com/hopsoft/cable_ready_test) project.
12
+ For a deeper dive into CableReady check out the [TodoMVC CableReady project](https://github.com/hopsoft/todomvc-cableready).
13
+
14
+ ## Quick Start
15
+
16
+ > Please read the official [ActionCable docs](http://guides.rubyonrails.org/action_cable_overview.html) to learn more about ActionCable before proceeding.
17
+
18
+ ```ruby
19
+ # app/models/user.rb
20
+ class User < ApplicationRecord
21
+ include CableReady::Broadcaster
22
+
23
+ def broadcast_name_change
24
+ cable_ready["UserChannel"].text_content selector: "#user-name", text: name
25
+ cable_ready.broadcast
26
+ end
27
+ end
28
+ ```
29
+
30
+ ```javascript
31
+ // app/assets/javascripts/application.js
32
+ /*
33
+ *= require cable_ready
34
+ */
35
+ ```
36
+
37
+ ```javascript
38
+ // app/assets/javascripts/channels/user.js
39
+ App.cable.subscriptions.create({ channel: "UserChannel" }, {
40
+ received: function (data) {
41
+ if (data.cableReady) {
42
+ CableReady.perform(data.operations);
43
+ }
44
+ }
45
+ });
46
+ ```
11
47
 
12
48
  ## Supported DOM Operations
13
49
 
50
+ - [dispatchEvent](#dispatchevent)
51
+ - [innerHTML](#innerhtml)
52
+ - [insertAdjacentHTML](#insertAdjacentHTML)
53
+ - [insertAdjacentText](#insertadjacenttext)
54
+ - [remove](#remove)
55
+ - [replace](#replace)
56
+ - [setValue](#setvalue)
57
+ - [setAttribute](#setattribute)
58
+ - [removeAttribute](#removeattribute)
59
+ - [addCssClass](#addcssclass)
60
+ - [removeCssClass](#removecssclass)
61
+ - [setDatasetProperty](#setdatasetproperty)
62
+
14
63
  > The `selector` options use [Document.querySelector()](https://developer.mozilla.org/en-US/docs/Web/API/Document/querySelector) to find elements.
15
64
 
16
65
  > It's possible to invoke multiple DOM operations with a single ActionCable broadcast.
@@ -22,11 +71,11 @@ Learn more about CableReady by reading through & running the [CableReady Test](h
22
71
  Dispatches a DOM event in the browser.
23
72
 
24
73
  ```ruby
25
- cable_ready_broadcast "MyChannel", dispatch_event: [{
74
+ cable_ready["MyChannel"].dispatch_event(
26
75
  name: "string", # required - the name of the DOM event to dispatch (can be custom)
27
76
  detail: "object", # [null] - assigned to event.detail
28
77
  selector: "string" # [window] - string containing one or more CSS selectors separated by commas
29
- }]
78
+ )
30
79
  ```
31
80
 
32
81
  ### Element Mutations
@@ -36,11 +85,11 @@ cable_ready_broadcast "MyChannel", dispatch_event: [{
36
85
  Sets the innerHTML of a DOM element.
37
86
 
38
87
  ```ruby
39
- cable_ready_broadcast "MyChannel", inner_html: [{
88
+ cable_ready["MyChannel"].inner_html(
40
89
  selector: "string", # required - string containing one or more CSS selectors separated by commas
41
90
  focusSelector: "string", # [null] - string containing one or more CSS selectors separated by commas
42
91
  html: "string" # [null] - the HTML to assign
43
- }]
92
+ )
44
93
  ```
45
94
 
46
95
  #### [textContent](https://developer.mozilla.org/en-US/docs/Web/API/Node/textContent)
@@ -48,10 +97,10 @@ cable_ready_broadcast "MyChannel", inner_html: [{
48
97
  Sets the text content of a DOM element.
49
98
 
50
99
  ```ruby
51
- cable_ready_broadcast "MyChannel", text_content: [{
100
+ cable_ready["MyChannel"].text_content(
52
101
  selector: "string", # required - string containing one or more CSS selectors separated by commas
53
102
  text: "string" # [null] - the text to assign
54
- }]
103
+ )
55
104
  ```
56
105
 
57
106
  #### [insertAdjacentHTML](https://developer.mozilla.org/en-US/docs/Web/API/Element/insertAdjacentHTML)
@@ -60,12 +109,12 @@ Inserts HTML into the DOM relative to an element.
60
109
  Supports behavior akin to prepend & append.
61
110
 
62
111
  ```ruby
63
- cable_ready_broadcast "MyChannel", insert_adjacent_html: [{
112
+ cable_ready["MyChannel"].insert_adjacent_html(
64
113
  selector: "string", # required - string containing one or more CSS selectors separated by commas
65
114
  focusSelector: "string", # [null] - string containing one or more CSS selectors separated by commas
66
115
  position: "string", # [beforeend] - the relative position to the DOM element (beforebegin, afterbegin, beforeend, afterend)
67
116
  html: "string" # [null] - the HTML to insert
68
- }]
117
+ )
69
118
  ```
70
119
 
71
120
  #### [insertAdjacentText](https://developer.mozilla.org/en-US/docs/Web/API/Element/insertAdjacentText)
@@ -74,11 +123,11 @@ Inserts text into the DOM relative to an element.
74
123
  Supports behavior akin to prepend & append.
75
124
 
76
125
  ```ruby
77
- cable_ready_broadcast "MyChannel", insert_adjacent_text: [{
126
+ cable_ready["MyChannel"].insert_adjacent_text(
78
127
  selector: "string", # required - string containing one or more CSS selectors separated by commas
79
128
  position: "string", # [beforeend] - the relative position to the DOM element (beforebegin, afterbegin, beforeend, afterend)
80
129
  text: "string" # [null] - the text to insert
81
- }]
130
+ )
82
131
  ```
83
132
 
84
133
  #### [remove](https://developer.mozilla.org/en-US/docs/Web/API/ChildNode/remove)
@@ -86,10 +135,10 @@ cable_ready_broadcast "MyChannel", insert_adjacent_text: [{
86
135
  Removes an element from the DOM.
87
136
 
88
137
  ```ruby
89
- cable_ready_broadcast "MyChannel", remove: [{
138
+ cable_ready["MyChannel"].remove(
90
139
  selector: "string", # required - string containing one or more CSS selectors separated by commas
91
140
  focusSelector: "string" # [null] - string containing one or more CSS selectors separated by commas
92
- }]
141
+ )
93
142
  ```
94
143
 
95
144
  #### [replace](https://developer.mozilla.org/en-US/docs/Web/API/Node/replaceChild)
@@ -97,11 +146,11 @@ cable_ready_broadcast "MyChannel", remove: [{
97
146
  Replaces a DOM element with new HTML.
98
147
 
99
148
  ```ruby
100
- cable_ready_broadcast "MyChannel", replace: [{
149
+ cable_ready["MyChannel"].replace(
101
150
  selector: "string", # required - string containing one or more CSS selectors separated by commas
102
151
  focusSelector: "string", # [null] - string containing one or more CSS selectors separated by commas
103
152
  html: "string" # [null] - the HTML to use as replacement
104
- }]
153
+ )
105
154
  ```
106
155
 
107
156
  #### [setValue](https://developer.mozilla.org/en-US/docs/Web/API/HTMLInputElement)
@@ -109,10 +158,10 @@ cable_ready_broadcast "MyChannel", replace: [{
109
158
  Sets the value of an element.
110
159
 
111
160
  ```ruby
112
- cable_ready_broadcast "MyChannel", set_value: [{
161
+ cable_ready["MyChannel"].set_value(
113
162
  selector: "string", # required - string containing one or more CSS selectors separated by commas
114
163
  value: "string" # [null] - the value to assign to the attribute
115
- }]
164
+ )
116
165
  ```
117
166
 
118
167
  ### Attribute Mutations
@@ -122,11 +171,11 @@ cable_ready_broadcast "MyChannel", set_value: [{
122
171
  Sets an attribute on an element.
123
172
 
124
173
  ```ruby
125
- cable_ready_broadcast "MyChannel", set_attribute: [{
174
+ cable_ready["MyChannel"].set_attribute(
126
175
  selector: "string", # required - string containing one or more CSS selectors separated by commas
127
176
  name: "string", # required - the attribute to set
128
177
  value: "string" # [null] - the value to assign to the attribute
129
- }]
178
+ )
130
179
  ```
131
180
 
132
181
  #### [removeAttribute](https://developer.mozilla.org/en-US/docs/Web/API/Element/removeAttribute)
@@ -134,10 +183,10 @@ cable_ready_broadcast "MyChannel", set_attribute: [{
134
183
  Removes an attribute from an element.
135
184
 
136
185
  ```ruby
137
- cable_ready_broadcast "MyChannel", remove_attribute: [{
186
+ cable_ready["MyChannel"].remove_attribute(
138
187
  selector: "string", # required - string containing one or more CSS selectors separated by commas
139
188
  name: "string" # required - the attribute to remove
140
- }]
189
+ )
141
190
  ```
142
191
 
143
192
  ### CSS Class Mutations
@@ -148,10 +197,10 @@ Adds a css class to an element.
148
197
  This is a `noop` if the css class is already assigned.
149
198
 
150
199
  ```ruby
151
- cable_ready_broadcast "MyChannel", add_css_class: [{
200
+ cable_ready["MyChannel"].add_css_class(
152
201
  selector: "string", # required - string containing one or more CSS selectors separated by commas
153
202
  name: "string" # [null] - the CSS class to add
154
- }]
203
+ )
155
204
 
156
205
  ```
157
206
  #### [removeCssClass](https://developer.mozilla.org/en-US/docs/Web/API/Element/classList)
@@ -159,10 +208,10 @@ cable_ready_broadcast "MyChannel", add_css_class: [{
159
208
  Removes a css class from an element.
160
209
 
161
210
  ```ruby
162
- cable_ready_broadcast "MyChannel", add_css_class: [{
211
+ cable_ready["MyChannel"].add_css_class(
163
212
  selector: "string", # required - string containing one or more CSS selectors separated by commas
164
213
  name: "string" # [null] - the CSS class to remove
165
- }]
214
+ )
166
215
  ```
167
216
 
168
217
  ### Dataset Mutations
@@ -172,52 +221,14 @@ cable_ready_broadcast "MyChannel", add_css_class: [{
172
221
  Sets an dataset property (data-* attribute) on an element.
173
222
 
174
223
  ```ruby
175
- cable_ready_broadcast "MyChannel", set_dataset_property: [{
224
+ cable_ready["MyChannel"].set_dataset_property(
176
225
  selector: "string", # required - string containing one or more CSS selectors separated by commas
177
226
  name: "string", # required - the property to set
178
227
  value: "string" # [null] - the value to assign to the dataset
179
- }]
228
+ )
180
229
  ```
181
230
 
182
- ## Quick Start
183
-
184
- > Please read the official [ActionCable docs](http://guides.rubyonrails.org/action_cable_overview.html) to learn more about ActionCable before proceeding.
185
-
186
- ```ruby
187
- # app/models/user.rb
188
- class User < ApplicationRecord
189
- include CableReady::Broadcaster
190
-
191
- def broadcast_name_change
192
- cable_ready_broadcast "UserChannel", text_content: [{ selector: "#user-name", text: name }]
193
- end
194
- end
195
- ```
196
-
197
- ```javascript
198
- // app/assets/javascripts/application.js
199
- /*
200
- * ...
201
- *= require cable_ready
202
- * ...
203
- */
204
- ```
205
-
206
- ```javascript
207
- // app/assets/javascripts/channels/user.js
208
- App.cable.subscriptions.create({ channel: "UserChannel" }, {
209
- received: function (data) {
210
- if (data.cableReady) {
211
- CableReady.perform(data.operations);
212
- }
213
- }
214
- });
215
- ```
216
-
217
- ## Advanced Usage
218
-
219
- Consider using CableReady in concert with a gem like
220
- [SelfRenderer](https://github.com/hopsoft/self_renderer) to create a powerful SPA style user experience with the simplicity of server side rendering.
231
+ ---
221
232
 
222
233
  <a target='_blank' rel='nofollow' href='https://app.codesponsor.io/link/QMSjMHrtPhvfmCnk5Hbikhhr/hopsoft/cable_ready'>
223
234
  <img alt='Sponsor' width='888' height='68' src='https://app.codesponsor.io/embed/QMSjMHrtPhvfmCnk5Hbikhhr/hopsoft/cable_ready.svg' />
@@ -1,97 +1,11 @@
1
+ require_relative "channels"
2
+
1
3
  module CableReady
2
4
  module Broadcaster
3
5
  extend ::ActiveSupport::Concern
4
6
 
5
- # Example Payload:
6
- #
7
- # {
8
- # # DOM Events ..................................................................................................
9
- #
10
- # dispatch_event: [{
11
- # name: "string",
12
- # detail: "object",
13
- # selector: "string",
14
- # }, ...],
15
- #
16
- # # Element Mutations ...........................................................................................
17
- #
18
- # inner_html: [{
19
- # selector: "string",
20
- # focusSelector: "string",
21
- # html: "string"
22
- # }, ...],
23
- #
24
- # text_content: [{
25
- # selector: "string",
26
- # text: "string"
27
- # }, ...]
28
- #
29
- # insert_adjacent_html: [{
30
- # selector: "string",
31
- # focusSelector: "string",
32
- # position: "string",
33
- # html: "string"
34
- # }, ...],
35
- #
36
- # insert_adjacent_text: [{
37
- # selector: "string",
38
- # position: "string",
39
- # text: "string"
40
- # }, ...],
41
- #
42
- # remove: [{
43
- # selector: "string",
44
- # focusSelector: "string,
45
- # }, ...],
46
- #
47
- # replace: [{
48
- # selector: "string",
49
- # focusSelector: "string",
50
- # html: "string"
51
- # }, ...],
52
- #
53
- # set_value: [{
54
- # selector: "string",
55
- # value: "string"
56
- # }, ...],
57
- #
58
- # # Attribute Mutations .........................................................................................
59
- #
60
- # set_attribute: [{
61
- # selector: "string",
62
- # name: "string",
63
- # value: "string"
64
- # }, ...],
65
- #
66
- # remove_attribute: [{
67
- # selector: "string",
68
- # name: "string"
69
- # }, ...],
70
- #
71
- # # CSS Class Mutations .........................................................................................
72
- #
73
- # add_css_class: [{
74
- # selector: "string",
75
- # name: "string"
76
- # }, ...],
77
- #
78
- # remove_css_class: [{
79
- # selector: "string",
80
- # name: "string"
81
- # }, ...],
82
- #
83
- # # Dataset Mutations ...........................................................................................
84
- #
85
- # set_dataset_property: [{
86
- # selector: "string",
87
- # name: "string",
88
- # value: "string"
89
- # }, ...],
90
- # }
91
- def cable_ready_broadcast(channel, operations={})
92
- operations ||= {}
93
- operations = operations.deep_transform_keys { |key| key.to_s.camelize(:lower) }
94
- ActionCable.server.broadcast channel, "cableReady" => true, "operations" => operations
7
+ def cable_ready
8
+ @cable_ready_channels ||= CableReady::Channels.new
95
9
  end
96
10
  end
97
11
  end
@@ -0,0 +1,172 @@
1
+ module CableReady
2
+ class Channel
3
+ attr_reader :name, :operations
4
+
5
+ # Example Operations Payload:
6
+ #
7
+ # {
8
+ # # DOM Events ..................................................................................................
9
+ #
10
+ # dispatch_event: [{
11
+ # name: "string",
12
+ # detail: "object",
13
+ # selector: "string",
14
+ # }, ...],
15
+ #
16
+ # # Element Mutations ...........................................................................................
17
+ #
18
+ # inner_html: [{
19
+ # selector: "string",
20
+ # focusSelector: "string",
21
+ # html: "string"
22
+ # }, ...],
23
+ #
24
+ # text_content: [{
25
+ # selector: "string",
26
+ # text: "string"
27
+ # }, ...]
28
+ #
29
+ # insert_adjacent_html: [{
30
+ # selector: "string",
31
+ # focusSelector: "string",
32
+ # position: "string",
33
+ # html: "string"
34
+ # }, ...],
35
+ #
36
+ # insert_adjacent_text: [{
37
+ # selector: "string",
38
+ # position: "string",
39
+ # text: "string"
40
+ # }, ...],
41
+ #
42
+ # remove: [{
43
+ # selector: "string",
44
+ # focusSelector: "string,
45
+ # }, ...],
46
+ #
47
+ # replace: [{
48
+ # selector: "string",
49
+ # focusSelector: "string",
50
+ # html: "string"
51
+ # }, ...],
52
+ #
53
+ # set_value: [{
54
+ # selector: "string",
55
+ # value: "string"
56
+ # }, ...],
57
+ #
58
+ # # Attribute Mutations .........................................................................................
59
+ #
60
+ # set_attribute: [{
61
+ # selector: "string",
62
+ # name: "string",
63
+ # value: "string"
64
+ # }, ...],
65
+ #
66
+ # remove_attribute: [{
67
+ # selector: "string",
68
+ # name: "string"
69
+ # }, ...],
70
+ #
71
+ # # CSS Class Mutations .........................................................................................
72
+ #
73
+ # add_css_class: [{
74
+ # selector: "string",
75
+ # name: "string"
76
+ # }, ...],
77
+ #
78
+ # remove_css_class: [{
79
+ # selector: "string",
80
+ # name: "string"
81
+ # }, ...],
82
+ #
83
+ # # Dataset Mutations ...........................................................................................
84
+ #
85
+ # set_dataset_property: [{
86
+ # selector: "string",
87
+ # name: "string",
88
+ # value: "string"
89
+ # }, ...],
90
+ # }
91
+ def initialize(name)
92
+ @name = name
93
+ @operations = stub
94
+ end
95
+
96
+ def clear
97
+ @operations = stub
98
+ end
99
+
100
+ def dispatch_event(options={})
101
+ operations[:dispatch_event] << options
102
+ end
103
+
104
+ def inner_html(options={})
105
+ operations[:inner_html] << options
106
+ end
107
+
108
+ def text_content(options={})
109
+ operations[:text_content] << options
110
+ end
111
+
112
+ def insert_adjacent_html(options={})
113
+ operations[:insert_adjacent_html] << options
114
+ end
115
+
116
+ def insert_adjacent_text(options={})
117
+ operations[:insert_adjacent_text] << options
118
+ end
119
+
120
+ def remove(options={})
121
+ operations[:remove] << options
122
+ end
123
+
124
+ def replace(options={})
125
+ operations[:replace] << options
126
+ end
127
+
128
+ def set_value(options={})
129
+ operations[:set_value] << options
130
+ end
131
+
132
+ def set_attribute(options={})
133
+ operations[:set_attribute] << options
134
+ end
135
+
136
+ def remove_attribute(options={})
137
+ operations[:remove_attribute] << options
138
+ end
139
+
140
+ def add_css_class(options={})
141
+ operations[:add_css_class] << options
142
+ end
143
+
144
+ def remove_css_class(options={})
145
+ operations[:remove_css_class] << options
146
+ end
147
+
148
+ def set_dataset_property(options={})
149
+ operations[:set_dataset_property] << options
150
+ end
151
+
152
+ private
153
+
154
+ def stub
155
+ {
156
+ dispatch_event: [],
157
+ inner_html: [],
158
+ text_content: [],
159
+ insert_adjacent_html: [],
160
+ insert_adjacent_text: [],
161
+ remove: [],
162
+ replace: [],
163
+ set_value: [],
164
+ set_attribute: [],
165
+ remove_attribute: [],
166
+ add_css_class: [],
167
+ remove_css_class: [],
168
+ set_dataset_property: []
169
+ }
170
+ end
171
+ end
172
+ end
@@ -0,0 +1,26 @@
1
+ require_relative "channel"
2
+
3
+ module CableReady
4
+ class Channels
5
+ def initialize
6
+ @channels = {}
7
+ end
8
+
9
+ def [](channel_name)
10
+ @channels[channel_name] ||= CableReady::Channel.new(channel_name)
11
+ end
12
+
13
+ def clear
14
+ @channels = {}
15
+ end
16
+
17
+ def broadcast
18
+ @channels.each do |channel_name, channel|
19
+ ActionCable.server.broadcast channel_name,
20
+ "cableReady" => true,
21
+ "operations" => channel.operations.deep_transform_keys { |key| key.to_s.camelize(:lower) }
22
+ end
23
+ clear
24
+ end
25
+ end
26
+ end
@@ -1,3 +1,3 @@
1
1
  module CableReady
2
- VERSION = "1.1.0"
2
+ VERSION = "2.0.0"
3
3
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: cable_ready
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.1.0
4
+ version: 2.0.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Nathan Hopkins
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2017-09-24 00:00:00.000000000 Z
11
+ date: 2017-10-14 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: activesupport
@@ -96,6 +96,8 @@ files:
96
96
  - bin/setup
97
97
  - lib/cable_ready.rb
98
98
  - lib/cable_ready/broadcaster.rb
99
+ - lib/cable_ready/channel.rb
100
+ - lib/cable_ready/channels.rb
99
101
  - lib/cable_ready/version.rb
100
102
  - vendor/assets/javascripts/cable_ready.js
101
103
  homepage: https://github.com/hopsoft/cable_ready