hkroger-websocket-rails 0.7.1
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 +7 -0
- data/CHANGELOG.md +328 -0
- data/Gemfile +27 -0
- data/MIT-LICENSE +20 -0
- data/README.md +237 -0
- data/Rakefile +72 -0
- data/bin/thin-socketrails +45 -0
- data/lib/assets/javascripts/websocket_rails/abstract_connection.js.coffee +45 -0
- data/lib/assets/javascripts/websocket_rails/channel.js.coffee +70 -0
- data/lib/assets/javascripts/websocket_rails/event.js.coffee +42 -0
- data/lib/assets/javascripts/websocket_rails/http_connection.js.coffee +66 -0
- data/lib/assets/javascripts/websocket_rails/main.js +6 -0
- data/lib/assets/javascripts/websocket_rails/websocket_connection.js.coffee +29 -0
- data/lib/assets/javascripts/websocket_rails/websocket_rails.js.coffee +158 -0
- data/lib/config.ru +3 -0
- data/lib/generators/websocket_rails/install/install_generator.rb +33 -0
- data/lib/generators/websocket_rails/install/templates/events.rb +14 -0
- data/lib/generators/websocket_rails/install/templates/websocket_rails.rb +63 -0
- data/lib/hkroger-websocket-rails.rb +1 -0
- data/lib/rails/app/controllers/websocket_rails/delegation_controller.rb +13 -0
- data/lib/rails/config/routes.rb +7 -0
- data/lib/rails/tasks/websocket_rails.tasks +42 -0
- data/lib/spec_helpers/matchers/route_matchers.rb +65 -0
- data/lib/spec_helpers/matchers/trigger_matchers.rb +113 -0
- data/lib/spec_helpers/spec_helper_event.rb +34 -0
- data/lib/websocket-rails.rb +108 -0
- data/lib/websocket_rails/base_controller.rb +197 -0
- data/lib/websocket_rails/channel.rb +97 -0
- data/lib/websocket_rails/channel_manager.rb +55 -0
- data/lib/websocket_rails/configuration.rb +169 -0
- data/lib/websocket_rails/connection_adapters.rb +195 -0
- data/lib/websocket_rails/connection_adapters/http.rb +120 -0
- data/lib/websocket_rails/connection_adapters/web_socket.rb +36 -0
- data/lib/websocket_rails/connection_manager.rb +119 -0
- data/lib/websocket_rails/controller_factory.rb +80 -0
- data/lib/websocket_rails/data_store.rb +145 -0
- data/lib/websocket_rails/dispatcher.rb +129 -0
- data/lib/websocket_rails/engine.rb +26 -0
- data/lib/websocket_rails/event.rb +189 -0
- data/lib/websocket_rails/event_map.rb +184 -0
- data/lib/websocket_rails/event_queue.rb +33 -0
- data/lib/websocket_rails/internal_events.rb +37 -0
- data/lib/websocket_rails/logging.rb +133 -0
- data/lib/websocket_rails/spec_helpers.rb +3 -0
- data/lib/websocket_rails/synchronization.rb +182 -0
- data/lib/websocket_rails/user_manager.rb +276 -0
- data/lib/websocket_rails/version.rb +3 -0
- data/spec/dummy/Rakefile +7 -0
- data/spec/dummy/app/controllers/application_controller.rb +3 -0
- data/spec/dummy/app/controllers/chat_controller.rb +53 -0
- data/spec/dummy/app/helpers/application_helper.rb +2 -0
- data/spec/dummy/app/models/user.rb +2 -0
- data/spec/dummy/app/views/layouts/application.html.erb +14 -0
- data/spec/dummy/config.ru +4 -0
- data/spec/dummy/config/application.rb +45 -0
- data/spec/dummy/config/boot.rb +10 -0
- data/spec/dummy/config/database.yml +22 -0
- data/spec/dummy/config/environment.rb +5 -0
- data/spec/dummy/config/environments/development.rb +26 -0
- data/spec/dummy/config/environments/production.rb +49 -0
- data/spec/dummy/config/environments/test.rb +34 -0
- data/spec/dummy/config/events.rb +7 -0
- data/spec/dummy/config/initializers/backtrace_silencers.rb +7 -0
- data/spec/dummy/config/initializers/inflections.rb +10 -0
- data/spec/dummy/config/initializers/mime_types.rb +5 -0
- data/spec/dummy/config/initializers/secret_token.rb +7 -0
- data/spec/dummy/config/initializers/session_store.rb +8 -0
- data/spec/dummy/config/locales/en.yml +5 -0
- data/spec/dummy/config/routes.rb +58 -0
- data/spec/dummy/db/development.sqlite3 +0 -0
- data/spec/dummy/db/migrate/20130902222552_create_users.rb +10 -0
- data/spec/dummy/db/schema.rb +23 -0
- data/spec/dummy/db/test.sqlite3 +0 -0
- data/spec/dummy/log/development.log +17 -0
- data/spec/dummy/log/production.log +0 -0
- data/spec/dummy/log/server.log +0 -0
- data/spec/dummy/public/404.html +26 -0
- data/spec/dummy/public/422.html +26 -0
- data/spec/dummy/public/500.html +26 -0
- data/spec/dummy/public/favicon.ico +0 -0
- data/spec/dummy/public/javascripts/application.js +2 -0
- data/spec/dummy/public/javascripts/controls.js +965 -0
- data/spec/dummy/public/javascripts/dragdrop.js +974 -0
- data/spec/dummy/public/javascripts/effects.js +1123 -0
- data/spec/dummy/public/javascripts/prototype.js +6001 -0
- data/spec/dummy/public/javascripts/rails.js +202 -0
- data/spec/dummy/script/rails +6 -0
- data/spec/integration/connection_manager_spec.rb +135 -0
- data/spec/javascripts/support/jasmine.yml +52 -0
- data/spec/javascripts/support/jasmine_helper.rb +38 -0
- data/spec/javascripts/support/vendor/sinon-1.7.1.js +4343 -0
- data/spec/javascripts/websocket_rails/channel_spec.coffee +112 -0
- data/spec/javascripts/websocket_rails/event_spec.coffee +69 -0
- data/spec/javascripts/websocket_rails/helpers.coffee +6 -0
- data/spec/javascripts/websocket_rails/websocket_connection_spec.coffee +158 -0
- data/spec/javascripts/websocket_rails/websocket_rails_spec.coffee +274 -0
- data/spec/spec_helper.rb +41 -0
- data/spec/spec_helpers/matchers/route_matchers_spec.rb +109 -0
- data/spec/spec_helpers/matchers/trigger_matchers_spec.rb +247 -0
- data/spec/spec_helpers/spec_helper_event_spec.rb +66 -0
- data/spec/support/helper_methods.rb +42 -0
- data/spec/support/mock_web_socket.rb +41 -0
- data/spec/unit/base_controller_spec.rb +74 -0
- data/spec/unit/channel_manager_spec.rb +58 -0
- data/spec/unit/channel_spec.rb +169 -0
- data/spec/unit/connection_adapters/http_spec.rb +88 -0
- data/spec/unit/connection_adapters/web_socket_spec.rb +30 -0
- data/spec/unit/connection_adapters_spec.rb +259 -0
- data/spec/unit/connection_manager_spec.rb +148 -0
- data/spec/unit/controller_factory_spec.rb +76 -0
- data/spec/unit/data_store_spec.rb +106 -0
- data/spec/unit/dispatcher_spec.rb +203 -0
- data/spec/unit/event_map_spec.rb +120 -0
- data/spec/unit/event_queue_spec.rb +36 -0
- data/spec/unit/event_spec.rb +181 -0
- data/spec/unit/logging_spec.rb +162 -0
- data/spec/unit/synchronization_spec.rb +150 -0
- data/spec/unit/target_validator_spec.rb +88 -0
- data/spec/unit/user_manager_spec.rb +165 -0
- metadata +320 -0
|
@@ -0,0 +1,197 @@
|
|
|
1
|
+
require "websocket_rails/data_store"
|
|
2
|
+
require 'abstract_controller/callbacks'
|
|
3
|
+
|
|
4
|
+
module WebsocketRails
|
|
5
|
+
# Provides controller helper methods for developing a WebsocketRails controller. Action methods
|
|
6
|
+
# defined on a WebsocketRails controller can be mapped to events using the {EventMap} class.
|
|
7
|
+
#
|
|
8
|
+
# == Example WebsocketRails controller
|
|
9
|
+
# class ChatController < WebsocketRails::BaseController
|
|
10
|
+
# # Can be mapped to the :client_connected event in the events.rb file.
|
|
11
|
+
# def new_user
|
|
12
|
+
# send_message :new_message, {:message => 'Welcome to the Chat Room!'}
|
|
13
|
+
# end
|
|
14
|
+
# end
|
|
15
|
+
#
|
|
16
|
+
# It is best to use the provided {DataStore} to temporarily persist data for each client between
|
|
17
|
+
# events. Read more about it in the {DataStore} documentation.
|
|
18
|
+
#
|
|
19
|
+
#
|
|
20
|
+
class BaseController
|
|
21
|
+
|
|
22
|
+
# We need process_action to be in a module loaded before AbstractController::Callbacks
|
|
23
|
+
# to get inheritance properly
|
|
24
|
+
module Metal
|
|
25
|
+
def process_action(method, event)
|
|
26
|
+
if respond_to?(method)
|
|
27
|
+
self.send(method)
|
|
28
|
+
else
|
|
29
|
+
raise EventRoutingError.new(event, self, method)
|
|
30
|
+
end
|
|
31
|
+
end
|
|
32
|
+
def response_body
|
|
33
|
+
false
|
|
34
|
+
end
|
|
35
|
+
end
|
|
36
|
+
|
|
37
|
+
include Metal
|
|
38
|
+
include AbstractController::Callbacks
|
|
39
|
+
|
|
40
|
+
# Tell Rails that BaseController and children can be reloaded when in
|
|
41
|
+
# the Development environment.
|
|
42
|
+
def self.inherited(controller)
|
|
43
|
+
unless controller.name == "WebsocketRails::InternalController" || Rails.version =~/^4/
|
|
44
|
+
unloadable controller
|
|
45
|
+
end
|
|
46
|
+
end
|
|
47
|
+
|
|
48
|
+
# Tell the dispatcher to use channel filtering on specific channels.
|
|
49
|
+
# If supplied, the :catch_all => :method will be processed for every
|
|
50
|
+
# event that comes into the channel(s).
|
|
51
|
+
#
|
|
52
|
+
#
|
|
53
|
+
# Example:
|
|
54
|
+
# To process events based upon the event_name inside :channel_one
|
|
55
|
+
#
|
|
56
|
+
# filter_for_channels :channel_one
|
|
57
|
+
#
|
|
58
|
+
# To process events based upon the event_name and a catch all
|
|
59
|
+
#
|
|
60
|
+
# filter_for_channels :channel_one, :catch_all => :logger_method
|
|
61
|
+
#
|
|
62
|
+
def self.filter_for_channels(*channels)
|
|
63
|
+
options = channels.last.is_a?(Hash) ? channels.pop : {}
|
|
64
|
+
channels.each do |channel|
|
|
65
|
+
WebsocketRails.filtered_channels[channel] = options[:catch_all].nil? ? self : [self, options[:catch_all]]
|
|
66
|
+
end
|
|
67
|
+
end
|
|
68
|
+
|
|
69
|
+
# Provides direct access to the connection object for the client that
|
|
70
|
+
# initiated the event that is currently being executed.
|
|
71
|
+
def connection
|
|
72
|
+
@_event.connection
|
|
73
|
+
end
|
|
74
|
+
|
|
75
|
+
# The numerical ID for the client connection that initiated the event. The ID is unique
|
|
76
|
+
# for each currently active connection but can not be used to associate a client between
|
|
77
|
+
# multiple connection attempts.
|
|
78
|
+
def client_id
|
|
79
|
+
connection.id
|
|
80
|
+
end
|
|
81
|
+
|
|
82
|
+
# The {Event} object that triggered this action.
|
|
83
|
+
# Find the current event name with event.name
|
|
84
|
+
# Access the data sent with the event with event.data
|
|
85
|
+
# Find the event's namespace with event.namespace
|
|
86
|
+
def event
|
|
87
|
+
@_event
|
|
88
|
+
end
|
|
89
|
+
|
|
90
|
+
# The current message that was passed from the client when the event was initiated. The
|
|
91
|
+
# message is typically a standard ruby Hash object. See the README for more information.
|
|
92
|
+
def message
|
|
93
|
+
@_event.data
|
|
94
|
+
end
|
|
95
|
+
alias_method :data, :message
|
|
96
|
+
|
|
97
|
+
# Trigger the success callback function attached to the client event that triggered
|
|
98
|
+
# this action. The object passed to this method will be passed as an argument to
|
|
99
|
+
# the callback function on the client.
|
|
100
|
+
def trigger_success(data=nil)
|
|
101
|
+
event.success = true
|
|
102
|
+
event.data = data
|
|
103
|
+
event.trigger
|
|
104
|
+
end
|
|
105
|
+
|
|
106
|
+
# Trigger the failure callback function attached to the client event that triggered
|
|
107
|
+
# this action. The object passed to this method will be passed as an argument to
|
|
108
|
+
# the callback function on the client.
|
|
109
|
+
def trigger_failure(data=nil)
|
|
110
|
+
event.success = false
|
|
111
|
+
event.data = data
|
|
112
|
+
event.trigger
|
|
113
|
+
end
|
|
114
|
+
|
|
115
|
+
def accept_channel(data=nil)
|
|
116
|
+
channel_name = event.data[:channel]
|
|
117
|
+
WebsocketRails[channel_name].subscribe connection
|
|
118
|
+
trigger_success data
|
|
119
|
+
end
|
|
120
|
+
|
|
121
|
+
def deny_channel(data=nil)
|
|
122
|
+
trigger_failure data
|
|
123
|
+
end
|
|
124
|
+
|
|
125
|
+
def stop_event_propagation!
|
|
126
|
+
event.propagate = false
|
|
127
|
+
end
|
|
128
|
+
|
|
129
|
+
# Sends a message to the client that initiated the current event being executed. Messages
|
|
130
|
+
# are serialized as JSON into a two element Array where the first element is the event
|
|
131
|
+
# and the second element is the message that was passed, typically a Hash.
|
|
132
|
+
#
|
|
133
|
+
# To send an event under a namespace, add the `:namespace => :target_namespace` option.
|
|
134
|
+
#
|
|
135
|
+
# send_message :new_message, message_hash, :namespace => :product
|
|
136
|
+
#
|
|
137
|
+
# Nested namespaces can be passed as an array like the following:
|
|
138
|
+
#
|
|
139
|
+
# send_message :new, message_hash, :namespace => [:products,:glasses]
|
|
140
|
+
#
|
|
141
|
+
# See the {EventMap} documentation for more on mapping namespaced actions.
|
|
142
|
+
def send_message(event_name, message, options={})
|
|
143
|
+
options.merge! :connection => connection, :data => message
|
|
144
|
+
event = Event.new( event_name, options )
|
|
145
|
+
@_dispatcher.send_message event if @_dispatcher.respond_to?(:send_message)
|
|
146
|
+
end
|
|
147
|
+
|
|
148
|
+
# Broadcasts a message to all connected clients. See {#send_message} for message passing details.
|
|
149
|
+
def broadcast_message(event_name, message, options={})
|
|
150
|
+
options.merge! :connection => connection, :data => message
|
|
151
|
+
event = Event.new( event_name, options )
|
|
152
|
+
@_dispatcher.broadcast_message event if @_dispatcher.respond_to?(:broadcast_message)
|
|
153
|
+
end
|
|
154
|
+
|
|
155
|
+
def request
|
|
156
|
+
connection.request
|
|
157
|
+
end
|
|
158
|
+
|
|
159
|
+
def action_name
|
|
160
|
+
@_action_name
|
|
161
|
+
end
|
|
162
|
+
|
|
163
|
+
# Provides access to the {DataStore} for the current controller. The {DataStore} provides convenience
|
|
164
|
+
# methods for keeping track of data associated with active connections. See it's documentation for
|
|
165
|
+
# more information.
|
|
166
|
+
def controller_store
|
|
167
|
+
@_controller_store
|
|
168
|
+
end
|
|
169
|
+
|
|
170
|
+
def connection_store
|
|
171
|
+
connection.data_store
|
|
172
|
+
end
|
|
173
|
+
|
|
174
|
+
def self.controller_name
|
|
175
|
+
self.name.underscore.gsub(/_controller$/,'')
|
|
176
|
+
end
|
|
177
|
+
|
|
178
|
+
def controller_name
|
|
179
|
+
self.class.controller_name
|
|
180
|
+
end
|
|
181
|
+
|
|
182
|
+
private
|
|
183
|
+
|
|
184
|
+
def delegate
|
|
185
|
+
connection.controller_delegate
|
|
186
|
+
end
|
|
187
|
+
|
|
188
|
+
def method_missing(method,*args,&block)
|
|
189
|
+
if delegate.respond_to? method
|
|
190
|
+
delegate.send method, *args, &block
|
|
191
|
+
else
|
|
192
|
+
super
|
|
193
|
+
end
|
|
194
|
+
end
|
|
195
|
+
|
|
196
|
+
end
|
|
197
|
+
end
|
|
@@ -0,0 +1,97 @@
|
|
|
1
|
+
module WebsocketRails
|
|
2
|
+
class Channel
|
|
3
|
+
|
|
4
|
+
include Logging
|
|
5
|
+
|
|
6
|
+
delegate :config, :channel_tokens, :channel_manager, :filtered_channels, :to => WebsocketRails
|
|
7
|
+
|
|
8
|
+
attr_reader :name, :subscribers
|
|
9
|
+
|
|
10
|
+
def initialize(channel_name)
|
|
11
|
+
@subscribers = []
|
|
12
|
+
@name = channel_name
|
|
13
|
+
@private = false
|
|
14
|
+
end
|
|
15
|
+
|
|
16
|
+
def subscribe(connection)
|
|
17
|
+
info "#{connection} subscribed to channel #{@name}"
|
|
18
|
+
trigger 'subscriber_join', connection.user if config.broadcast_subscriber_events?
|
|
19
|
+
@subscribers << connection
|
|
20
|
+
send_token connection
|
|
21
|
+
end
|
|
22
|
+
|
|
23
|
+
def unsubscribe(connection)
|
|
24
|
+
return unless @subscribers.include? connection
|
|
25
|
+
info "#{connection} unsubscribed from channel #{@name}"
|
|
26
|
+
@subscribers.delete connection
|
|
27
|
+
trigger 'subscriber_part', connection.user if config.broadcast_subscriber_events?
|
|
28
|
+
end
|
|
29
|
+
|
|
30
|
+
def trigger(event_name,data={},options={})
|
|
31
|
+
options.merge! :channel => @name, :token => token
|
|
32
|
+
options[:data] = data
|
|
33
|
+
|
|
34
|
+
event = Event.new event_name, options
|
|
35
|
+
|
|
36
|
+
info "[#{@name}] #{event.data.inspect}"
|
|
37
|
+
send_data event
|
|
38
|
+
end
|
|
39
|
+
|
|
40
|
+
def trigger_event(event)
|
|
41
|
+
return if event.token != token
|
|
42
|
+
info "[#{@name}] #{event.data.inspect}"
|
|
43
|
+
send_data event
|
|
44
|
+
end
|
|
45
|
+
|
|
46
|
+
def make_private
|
|
47
|
+
unless config.keep_subscribers_when_private?
|
|
48
|
+
@subscribers.clear
|
|
49
|
+
end
|
|
50
|
+
@private = true
|
|
51
|
+
end
|
|
52
|
+
|
|
53
|
+
def filter_with(controller, catch_all=nil)
|
|
54
|
+
filtered_channels[@name] = catch_all.nil? ? controller : [controller, catch_all]
|
|
55
|
+
end
|
|
56
|
+
|
|
57
|
+
def is_private?
|
|
58
|
+
@private
|
|
59
|
+
end
|
|
60
|
+
|
|
61
|
+
def token
|
|
62
|
+
@token ||= channel_tokens[@name] ||= generate_unique_token
|
|
63
|
+
end
|
|
64
|
+
|
|
65
|
+
private
|
|
66
|
+
|
|
67
|
+
def generate_unique_token
|
|
68
|
+
begin
|
|
69
|
+
new_token = SecureRandom.uuid
|
|
70
|
+
end while channel_tokens.values.include?(new_token)
|
|
71
|
+
|
|
72
|
+
new_token
|
|
73
|
+
end
|
|
74
|
+
|
|
75
|
+
def send_token(connection)
|
|
76
|
+
options = {
|
|
77
|
+
:channel => @name,
|
|
78
|
+
:data => {:token => token},
|
|
79
|
+
:connection => connection
|
|
80
|
+
}
|
|
81
|
+
info 'sending token'
|
|
82
|
+
Event.new('websocket_rails.channel_token', options).trigger
|
|
83
|
+
end
|
|
84
|
+
|
|
85
|
+
def send_data(event)
|
|
86
|
+
return unless event.should_propagate?
|
|
87
|
+
if WebsocketRails.synchronize? && event.server_token.nil?
|
|
88
|
+
Synchronization.publish event
|
|
89
|
+
end
|
|
90
|
+
|
|
91
|
+
@subscribers.each do |subscriber|
|
|
92
|
+
subscriber.trigger event
|
|
93
|
+
end
|
|
94
|
+
end
|
|
95
|
+
|
|
96
|
+
end
|
|
97
|
+
end
|
|
@@ -0,0 +1,55 @@
|
|
|
1
|
+
require 'redis-objects'
|
|
2
|
+
|
|
3
|
+
module WebsocketRails
|
|
4
|
+
|
|
5
|
+
class << self
|
|
6
|
+
|
|
7
|
+
def channel_manager
|
|
8
|
+
@channel_manager ||= ChannelManager.new
|
|
9
|
+
end
|
|
10
|
+
|
|
11
|
+
def [](channel)
|
|
12
|
+
channel_manager[channel]
|
|
13
|
+
end
|
|
14
|
+
|
|
15
|
+
def channel_tokens
|
|
16
|
+
channel_manager.channel_tokens
|
|
17
|
+
end
|
|
18
|
+
|
|
19
|
+
def filtered_channels
|
|
20
|
+
channel_manager.filtered_channels
|
|
21
|
+
end
|
|
22
|
+
|
|
23
|
+
end
|
|
24
|
+
|
|
25
|
+
class ChannelManager
|
|
26
|
+
|
|
27
|
+
attr_reader :channels, :filtered_channels
|
|
28
|
+
|
|
29
|
+
def initialize
|
|
30
|
+
@channels = {}.with_indifferent_access
|
|
31
|
+
@filtered_channels = {}.with_indifferent_access
|
|
32
|
+
end
|
|
33
|
+
|
|
34
|
+
def channel_tokens
|
|
35
|
+
@channel_tokens ||= begin
|
|
36
|
+
if WebsocketRails.synchronize?
|
|
37
|
+
::Redis::HashKey.new('websocket_rails.channel_tokens', Synchronization.redis)
|
|
38
|
+
else
|
|
39
|
+
{}
|
|
40
|
+
end
|
|
41
|
+
end
|
|
42
|
+
end
|
|
43
|
+
|
|
44
|
+
def [](channel)
|
|
45
|
+
@channels[channel] ||= Channel.new channel
|
|
46
|
+
end
|
|
47
|
+
|
|
48
|
+
def unsubscribe(connection)
|
|
49
|
+
@channels.each do |channel_name, channel|
|
|
50
|
+
channel.unsubscribe(connection)
|
|
51
|
+
end
|
|
52
|
+
end
|
|
53
|
+
|
|
54
|
+
end
|
|
55
|
+
end
|
|
@@ -0,0 +1,169 @@
|
|
|
1
|
+
module WebsocketRails
|
|
2
|
+
class Configuration
|
|
3
|
+
|
|
4
|
+
def user_identifier
|
|
5
|
+
@user_identifier ||= :id
|
|
6
|
+
end
|
|
7
|
+
|
|
8
|
+
def user_identifier=(identifier)
|
|
9
|
+
@user_identifier = identifier
|
|
10
|
+
end
|
|
11
|
+
|
|
12
|
+
def user_class
|
|
13
|
+
@user_class ||= User
|
|
14
|
+
end
|
|
15
|
+
|
|
16
|
+
def user_class=(klass)
|
|
17
|
+
@user_class = klass
|
|
18
|
+
end
|
|
19
|
+
|
|
20
|
+
def keep_subscribers_when_private?
|
|
21
|
+
@keep_subscribers_when_private ||= false
|
|
22
|
+
end
|
|
23
|
+
|
|
24
|
+
def keep_subscribers_when_private=(value)
|
|
25
|
+
@keep_subscribers_when_private = value
|
|
26
|
+
end
|
|
27
|
+
|
|
28
|
+
def allowed_origins
|
|
29
|
+
# allows the value to be string or array
|
|
30
|
+
[@allowed_origins].flatten.compact.uniq ||= []
|
|
31
|
+
end
|
|
32
|
+
|
|
33
|
+
def allowed_origins=(value)
|
|
34
|
+
@allowed_origins = value
|
|
35
|
+
end
|
|
36
|
+
|
|
37
|
+
def broadcast_subscriber_events?
|
|
38
|
+
@broadcast_subscriber_events ||= false
|
|
39
|
+
end
|
|
40
|
+
|
|
41
|
+
def broadcast_subscriber_events=(value)
|
|
42
|
+
@broadcast_subscriber_events = value
|
|
43
|
+
end
|
|
44
|
+
|
|
45
|
+
def route_block=(routes)
|
|
46
|
+
@event_routes = routes
|
|
47
|
+
end
|
|
48
|
+
|
|
49
|
+
def route_block
|
|
50
|
+
@event_routes
|
|
51
|
+
end
|
|
52
|
+
|
|
53
|
+
def log_level
|
|
54
|
+
@log_level ||= begin
|
|
55
|
+
case Rails.env.to_sym
|
|
56
|
+
when :production then :info
|
|
57
|
+
when :development then :debug
|
|
58
|
+
end
|
|
59
|
+
end
|
|
60
|
+
end
|
|
61
|
+
|
|
62
|
+
def log_level=(level)
|
|
63
|
+
@log_level = level
|
|
64
|
+
end
|
|
65
|
+
|
|
66
|
+
def logger
|
|
67
|
+
@logger ||= begin
|
|
68
|
+
logger = Logger.new(log_path)
|
|
69
|
+
Logging.configure(logger)
|
|
70
|
+
end
|
|
71
|
+
end
|
|
72
|
+
|
|
73
|
+
def logger=(logger)
|
|
74
|
+
@logger = logger
|
|
75
|
+
end
|
|
76
|
+
|
|
77
|
+
def log_path
|
|
78
|
+
@log_path ||= "#{Rails.root}/log/websocket_rails.log"
|
|
79
|
+
end
|
|
80
|
+
|
|
81
|
+
def log_path=(path)
|
|
82
|
+
@log_path = path
|
|
83
|
+
end
|
|
84
|
+
|
|
85
|
+
def log_internal_events?
|
|
86
|
+
@log_internal_events ||= false
|
|
87
|
+
end
|
|
88
|
+
|
|
89
|
+
def log_internal_events=(value)
|
|
90
|
+
@log_internal_events = value
|
|
91
|
+
end
|
|
92
|
+
|
|
93
|
+
def daemonize?
|
|
94
|
+
@daemonize.nil? ? true : @daemonize
|
|
95
|
+
end
|
|
96
|
+
|
|
97
|
+
def daemonize=(value)
|
|
98
|
+
@daemonize = value
|
|
99
|
+
end
|
|
100
|
+
|
|
101
|
+
def synchronize
|
|
102
|
+
@synchronize ||= false
|
|
103
|
+
end
|
|
104
|
+
|
|
105
|
+
def synchronize=(synchronize)
|
|
106
|
+
@synchronize = synchronize
|
|
107
|
+
end
|
|
108
|
+
|
|
109
|
+
def redis_options
|
|
110
|
+
@redis_options ||= redis_defaults
|
|
111
|
+
end
|
|
112
|
+
|
|
113
|
+
def redis_options=(options = {})
|
|
114
|
+
@redis_options = redis_defaults.merge(options)
|
|
115
|
+
end
|
|
116
|
+
|
|
117
|
+
def redis_defaults
|
|
118
|
+
{:host => '127.0.0.1', :port => 6379, :driver => :synchrony}
|
|
119
|
+
end
|
|
120
|
+
|
|
121
|
+
def standalone
|
|
122
|
+
@standalone ||= false
|
|
123
|
+
end
|
|
124
|
+
|
|
125
|
+
def standalone=(standalone)
|
|
126
|
+
@standalone = standalone
|
|
127
|
+
end
|
|
128
|
+
|
|
129
|
+
def standalone_port
|
|
130
|
+
@standalone_port ||= '3001'
|
|
131
|
+
end
|
|
132
|
+
|
|
133
|
+
def standalone_port=(port)
|
|
134
|
+
@standalone_port = port
|
|
135
|
+
end
|
|
136
|
+
|
|
137
|
+
def thin_options
|
|
138
|
+
@thin_options ||= thin_defaults
|
|
139
|
+
end
|
|
140
|
+
|
|
141
|
+
def thin_options=(options = {})
|
|
142
|
+
@thin_options = thin_defaults.merge(options)
|
|
143
|
+
end
|
|
144
|
+
|
|
145
|
+
def thin_defaults
|
|
146
|
+
{
|
|
147
|
+
:port => standalone_port,
|
|
148
|
+
:pid => "#{Rails.root}/tmp/pids/websocket_rails.pid",
|
|
149
|
+
:log => "#{Rails.root}/log/websocket_rails_server.log",
|
|
150
|
+
:tag => 'websocket_rails',
|
|
151
|
+
:rackup => "#{Rails.root}/config.ru",
|
|
152
|
+
:threaded => false,
|
|
153
|
+
:daemonize => daemonize?,
|
|
154
|
+
:dirname => Rails.root,
|
|
155
|
+
:max_persistent_conns => 1024,
|
|
156
|
+
:max_conns => 1024
|
|
157
|
+
}
|
|
158
|
+
end
|
|
159
|
+
|
|
160
|
+
def default_ping_interval
|
|
161
|
+
@default_ping_interval ||= 10
|
|
162
|
+
end
|
|
163
|
+
|
|
164
|
+
def default_ping_interval=(interval)
|
|
165
|
+
@default_ping_interval = interval.to_i
|
|
166
|
+
end
|
|
167
|
+
|
|
168
|
+
end
|
|
169
|
+
end
|