cubism 0.1.0.pre7 → 0.1.0.pre11

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: 60592da9032ef659e0cc7b05906f5f0711d7dc2e6e6d764248e2a959f05630a3
4
- data.tar.gz: ebac5554adf2599e0bc24d650f237b160681d834e9187d917dc346d153a55c36
3
+ metadata.gz: cf5d9eed6d97039688a2f51dd5ddab248619879ad47d50abbf37bab73d7f7d56
4
+ data.tar.gz: 8120474f22abf5ee4b9bc2497e91ef2e68f41aea79f59fde4ae1c9e577a75dd7
5
5
  SHA512:
6
- metadata.gz: 59667a0621019d1909b461f5e7209127cda5e10e6ccb59c40fc876e4009934ea458e91b3f3db38cd558895419290c594379c8d3c5a66cd800a0a02da61e63a94
7
- data.tar.gz: 5057d6a805878455811521a75422bd86e0b018f5fb0a5bc31409b765713eba8d5a9a3d0ce8eaf7795246796719e097407243f932eb1c97b006bac08d803ccf07
6
+ metadata.gz: fe7a0bca6d22807e0eb6b81e612ee8d435f67380a5aec20df253a86a92606642f907a67341b845159b2ae498dfcc0d7c56c1f49fb3425e1470789140adf4939e
7
+ data.tar.gz: dd6925f36a82fcfab2de5a888b1d974b151fb9a14a7c4cf76cab9f3ffde28b865790c09dd4b97b19a8284192cef644847a3c944b06e53dd2d690ef8da2a7245e
data/README.md CHANGED
@@ -4,7 +4,9 @@
4
4
  <!-- ALL-CONTRIBUTORS-BADGE:END -->
5
5
  [![Twitter follow](https://img.shields.io/twitter/follow/julian_rubisch?style=social)](https://twitter.com/julian_rubisch)
6
6
 
7
- Lightweight Resource-Based Presence Solution with CableReady
7
+ Lightweight Resource-Based Presence Solution with CableReady.
8
+
9
+ `Cubism` provides real-time updates of who is viewing or interacting with whatever resources you need. Whether you want Slack's "X is typing..." indicator or an e-commerce "5 other customers are viewing this item" notice, `Cubism` gives you everything you need "under the hood" so that you can focus on what really matters—end-user functionality.
8
10
 
9
11
  ## Table of Contents
10
12
 
@@ -12,6 +14,7 @@ Lightweight Resource-Based Presence Solution with CableReady
12
14
  - [Usage](#usage)
13
15
  - [Installation](#installation)
14
16
  - [API](#api)
17
+ - [Limitations](#limitations)
15
18
  - [Gotchas](#gotchas)
16
19
  - [Contributing](#contributing)
17
20
  - [License](#license)
@@ -54,6 +57,8 @@ Using the `cubicle_for` helper, you can set up a presence indicator. It will
54
57
  <% end %>
55
58
  ```
56
59
 
60
+ **Important!** due to technical limitations the cubism block does _not_ act as a closure, i.e. it has _only_ access to the `users` variable passed to it - think of it more as a self-contained component.
61
+
57
62
  ## Installation
58
63
  Add this line to your application's Gemfile:
59
64
 
@@ -91,12 +96,17 @@ CableReady.initialize({ consumer });
91
96
 
92
97
  The `cubicle_for` helper accepts the following options as keyword arguments:
93
98
 
94
- - `exclude_current_user (true|false)`: Whether or not to exclude the current user from the list of present users broadcasted to the view. Useful e.g. for "typing..." indicators.
99
+ - `exclude_current_user (true|false)`: Whether or not to exclude the current user from the list of present users broadcasted to the view. Useful e.g. for "typing..." indicators (default: `true`).
95
100
  - `appear_trigger`: JavaScript event names (e.g. `["focus", "debounced:input]`) to use. (Can also be a singular string, which will be converted to an array). The default is `:connect`, i.e. register a user as "appeared"/"present" when the element connects to the DOM.
96
101
  - `disappear_trigger`: a JavaScript event name (e.g. `:blur`) to use. (Can also be a singular string, which will be converted to an array). The default is `:disconnect`, i.e. remove a user form the present users list when the element disconnects from the DOM.
97
102
  - `trigger_root`: a CSS selector to attach the appear/disappear events to. Defaults to the `cubicle-element` itself.
98
103
  - `html_options` are passed to the TagBuilder.
99
104
 
105
+ ## Limitations
106
+
107
+ ### Supported Template Handlers
108
+ - ERB
109
+
100
110
  ## Gotchas
101
111
 
102
112
  ### Usage with ViewComponent
@@ -3,7 +3,7 @@ class Cubism::PresenceChannel < ActionCable::Channel::Base
3
3
 
4
4
  def subscribed
5
5
  if resource.present?
6
- stream_for resource
6
+ stream_from params[:element_id]
7
7
  resource.cubicle_element_ids << element_id
8
8
  resource.excluded_user_id_for_element_id[element_id] = user.id if exclude_current_user?
9
9
  else
@@ -2,17 +2,32 @@ module CubismHelper
2
2
  include CableReady::StreamIdentifier
3
3
 
4
4
  def cubicle_for(resource, user, html_options: {}, appear_trigger: :connect, disappear_trigger: nil, trigger_root: nil, exclude_current_user: true, &block)
5
- key = "#{block.source_location.join(":")}:#{resource.to_gid}:#{user.to_gid}"
6
- digested_id = ActiveSupport::Digest.hexdigest(key)
5
+ block_location = block.source_location.join(":")
6
+ block_source = Cubism::BlockSource.find_or_create(
7
+ location: block_location,
8
+ view_context: self
9
+ )
10
+
11
+ resource_gid = resource.to_gid.to_s
12
+
13
+ block_container = Cubism::BlockContainer.new(
14
+ block_location: block_location,
15
+ block_source: block_source,
16
+ resource_gid: resource_gid,
17
+ user_gid: user.to_gid.to_s
18
+ )
19
+
20
+ digested_block_key = block_container.digest
21
+
22
+ Cubism.block_store.fetch(digested_block_key, block_container)
7
23
 
8
- Cubism.store[digested_id] = Cubism::BlockStoreItem.new(context: self, block: block.dup)
9
24
  tag.cubicle_element(
10
- identifier: signed_stream_identifier(resource.to_gid.to_s),
25
+ identifier: signed_stream_identifier(resource_gid),
11
26
  user: user.to_sgid.to_s,
12
27
  "appear-trigger": Array(appear_trigger).join(","),
13
28
  "disappear-trigger": disappear_trigger,
14
29
  "trigger-root": trigger_root,
15
- id: "cubicle-#{digested_id}",
30
+ id: "cubicle-#{digested_block_key}",
16
31
  "exclude-current-user": exclude_current_user,
17
32
  **html_options
18
33
  )
@@ -2,17 +2,30 @@ module CubismHelper
2
2
  include CableReady::StreamIdentifier
3
3
 
4
4
  def cubicle_for(resource, user, html_options: {}, appear_trigger: :connect, disappear_trigger: nil, trigger_root: nil, exclude_current_user: true, &block)
5
- key = "#{block.source_location.join(":")}:#{resource.to_gid}:#{user.to_gid}"
6
- digested_id = ActiveSupport::Digest.hexdigest(key)
5
+ block_location = block.source_location.join(":")
6
+
7
+ resource_gid = resource.to_gid.to_s
8
+
9
+ store_item = Cubism::BlockStoreItem.new(
10
+ block_location: block_location,
11
+ resource_gid: resource_gid,
12
+ user_gid: user.to_gid.to_s,
13
+ view_context: self
14
+ )
15
+
16
+ digested_block_key = store_item.digest
17
+
18
+ store_item.parse!
19
+
20
+ Cubism.block_store[digested_block_key] = store_item
7
21
 
8
- Cubism.store[digested_id] = Cubism::BlockStoreItem.new(context: self, block: block.dup)
9
22
  tag.cubicle_element(
10
- identifier: signed_stream_identifier(resource.to_gid.to_s),
23
+ identifier: signed_stream_identifier(resource_gid),
11
24
  user: user.to_sgid.to_s,
12
- "appear-trigger": appear_trigger,
25
+ "appear-trigger": Array(appear_trigger).join(","),
13
26
  "disappear-trigger": disappear_trigger,
14
27
  "trigger-root": trigger_root,
15
- id: "cubicle-#{digested_id}",
28
+ id: "cubicle-#{digested_block_key}",
16
29
  "exclude-current-user": exclude_current_user,
17
30
  **html_options
18
31
  )
@@ -10,4 +10,11 @@ module Cubism::Presence
10
10
  def stream_presence
11
11
  Cubism::Broadcaster.new(resource: self).broadcast
12
12
  end
13
+
14
+ def present_users_for_element_id(element_id)
15
+ users = Cubism.user_class.find(present_users.members)
16
+ users.reject! { |user| user.id == excluded_user_id_for_element_id[element_id].to_i }
17
+
18
+ users
19
+ end
13
20
  end
@@ -2,10 +2,19 @@ module Cubism::Presence
2
2
  extend ActiveSupport::Concern
3
3
 
4
4
  included do
5
- kredis_set :present_users, after_change: :stream_presence_later
5
+ kredis_set :present_users, after_change: :stream_presence
6
+ kredis_set :cubicle_element_ids
7
+ kredis_hash :excluded_user_id_for_element_id
6
8
  end
7
9
 
8
- def stream_presence_later
9
- Cubism::StreamPresenceJob.perform_later(resource: self)
10
+ def stream_presence
11
+ Cubism::Broadcaster.new(resource: self).broadcast
12
+ end
13
+
14
+ def present_users_for_element_id(element_id)
15
+ users = Cubism.user_class.find(present_users.members)
16
+ users.reject! { |user| user.id == excluded_user_id_for_element_id[element_id].to_i }
17
+
18
+ users
10
19
  end
11
20
  end
@@ -14,9 +14,13 @@ module Cubism
14
14
  def broadcast
15
15
  resource.cubicle_element_ids.to_a.each do |element_id|
16
16
  /cubicle-(?<block_key>.+)/ =~ element_id
17
- block = Cubism.store[block_key].block
18
- view_context = Cubism.store[block_key].context
19
- html = view_context.capture(users_for(resource, element_id), &block)
17
+ block_container = Cubism.block_store[block_key]
18
+
19
+ next if block_container.blank?
20
+
21
+ block_source = block_container.block_source
22
+
23
+ html = ApplicationController.render(inline: block_source.source, locals: {"#{block_source.variable_name}": resource.present_users_for_element_id(element_id)})
20
24
 
21
25
  cable_ready[element_id].inner_html(
22
26
  selector: "cubicle-element##{element_id}[identifier='#{signed_stream_identifier(resource.to_global_id.to_s)}']",
@@ -24,14 +28,5 @@ module Cubism
24
28
  ).broadcast
25
29
  end
26
30
  end
27
-
28
- private
29
-
30
- def users_for(resource, element_id)
31
- users = Cubism.user_class.find(resource.present_users.members)
32
- users.reject! { |user| user.id == resource.excluded_user_id_for_element_id[element_id].to_i }
33
-
34
- users
35
- end
36
31
  end
37
32
  end
@@ -14,24 +14,17 @@ module Cubism
14
14
  def broadcast
15
15
  resource.cubicle_element_ids.to_a.each do |element_id|
16
16
  /cubicle-(?<block_key>.+)/ =~ element_id
17
- block = Cubism.store[block_key].block
18
- view_context = Cubism.store[block_key].context
19
- html = view_context.capture(users_for(resource, element_id), &block)
17
+ store_item = Cubism.block_store[block_key]
20
18
 
21
- cable_ready[Cubism::PresenceChannel].inner_html(
19
+ next if store_item.blank?
20
+
21
+ html = ApplicationController.render(inline: store_item.block_source, locals: {"#{store_item.block_variable_name}": resource.present_users_for_element_id(element_id)})
22
+
23
+ cable_ready[element_id].inner_html(
22
24
  selector: "cubicle-element##{element_id}[identifier='#{signed_stream_identifier(resource.to_global_id.to_s)}']",
23
25
  html: html
24
- ).broadcast_to(resource)
26
+ ).broadcast
25
27
  end
26
28
  end
27
-
28
- private
29
-
30
- def users_for(resource, element_id)
31
- users = Cubism.user_class.find(resource.present_users.members)
32
- users.reject! { |user| user.id == resource.excluded_user_id_for_element_id[element_id].to_i }
33
-
34
- users
35
- end
36
29
  end
37
30
  end
@@ -0,0 +1,56 @@
1
+ module Cubism
2
+ class CubicleBlockStore
3
+ delegate_missing_to :@blocks
4
+
5
+ def initialize
6
+ @blocks = Kredis.hash "cubism-blocks"
7
+ end
8
+
9
+ def [](key)
10
+ Marshal.load(@blocks[key]) if @blocks[key]
11
+ end
12
+
13
+ def []=(key, value)
14
+ mutex.synchronize do
15
+ @blocks[key] = Marshal.dump value
16
+ end
17
+ end
18
+
19
+ def clear
20
+ mutex.synchronize do
21
+ # kredis #remove
22
+ @blocks.remove
23
+ end
24
+ end
25
+
26
+ def size
27
+ @blocks.to_h.size
28
+ end
29
+
30
+ private
31
+
32
+ def mutex
33
+ @mutex ||= Mutex.new
34
+ end
35
+ end
36
+
37
+ BlockStoreItem = Struct.new(:block_location, :block_source, :user_gid, :resource_gid, keyword_init: true) do
38
+ def user
39
+ GlobalID::Locator.locate self[:user_gid]
40
+ end
41
+
42
+ def resource
43
+ GlobalID::Locator.locate self[:resource_gid]
44
+ end
45
+
46
+ def marshal_dump
47
+ to_h
48
+ end
49
+
50
+ def marshal_load(serialized_item)
51
+ %i[block_location block_source user_gid resource_gid].each do |arg|
52
+ send("#{arg}=", serialized_item[arg])
53
+ end
54
+ end
55
+ end
56
+ end
@@ -0,0 +1,136 @@
1
+ module Cubism
2
+ class CubicleStore
3
+ delegate_missing_to :@blocks
4
+
5
+ def initialize(key)
6
+ @blocks = Kredis.hash key
7
+ end
8
+
9
+ def [](key)
10
+ Marshal.load(@blocks[key]) if @blocks[key]
11
+ end
12
+
13
+ def []=(key, value)
14
+ mutex.synchronize do
15
+ @blocks[key] = Marshal.dump value
16
+ end
17
+ end
18
+
19
+ def fetch(key, value = nil, &block)
20
+ if self[key].nil?
21
+ yield value if block
22
+ self[key] = value
23
+ end
24
+
25
+ self[key]
26
+ end
27
+
28
+ def clear
29
+ mutex.synchronize do
30
+ # kredis #remove
31
+ @blocks.remove
32
+ end
33
+ end
34
+
35
+ def size
36
+ @blocks.to_h.size
37
+ end
38
+
39
+ private
40
+
41
+ def mutex
42
+ @mutex ||= Mutex.new
43
+ end
44
+ end
45
+
46
+ # Container for cubicle blocks
47
+ BlockContainer = Struct.new(
48
+ :block_location,
49
+ :block_source,
50
+ :user_gid,
51
+ :resource_gid,
52
+ keyword_init: true
53
+ ) do
54
+ def initialize(*args)
55
+ super
56
+
57
+ @filename, _lineno = block_location.split(":")
58
+ end
59
+
60
+ def user
61
+ GlobalID::Locator.locate self[:user_gid]
62
+ end
63
+
64
+ def resource
65
+ GlobalID::Locator.locate self[:resource_gid]
66
+ end
67
+
68
+ def digest
69
+ resource_user_key = [resource_gid, user_gid].join(":")
70
+
71
+ ActiveSupport::Digest.hexdigest("#{block_location}:#{File.read(@filename)}:#{resource_user_key}")
72
+ end
73
+
74
+ def marshal_dump
75
+ to_h.merge(block_source: block_source.digest)
76
+ end
77
+
78
+ def marshal_load(serialized_item)
79
+ members.excluding(:block_source).each do |arg|
80
+ send("#{arg}=", serialized_item[arg])
81
+ end
82
+
83
+ self.block_source = Cubism.source_store[serialized_item[:block_source]]
84
+ end
85
+ end
86
+
87
+ # Container for cubicle block sources
88
+ BlockSource = Struct.new(
89
+ :location,
90
+ :source,
91
+ :variable_name,
92
+ :view_context,
93
+ keyword_init: true
94
+ ) do
95
+ def self.find_or_create(location:, view_context:)
96
+ instance = new(location: location, view_context: view_context)
97
+
98
+ Cubism.source_store.fetch(instance.digest, instance) do |instance|
99
+ instance.parse!
100
+ end
101
+
102
+ instance
103
+ end
104
+
105
+ def initialize(*args)
106
+ super
107
+
108
+ @filename, @lineno = location.split(":")
109
+ @lineno = @lineno.to_i
110
+ end
111
+
112
+ def parse!
113
+ return if location.start_with?("inline template")
114
+
115
+ lines = File.readlines(@filename)[@lineno - 1..]
116
+
117
+ preprocessor = Cubism::Preprocessor.new(source: lines.join.squish, view_context: view_context)
118
+ self.variable_name = preprocessor.block_variable_name
119
+ self.source = preprocessor.process
120
+ end
121
+
122
+ def digest
123
+ ActiveSupport::Digest.hexdigest("#{location}:#{File.read(@filename)}")
124
+ end
125
+
126
+ def marshal_dump
127
+ to_h.except(:view_context)
128
+ end
129
+
130
+ def marshal_load(serialized_item)
131
+ members.excluding(:view_context).each do |arg|
132
+ send("#{arg}=", serialized_item[arg])
133
+ end
134
+ end
135
+ end
136
+ end
@@ -0,0 +1,136 @@
1
+ module Cubism
2
+ class CubicleStore
3
+ delegate_missing_to :@blocks
4
+
5
+ def initialize(key)
6
+ @blocks = Kredis.hash key
7
+ end
8
+
9
+ def [](key)
10
+ Marshal.load(@blocks[key]) if @blocks[key]
11
+ end
12
+
13
+ def []=(key, value)
14
+ mutex.synchronize do
15
+ @blocks[key] = Marshal.dump value
16
+ end
17
+ end
18
+
19
+ def fetch(key, value = nil, &block)
20
+ if self[key].nil?
21
+ yield value if block
22
+ self[key] = value
23
+ end
24
+
25
+ self[key]
26
+ end
27
+
28
+ def clear
29
+ mutex.synchronize do
30
+ # kredis #remove
31
+ @blocks.remove
32
+ end
33
+ end
34
+
35
+ def size
36
+ @blocks.to_h.size
37
+ end
38
+
39
+ private
40
+
41
+ def mutex
42
+ @mutex ||= Mutex.new
43
+ end
44
+ end
45
+
46
+ # Container for cubicle blocks
47
+ BlockStoreItem = Struct.new(
48
+ :block_location,
49
+ :block_source,
50
+ :user_gid,
51
+ :resource_gid,
52
+ keyword_init: true
53
+ ) do
54
+ def initialize(*args)
55
+ super
56
+
57
+ @filename, _lineno = block_location.split(":")
58
+ end
59
+
60
+ def user
61
+ GlobalID::Locator.locate self[:user_gid]
62
+ end
63
+
64
+ def resource
65
+ GlobalID::Locator.locate self[:resource_gid]
66
+ end
67
+
68
+ def digest
69
+ resource_user_key = [resource_gid, user_gid].join(":")
70
+
71
+ ActiveSupport::Digest.hexdigest("#{block_location}:#{File.read(@filename)}:#{resource_user_key}")
72
+ end
73
+
74
+ def marshal_dump
75
+ to_h.reverse_merge(block_source: block_source.digest)
76
+ end
77
+
78
+ def marshal_load(serialized_item)
79
+ members.excluding(:block_source).each do |arg|
80
+ send("#{arg}=", serialized_item[arg])
81
+ end
82
+
83
+ self.block_source = Cubism.source_store(serialized_item[:block_source])
84
+ end
85
+ end
86
+
87
+ # Container for cubicle block sources
88
+ BlockSource = Struct.new(
89
+ :location,
90
+ :source,
91
+ :variable_name,
92
+ :view_context,
93
+ keyword_init: true
94
+ ) do
95
+ def self.find_or_create(location:, view_context:)
96
+ instance = new(location: location, view_context: view_context)
97
+
98
+ Cubism.source_store.fetch(instance.digest, instance) do |instance|
99
+ instance.parse!
100
+ end
101
+
102
+ instance
103
+ end
104
+
105
+ def initialize(*args)
106
+ super
107
+
108
+ @filename, @lineno = location.split(":")
109
+ @lineno = @lineno.to_i
110
+ end
111
+
112
+ def parse!
113
+ return if location.start_with?("inline template")
114
+
115
+ lines = File.readlines(@filename)[@lineno - 1..]
116
+
117
+ preprocessor = Cubism::Preprocessor.new(source: lines.join.squish, view_context: view_context)
118
+ self.variable_name = preprocessor.block_variable_name
119
+ self.source = preprocessor.process
120
+ end
121
+
122
+ def digest
123
+ ActiveSupport::Digest.hexdigest("#{location}:#{File.read(@filename)}")
124
+ end
125
+
126
+ def marshal_dump
127
+ to_h.except(:view_context)
128
+ end
129
+
130
+ def marshal_load(serialized_item)
131
+ members.excluding(:view_context).each do |arg|
132
+ send("#{arg}=", serialized_item[arg])
133
+ end
134
+ end
135
+ end
136
+ end
data/lib/cubism/engine.rb CHANGED
@@ -1,4 +1,8 @@
1
1
  module Cubism
2
2
  class Engine < ::Rails::Engine
3
+ initializer "cubism.stores" do
4
+ Cubism.block_store = Cubism::CubicleStore.new("cubism-blocks")
5
+ Cubism.source_store = Cubism::CubicleStore.new("cubism-source")
6
+ end
3
7
  end
4
8
  end
@@ -1,5 +1,7 @@
1
1
  module Cubism
2
2
  class Engine < ::Rails::Engine
3
+ initializer "cubism.block_store" do
4
+ Cubism.block_store = Cubism::CubicleBlockStore.new
5
+ end
3
6
  end
4
7
  end
5
-
File without changes
@@ -0,0 +1,33 @@
1
+ module Cubism
2
+ class Preprocessor
3
+ attr_reader :block_variable_name
4
+
5
+ def initialize(source:, view_context:)
6
+ match_data = /<%=\s+cubicle_for.+?\|(\w+)\|\s+%>/.match(source)
7
+ start_pos = match_data&.end(0) || 0
8
+ @block_variable_name = match_data[1] if match_data
9
+ @source = source[start_pos..]
10
+ @view_context = view_context
11
+ end
12
+
13
+ def process
14
+ begin
15
+ do_parse
16
+ rescue NameError
17
+ # we ignore any name errors from unset instance variables or local assigns here
18
+ end
19
+
20
+ @source
21
+ end
22
+
23
+ private
24
+
25
+ def do_parse
26
+ ActionView::Template::Handlers::ERB::Erubi.new(@source).evaluate(@view_context)
27
+ rescue SyntaxError
28
+ end_at_end = /(<%\s+end\s+%>)\z/.match(@source)
29
+ @source = end_at_end ? @source[..-(end_at_end[0].length + 1)] : @source[..-2]
30
+ do_parse
31
+ end
32
+ end
33
+ end
@@ -0,0 +1,30 @@
1
+ module Cubism
2
+ class Preprocessor
3
+ def initialize(source:, view_context:)
4
+ match_data = /<%=\s+cubicle_for.+\|.+\|\s+%>/.match(source)
5
+ start_pos = match_data&.end(0) || 0
6
+ @source = source[start_pos..]
7
+ @view_context = view_context
8
+ end
9
+
10
+ def process
11
+ begin
12
+ do_parse
13
+ rescue NameError
14
+ # we ignore any name errors from unset instance variables or local assigns here
15
+ end
16
+
17
+ @source
18
+ end
19
+
20
+ private
21
+
22
+ def do_parse
23
+ ActionView::Template::Handlers::ERB::Erubi.new(@source).evaluate(@view_context)
24
+ rescue SyntaxError
25
+ end_at_end = /(<%\s+end\s+%>)\z/.match(@source)
26
+ @source = end_at_end ? @source[..-(end_at_end[0].length + 1)] : @source[..-2]
27
+ do_parse
28
+ end
29
+ end
30
+ end
@@ -1,3 +1,3 @@
1
1
  module Cubism
2
- VERSION = "0.1.0.pre7"
2
+ VERSION = "0.1.0.pre11"
3
3
  end
@@ -1,3 +1,3 @@
1
1
  module Cubism
2
- VERSION = "0.1.0.pre6"
2
+ VERSION = "0.1.0.pre9"
3
3
  end
data/lib/cubism.rb CHANGED
@@ -3,14 +3,17 @@ require "kredis"
3
3
  require "cubism/version"
4
4
  require "cubism/engine"
5
5
  require "cubism/broadcaster"
6
- require "cubism/cubicle_block_store"
6
+ require "cubism/cubicle_store"
7
+ require "cubism/preprocessor"
7
8
 
8
9
  module Cubism
9
10
  extend ActiveSupport::Autoload
10
11
 
11
12
  autoload :Broadcaster, "cubism/broadcaster"
13
+ autoload :Preprocessor, "cubism/preprocessor"
12
14
 
13
15
  mattr_accessor :user_class, instance_writer: false, instance_reader: false
14
16
 
15
- mattr_reader :store, instance_reader: false, default: Cubism::CubicleBlockStore.instance
17
+ mattr_accessor :block_store, instance_reader: false
18
+ mattr_accessor :source_store, instance_reader: false
16
19
  end
data/lib/cubism.rb~ CHANGED
@@ -2,7 +2,17 @@ require "kredis"
2
2
 
3
3
  require "cubism/version"
4
4
  require "cubism/engine"
5
+ require "cubism/broadcaster"
6
+ require "cubism/cubicle_block_store"
7
+ require "cubism/preprocessor"
5
8
 
6
9
  module Cubism
10
+ extend ActiveSupport::Autoload
11
+
12
+ autoload :Broadcaster, "cubism/broadcaster"
13
+ autoload :Preprocessor, "cubism/preprocessor"
14
+
7
15
  mattr_accessor :user_class, instance_writer: false, instance_reader: false
16
+
17
+ mattr_accessor :block_store, instance_reader: false
8
18
  end
metadata CHANGED
@@ -1,29 +1,29 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: cubism
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.0.pre7
4
+ version: 0.1.0.pre11
5
5
  platform: ruby
6
6
  authors:
7
7
  - Julian Rubisch
8
- autorequire:
8
+ autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2021-12-22 00:00:00.000000000 Z
11
+ date: 2022-02-16 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: rails
15
15
  requirement: !ruby/object:Gem::Requirement
16
16
  requirements:
17
- - - "~>"
17
+ - - ">="
18
18
  - !ruby/object:Gem::Version
19
- version: 6.1.0
19
+ version: '6.0'
20
20
  type: :runtime
21
21
  prerelease: false
22
22
  version_requirements: !ruby/object:Gem::Requirement
23
23
  requirements:
24
- - - "~>"
24
+ - - ">="
25
25
  - !ruby/object:Gem::Version
26
- version: 6.1.0
26
+ version: '6.0'
27
27
  - !ruby/object:Gem::Dependency
28
28
  name: kredis
29
29
  requirement: !ruby/object:Gem::Requirement
@@ -53,7 +53,7 @@ dependencies:
53
53
  - !ruby/object:Gem::Version
54
54
  version: 5.0.0.pre8
55
55
  - !ruby/object:Gem::Dependency
56
- name: pry
56
+ name: standard
57
57
  requirement: !ruby/object:Gem::Requirement
58
58
  requirements:
59
59
  - - ">="
@@ -67,7 +67,49 @@ dependencies:
67
67
  - !ruby/object:Gem::Version
68
68
  version: '0'
69
69
  - !ruby/object:Gem::Dependency
70
- name: standard
70
+ name: nokogiri
71
+ requirement: !ruby/object:Gem::Requirement
72
+ requirements:
73
+ - - ">="
74
+ - !ruby/object:Gem::Version
75
+ version: '0'
76
+ type: :development
77
+ prerelease: false
78
+ version_requirements: !ruby/object:Gem::Requirement
79
+ requirements:
80
+ - - ">="
81
+ - !ruby/object:Gem::Version
82
+ version: '0'
83
+ - !ruby/object:Gem::Dependency
84
+ name: mocha
85
+ requirement: !ruby/object:Gem::Requirement
86
+ requirements:
87
+ - - ">="
88
+ - !ruby/object:Gem::Version
89
+ version: '0'
90
+ type: :development
91
+ prerelease: false
92
+ version_requirements: !ruby/object:Gem::Requirement
93
+ requirements:
94
+ - - ">="
95
+ - !ruby/object:Gem::Version
96
+ version: '0'
97
+ - !ruby/object:Gem::Dependency
98
+ name: appraisal
99
+ requirement: !ruby/object:Gem::Requirement
100
+ requirements:
101
+ - - ">="
102
+ - !ruby/object:Gem::Version
103
+ version: '0'
104
+ type: :development
105
+ prerelease: false
106
+ version_requirements: !ruby/object:Gem::Requirement
107
+ requirements:
108
+ - - ">="
109
+ - !ruby/object:Gem::Version
110
+ version: '0'
111
+ - !ruby/object:Gem::Dependency
112
+ name: sqlite3
71
113
  requirement: !ruby/object:Gem::Requirement
72
114
  requirements:
73
115
  - - ">="
@@ -90,30 +132,28 @@ files:
90
132
  - MIT-LICENSE
91
133
  - README.md
92
134
  - Rakefile
93
- - app/channels/cubism/presence.rb~
94
135
  - app/channels/cubism/presence_channel.rb
95
136
  - app/channels/cubism/presence_channel.rb~
96
137
  - app/helpers/cubism_helper.rb
97
138
  - app/helpers/cubism_helper.rb~
98
- - app/models/concerns/cubism/base.rb~
99
139
  - app/models/concerns/cubism/presence.rb
100
140
  - app/models/concerns/cubism/presence.rb~
101
141
  - app/models/concerns/cubism/user.rb
102
- - app/models/concerns/cubism/user.rb~
103
- - app/models/cubism/base.rb
104
- - app/models/cubism/base.rb~
105
142
  - app/models/cubism/current.rb
106
- - app/models/cubism/current.rb~
107
143
  - config/routes.rb
108
144
  - lib/cubism.rb
109
145
  - lib/cubism.rb~
110
146
  - lib/cubism/broadcaster.rb
111
147
  - lib/cubism/broadcaster.rb~
112
- - lib/cubism/cubicle_block_store.rb
113
148
  - lib/cubism/cubicle_block_store.rb~
149
+ - lib/cubism/cubicle_source_store.rb~
150
+ - lib/cubism/cubicle_store.rb
151
+ - lib/cubism/cubicle_store.rb~
114
152
  - lib/cubism/engine.rb
115
153
  - lib/cubism/engine.rb~
116
- - lib/cubism/railtie.rb~
154
+ - lib/cubism/parser.rb~
155
+ - lib/cubism/preprocessor.rb
156
+ - lib/cubism/preprocessor.rb~
117
157
  - lib/cubism/version.rb
118
158
  - lib/cubism/version.rb~
119
159
  - lib/tasks/cubism_tasks.rake
@@ -123,7 +163,7 @@ licenses:
123
163
  metadata:
124
164
  homepage_uri: https://github.com/julianrubisch/cubism
125
165
  source_code_uri: https://github.com/julianrubisch/cubism.git
126
- post_install_message:
166
+ post_install_message:
127
167
  rdoc_options: []
128
168
  require_paths:
129
169
  - lib
@@ -138,8 +178,8 @@ required_rubygems_version: !ruby/object:Gem::Requirement
138
178
  - !ruby/object:Gem::Version
139
179
  version: 1.3.1
140
180
  requirements: []
141
- rubygems_version: 3.2.3
142
- signing_key:
181
+ rubygems_version: 3.1.4
182
+ signing_key:
143
183
  specification_version: 4
144
184
  summary: Lightweight Resource-Based Presence Solution with CableReady
145
185
  test_files: []
@@ -1,18 +0,0 @@
1
- class Cubism::Presence < ActionCable::Channel::Base
2
- def subscribed
3
- resource = GlobalID::Locator.locate_signed params[:signed_resource]
4
- if resource.present?
5
- stream_for resource
6
- resource.present_users.add(current_user.id)
7
- else
8
- reject
9
- end
10
- end
11
-
12
- def unsubscribed
13
- resource = GlobalID::Locator.locate_signed params[:signed_resource]
14
- return unless resource.present?
15
-
16
- resource.present_users.remove(current_user.id)
17
- end
18
- end
@@ -1,3 +0,0 @@
1
- module Cubism::Base
2
- extend ActiveSupport::Concern
3
- end
@@ -1,11 +0,0 @@
1
- module Cubism::User
2
- extend ActiveSupport::Concern
3
-
4
- included do
5
- Cubism.user_class = self
6
-
7
- class_eval do
8
- cattr_accessor :cubicle_attributes
9
- end
10
- end
11
- end
@@ -1,14 +0,0 @@
1
- class Cubism::Base
2
- include ActiveModel::Model
3
- include Kredis::Attributes
4
- include Cubism::Presence
5
- include GlobalID::Identification
6
-
7
- def self.find(id)
8
- new if id == "cubism-#{self.class.name.underscore}"
9
- end
10
-
11
- def id
12
- "cubism-#{self.class.name.underscore}"
13
- end
14
- end
@@ -1,13 +0,0 @@
1
- class Cubism::Base
2
- include ActiveModel::Model
3
- include Cubism::Presence
4
- include GlobalID::Identifiable
5
-
6
- def self.find(id)
7
- new if id == "cubism-#{self.class.name.underscore}"
8
- end
9
-
10
- def id
11
- "cubism-#{self.class.name.underscore}"
12
- end
13
- end
@@ -1,27 +0,0 @@
1
- module Cubism
2
- class CubicleBlockStore
3
- include Singleton
4
-
5
- def initialize
6
- @blocks = {}
7
- end
8
-
9
- def [](key)
10
- @blocks[key]
11
- end
12
-
13
- def []=(key, value)
14
- mutex.synchronize do
15
- @blocks[key] = value
16
- end
17
- end
18
-
19
- private
20
-
21
- def mutex
22
- @mutex ||= Mutex.new
23
- end
24
- end
25
-
26
- BlockStoreItem = Struct.new(:context, :block, keyword_init: true)
27
- end
@@ -1,4 +0,0 @@
1
- module Cubism
2
- class Railtie < ::Rails::Railtie
3
- end
4
- end