sock-drawer 0.0.3 → 0.1.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 +4 -4
- data/.gitignore +1 -1
- data/README.md +58 -8
- data/lib/sock/client.rb +3 -9
- data/lib/sock/drawer.rb +1 -0
- data/lib/sock/drawer/version.rb +1 -1
- data/lib/sock/server.rb +16 -3
- data/lib/sock/subscriber.rb +18 -0
- data/spec/client_spec.rb +5 -24
- data/spec/mock_class.rb +17 -0
- data/spec/server_spec.rb +21 -2
- data/spec/spec_helper.rb +1 -1
- data/spec/subscriber_spec.rb +15 -0
- metadata +7 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: a2e3e0c5fd32ba6df30d8b2d50fec26a94bbcf51
|
4
|
+
data.tar.gz: 0fd0deb7386a08d81f8a70a427282bab09b2b490
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: df26b6ff39efb6fb87292133e728c250728cd54a0f1cc819a0f41b555fea95eca245c32f650e839774182108c72c84c1cf100252b98e34332e20114ef8b36f14
|
7
|
+
data.tar.gz: 753591b431fc63947bdf19836258fe6397431287052a93709938fcc74e99e896525acab419172b30f669615756697d6091ef691d5957bded4b9069706e07b1a5
|
data/.gitignore
CHANGED
data/README.md
CHANGED
@@ -25,26 +25,28 @@ Or install it yourself as:
|
|
25
25
|
|
26
26
|
## Usage
|
27
27
|
|
28
|
-
Initialize a instance of the sock client
|
28
|
+
Initialize a instance of the sock-drawer client
|
29
29
|
|
30
30
|
```Ruby
|
31
31
|
sock = Sock::Client.new(logger: Rails.logger, redis: redis)
|
32
32
|
```
|
33
33
|
|
34
|
+
### Publishing
|
35
|
+
|
34
36
|
Publish an event on a channel,
|
35
37
|
|
36
38
|
```Ruby
|
37
|
-
sock.pub("my message",
|
39
|
+
sock.pub("my message", channel: "my-channel")
|
38
40
|
```
|
39
41
|
|
40
|
-
|
42
|
+
or publish to all channels,
|
41
43
|
|
42
44
|
```Ruby
|
43
|
-
sock.
|
44
|
-
puts message
|
45
|
-
end
|
45
|
+
sock.pub("my message")
|
46
46
|
```
|
47
47
|
|
48
|
+
### Receiving in Javascript
|
49
|
+
|
48
50
|
To capture the event in Javascript use something like,
|
49
51
|
|
50
52
|
```javascript
|
@@ -55,9 +57,57 @@ webSocket.onmessage = function(event) {
|
|
55
57
|
}
|
56
58
|
```
|
57
59
|
|
58
|
-
|
60
|
+
### Subscribing
|
61
|
+
|
62
|
+
Create a class to handle redis events like,
|
63
|
+
|
64
|
+
```Ruby
|
65
|
+
class MyListener
|
66
|
+
include Sock::Subscriber
|
67
|
+
|
68
|
+
on 'echo' do |msg|
|
69
|
+
msg
|
70
|
+
end
|
71
|
+
end
|
72
|
+
```
|
73
|
+
|
74
|
+
Then register your listener with the server
|
75
|
+
|
76
|
+
```Ruby
|
77
|
+
Sock::Server.new(listener: MockClass)
|
78
|
+
```
|
79
|
+
|
80
|
+
Whenever an event is fired on the `sock-hook/echo` channel the block will be executed.
|
81
|
+
|
82
|
+
|
83
|
+
### Configuration
|
84
|
+
|
85
|
+
you can configure your sock server to run as a rake task like,
|
86
|
+
|
87
|
+
```Ruby
|
88
|
+
namespace :sock do
|
89
|
+
desc 'start the sock-drawer server to manage socket connections'
|
90
|
+
task :server do
|
91
|
+
Sock::Server.new.start!
|
92
|
+
end
|
93
|
+
end
|
94
|
+
```
|
95
|
+
|
96
|
+
Then run it with `rake sock:server`
|
97
|
+
Current supported configuration options:
|
98
|
+
|
99
|
+
| keyword arg | default |
|
100
|
+
| ----------- | ------- |
|
101
|
+
| name | 'sock-hook'
|
102
|
+
| logger | Logger.new(STDOUT) |
|
103
|
+
| socket_params | { host: '0.0.0.0', port: 8020 } |
|
104
|
+
| mode | 'default' |
|
105
|
+
| listener | N/A |
|
106
|
+
|
107
|
+
## Wish List
|
59
108
|
|
60
|
-
|
109
|
+
- Right now all configuration is passed into new, it would be nice to read from a config file
|
110
|
+
- There isn't a way of having multiple event handlers. Should be easy to pass multiple in or intelligently find them (given some convention)
|
61
111
|
|
62
112
|
And you are good to go!
|
63
113
|
|
data/lib/sock/client.rb
CHANGED
@@ -10,15 +10,9 @@ module Sock
|
|
10
10
|
end
|
11
11
|
|
12
12
|
# send a message to all subscribed listeners.
|
13
|
-
def pub(msg,
|
14
|
-
@logger.info "sending #{msg} on channel: #{channel_name(
|
15
|
-
@redis.publish(channel_name(
|
16
|
-
end
|
17
|
-
|
18
|
-
# subscribe to all events fired on a given channel
|
19
|
-
def sub(server, channel, &block)
|
20
|
-
@logger.info "subscribing to #{channel}"
|
21
|
-
server.channel(channel_name(channel)).subscribe { |msg| block.call(msg) }
|
13
|
+
def pub(msg, channel: '')
|
14
|
+
@logger.info "sending #{msg} on channel: #{channel_name(channel)}"
|
15
|
+
@redis.publish(channel_name(channel), msg)
|
22
16
|
end
|
23
17
|
|
24
18
|
private
|
data/lib/sock/drawer.rb
CHANGED
data/lib/sock/drawer/version.rb
CHANGED
data/lib/sock/server.rb
CHANGED
@@ -1,3 +1,5 @@
|
|
1
|
+
require 'json'
|
2
|
+
|
1
3
|
module Sock
|
2
4
|
# server provides a EM process that will manage websocket connections
|
3
5
|
class Server
|
@@ -5,23 +7,26 @@ module Sock
|
|
5
7
|
def initialize(name: DEFAULT_NAME,
|
6
8
|
logger: Logger.new(STDOUT),
|
7
9
|
socket_params: { host: HOST, port: PORT },
|
8
|
-
mode: 'default'
|
10
|
+
mode: 'default',
|
11
|
+
listener: nil)
|
9
12
|
@name = name
|
10
13
|
@socket_params = socket_params
|
11
14
|
@channels = {}
|
12
15
|
@logger = logger
|
13
16
|
@mode = mode
|
17
|
+
@listener = listener
|
14
18
|
end
|
15
19
|
|
16
20
|
# utility method used to subscribe on the default name and start the socket server
|
17
21
|
def start!
|
18
22
|
EM.run do
|
23
|
+
register!
|
19
24
|
subscribe(@name)
|
20
25
|
socket_start_listening
|
21
26
|
end
|
22
27
|
end
|
23
28
|
|
24
|
-
# subscribe fires a event on a EM channel whenever a message is fired on a pattern matching
|
29
|
+
# subscribe fires a event on a EM channel whenever a message is fired on a pattern matching `name`.
|
25
30
|
# @name (default: "sock-hook/") + '*'
|
26
31
|
def subscribe(subscription)
|
27
32
|
@logger.info "Subscribing to: #{subscription + '*'}"
|
@@ -38,7 +43,6 @@ module Sock
|
|
38
43
|
@channels[channel_name] ||= EM::Channel.new
|
39
44
|
end
|
40
45
|
|
41
|
-
|
42
46
|
# starts the websocket server
|
43
47
|
# on open this server will find a new channel based on the path
|
44
48
|
# on message it will fire an event to the default 'incoming-hook' channel.
|
@@ -51,6 +55,15 @@ module Sock
|
|
51
55
|
end
|
52
56
|
end
|
53
57
|
|
58
|
+
def register!
|
59
|
+
@listener.channels.each do |chan, block|
|
60
|
+
subscribe(@name + '/' + chan)
|
61
|
+
channel(@name + '/' + chan).subscribe { |msg|
|
62
|
+
block.call(msg)
|
63
|
+
}
|
64
|
+
end
|
65
|
+
end
|
66
|
+
|
54
67
|
private
|
55
68
|
|
56
69
|
def handle_open(ws)
|
@@ -0,0 +1,18 @@
|
|
1
|
+
module Sock
|
2
|
+
# module for catching events fired from redis
|
3
|
+
module Subscriber
|
4
|
+
def self.included(base)
|
5
|
+
base.extend(SubscriberDSL)
|
6
|
+
end
|
7
|
+
|
8
|
+
module SubscriberDSL
|
9
|
+
def on(channel, &block)
|
10
|
+
channels[channel] = block
|
11
|
+
end
|
12
|
+
|
13
|
+
def channels
|
14
|
+
@_channels ||= {}
|
15
|
+
end
|
16
|
+
end
|
17
|
+
end
|
18
|
+
end
|
data/spec/client_spec.rb
CHANGED
@@ -1,34 +1,15 @@
|
|
1
1
|
require 'spec_helper'
|
2
2
|
require 'logger'
|
3
|
+
require 'mock_class'
|
3
4
|
|
4
5
|
RSpec.describe Sock::Drawer do
|
5
|
-
let(:redis) { Redis.new }
|
6
|
-
let(:sock) { Sock::Client.new(redis: redis, logger: Logger.new(nil)) }
|
7
|
-
|
8
6
|
context '#pub' do
|
7
|
+
let(:redis) { Redis.new }
|
8
|
+
let(:sock) { Sock::Client.new(redis: redis, logger: Logger.new(nil)) }
|
9
|
+
|
9
10
|
it 'subscribes to events from redis with that name' do
|
10
11
|
expect(redis).to receive(:publish).with('sock-hook/new_channel', 'hi')
|
11
|
-
sock.pub('hi',
|
12
|
-
end
|
13
|
-
end
|
14
|
-
|
15
|
-
context '#sub' do
|
16
|
-
let(:server) { Sock::Server.new(logger: Logger.new(nil)) }
|
17
|
-
let(:hi_redis) { EM::Hiredis.connect }
|
18
|
-
|
19
|
-
it 'can register a callback to be run when a event comes through redis' do
|
20
|
-
steps :fire, :received
|
21
|
-
sock.sub(server, 'hi') { |msg|
|
22
|
-
expect(msg).to eq('hi there')
|
23
|
-
complete :received
|
24
|
-
}
|
25
|
-
event_block do
|
26
|
-
server.subscribe(server.name).callback do
|
27
|
-
hi_redis.publish('sock-hook/hi', 'hi there').callback do
|
28
|
-
complete :fire
|
29
|
-
end
|
30
|
-
end
|
31
|
-
end
|
12
|
+
sock.pub('hi', channel: 'new_channel')
|
32
13
|
end
|
33
14
|
end
|
34
15
|
end
|
data/spec/mock_class.rb
ADDED
data/spec/server_spec.rb
CHANGED
@@ -1,7 +1,6 @@
|
|
1
1
|
require 'spec_helper'
|
2
2
|
require 'em-websocket-client'
|
3
|
-
|
4
|
-
# TODO rename to server spec
|
3
|
+
require 'json'
|
5
4
|
|
6
5
|
RSpec.describe Sock::Server do
|
7
6
|
let(:server) { Sock::Server.new(logger: Logger.new(nil)) }
|
@@ -50,6 +49,26 @@ RSpec.describe Sock::Server do
|
|
50
49
|
end
|
51
50
|
end
|
52
51
|
|
52
|
+
context 'listener' do
|
53
|
+
let(:server) {
|
54
|
+
Sock::Server.new(logger: Logger.new(nil), listener: MockClass)
|
55
|
+
}
|
56
|
+
it 'will fire a ruby event when a server event comes in' do
|
57
|
+
allow(MockClass).to receive(:test_method)
|
58
|
+
steps :fire
|
59
|
+
event_block do
|
60
|
+
server.register!
|
61
|
+
hi_redis.publish('sock-hook/test', 'success').callback {
|
62
|
+
expect(server.channels.keys).to eq(['sock-hook/hi',
|
63
|
+
'sock-hook/echo',
|
64
|
+
'sock-hook/test'])
|
65
|
+
expect(MockClass).to have_received(:test_method)
|
66
|
+
complete :fire
|
67
|
+
}
|
68
|
+
end
|
69
|
+
end
|
70
|
+
end
|
71
|
+
|
53
72
|
context '#channel' do
|
54
73
|
it 'finds or creates a channel' do
|
55
74
|
server.channel('heyo')
|
data/spec/spec_helper.rb
CHANGED
@@ -5,7 +5,7 @@ require 'pry'
|
|
5
5
|
require 'codeclimate-test-reporter'
|
6
6
|
require 'simplecov'
|
7
7
|
|
8
|
-
SimpleCov.formatter = SimpleCov::Formatter::MultiFormatter[SimpleCov::Formatter::HTMLFormatter,CodeClimate::TestReporter::Formatter]
|
8
|
+
SimpleCov.formatter = SimpleCov::Formatter::MultiFormatter[SimpleCov::Formatter::HTMLFormatter, CodeClimate::TestReporter::Formatter]
|
9
9
|
|
10
10
|
dir = File.join("..", "coverage")
|
11
11
|
SimpleCov.coverage_dir(dir)
|
@@ -0,0 +1,15 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
require 'logger'
|
3
|
+
require 'mock_class'
|
4
|
+
|
5
|
+
RSpec.describe Sock::Subscriber do
|
6
|
+
context 'when included' do
|
7
|
+
it 'runs the block when that event fires' do
|
8
|
+
expect(MockClass.channels['hi'].call('hello')).to eq('success')
|
9
|
+
end
|
10
|
+
|
11
|
+
it 'can access the msg' do
|
12
|
+
expect(MockClass.channels['echo'].call('hello')).to eq('hello')
|
13
|
+
end
|
14
|
+
end
|
15
|
+
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: sock-drawer
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.0
|
4
|
+
version: 0.1.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Adam Hess
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2015-09-
|
11
|
+
date: 2015-09-30 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: redis
|
@@ -169,10 +169,13 @@ files:
|
|
169
169
|
- lib/sock/drawer.rb
|
170
170
|
- lib/sock/drawer/version.rb
|
171
171
|
- lib/sock/server.rb
|
172
|
+
- lib/sock/subscriber.rb
|
172
173
|
- sock-drawer.gemspec
|
173
174
|
- spec/client_spec.rb
|
175
|
+
- spec/mock_class.rb
|
174
176
|
- spec/server_spec.rb
|
175
177
|
- spec/spec_helper.rb
|
178
|
+
- spec/subscriber_spec.rb
|
176
179
|
homepage: http://www.thisisadam.me
|
177
180
|
licenses:
|
178
181
|
- MIT
|
@@ -199,5 +202,7 @@ specification_version: 4
|
|
199
202
|
summary: Super simple websocket manager.
|
200
203
|
test_files:
|
201
204
|
- spec/client_spec.rb
|
205
|
+
- spec/mock_class.rb
|
202
206
|
- spec/server_spec.rb
|
203
207
|
- spec/spec_helper.rb
|
208
|
+
- spec/subscriber_spec.rb
|