jugglite 0.4.0 → 0.5.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: edc6fd8a925f529423f772ed4493aec51792f0bb
4
- data.tar.gz: 45a96b192198b88cdb63d870864438190e671e5b
3
+ metadata.gz: 1b81b7cc5bc16c5f0fe6377c9f26217631a8bf0a
4
+ data.tar.gz: 38d82a7c27038f3f9fa2dbac6fa424ae594989fe
5
5
  SHA512:
6
- metadata.gz: 19a58f0d57d06b71e5bcc17d559697deff5d74cecac1955888725f1f0ce0c1a7cdee697f50713c33f06f3660a0eeb2e041d5f2216440c372ef438b2e86e6693b
7
- data.tar.gz: 468cb7af0fcd57f9dcbb00021439773ed9ce595d0c905e0b015e231cff5ca9a103ec942483151d94f01a77068ac49569427f7885f75b125cbb8b5c548978ebd1
6
+ metadata.gz: 50dbbe1c5535754c7887ec7fbfb2cd7ed63099c9875b46f03b303ea24c82fd008a760b0bc1c2f63e6c1428b1acacf816463af8ad2f2c5228fd67918bf55df88f
7
+ data.tar.gz: 0b8c90aac69b801d2cfc3eef9d6fde260bf73c6db28c75fb36efeb984dce54c8c85820859b3e919c3cc5e57c65ebae25f0a2b84ee84d3817dfd0da1253cd7bd8
data/CHANGELOG CHANGED
@@ -1,3 +1,7 @@
1
+ = 0.5.0 / 2014-05-03
2
+
3
+ * New option: +allowed_channels+ to limit/authorize which channels a request can listen to
4
+
1
5
  = 0.4.0 / 2014-03-12
2
6
 
3
7
  * Support for listening to multiple channels
@@ -11,8 +11,12 @@ module Jugglite
11
11
  }
12
12
 
13
13
  # Options include:
14
- # +path+ : the URI path to listen to ('/stream')
15
- # +keepalive_timeout+ : the timeout in seconds between keepalive comments
14
+ # +path+ : the URI path to listen to (defaults to '/stream')
15
+ # +keepalive_timeout+ : the timeout in seconds between keepalive comments (defaults to 20)
16
+ # +namespace+ : a namespace used as prefix for redis pubsub channels
17
+ # +allowed_channels+ :
18
+ # * an array with allowed channel names
19
+ # * a proc that takes a Rack::Request and returns an array of allowed channels for that particular request
16
20
  def initialize(app = nil, options = {})
17
21
  @app = app
18
22
  @options = {
@@ -51,7 +55,7 @@ module Jugglite
51
55
  connection.callback { unregister_connection(connection) }
52
56
  connection.errback { unregister_connection(connection) }
53
57
 
54
- # Needed for crappy Rack::Lint
58
+ # Needed for Rack::Lint
55
59
  throw :async
56
60
 
57
61
  # Returning a status of -1 keeps the connection open
@@ -77,12 +81,21 @@ module Jugglite
77
81
  end
78
82
 
79
83
  def channels_for_request(request)
80
- # TODO: Sanitize? Check signature?
81
84
  channels = Array(request.params["channel"].split(","))
85
+ # Sanitize channels
86
+ channels = channels & allowed_channels(request) if @options[:allowed_channels]
82
87
  channels.map! { |channel| @options[:namespace] + channel }
83
88
  Set.new(channels)
84
89
  end
85
90
 
91
+ def allowed_channels(request)
92
+ case @options[:allowed_channels]
93
+ when Proc then @options[:allowed_channels].call(request)
94
+ when Array then @options[:allowed_channels]
95
+ else raise(ArgumentError, ":allowed_channels should be nil, Array or a Proc")
96
+ end
97
+ end
98
+
86
99
  def register_connection(connection)
87
100
  requested_channels = channels_for_request(connection.request)
88
101
  subscribe_to_new_channels(requested_channels - @redis_channels)
@@ -1,3 +1,3 @@
1
1
  module Jugglite
2
- VERSION = "0.4.0"
2
+ VERSION = "0.5.0"
3
3
  end
@@ -0,0 +1,79 @@
1
+ require 'spec_helper'
2
+ require 'net/http'
3
+
4
+ def start_server(jugglite)
5
+ @app = nil
6
+ @thread = Thread.new do
7
+ @app = Thin::Server.new(@host, @port, jugglite)
8
+ @app.start
9
+ end
10
+ sleep(0.01) until @app && @app.running?
11
+ end
12
+
13
+ def stop_server
14
+ @app.stop!
15
+ @thread.join
16
+ end
17
+
18
+ describe "allowed_channels" do
19
+ before(:each) do
20
+ @host = '127.0.0.1'
21
+ @port = rand(10000)+10000
22
+ @channel1 = "randomized:test:#{rand(2**32)}"
23
+ @channel2 = "randomized:test:#{rand(2**32)}"
24
+ end
25
+
26
+ after(:each) do
27
+ stop_server
28
+ end
29
+
30
+ describe "as an array" do
31
+ before(:each) do
32
+ @jugglite = Jugglite::App.new(nil, allowed_channels: [@channel1])
33
+ start_server(@jugglite)
34
+ end
35
+
36
+ it "should only registers to channel 1" do
37
+ Net::HTTP.start(@host, @port) do |http|
38
+ request = Net::HTTP::Get.new("/?channel=#{@channel1},#{@channel2}")
39
+
40
+ body = ""
41
+ http.request(request) do |response|
42
+ response.read_body do |chunk|
43
+ body << chunk
44
+ body.should include(": registered to channels: #{@channel1}")
45
+ body.should_not include(@channel2)
46
+ http.finish
47
+ break
48
+ end
49
+ break
50
+ end
51
+ end
52
+ end
53
+ end
54
+
55
+ describe "as a Proc" do
56
+ before(:each) do
57
+ @jugglite = Jugglite::App.new(nil, allowed_channels: ->(request) { [@channel2] })
58
+ start_server(@jugglite)
59
+ end
60
+
61
+ it "should only registers to channel 2" do
62
+ Net::HTTP.start(@host, @port) do |http|
63
+ request = Net::HTTP::Get.new("/?channel=#{@channel1},#{@channel2}")
64
+
65
+ body = ""
66
+ http.request(request) do |response|
67
+ response.read_body do |chunk|
68
+ body << chunk
69
+ body.should include(": registered to channels: #{@channel2}")
70
+ body.should_not include(@channel1)
71
+ http.finish
72
+ break
73
+ end
74
+ break
75
+ end
76
+ end
77
+ end
78
+ end
79
+ end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: jugglite
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.4.0
4
+ version: 0.5.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - andruby
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2014-03-12 00:00:00.000000000 Z
11
+ date: 2014-06-03 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: thin
@@ -89,6 +89,7 @@ files:
89
89
  - lib/jugglite/deferrable_body.rb
90
90
  - lib/jugglite/sse_connection.rb
91
91
  - lib/jugglite/version.rb
92
+ - spec/acceptance/allowed_channels_spec.rb
92
93
  - spec/acceptance/stream_and_publish_spec.rb
93
94
  - spec/benchmark/max_connections.rb
94
95
  - spec/spec_helper.rb
@@ -111,12 +112,13 @@ required_rubygems_version: !ruby/object:Gem::Requirement
111
112
  version: '0'
112
113
  requirements: []
113
114
  rubyforge_project:
114
- rubygems_version: 2.2.1
115
+ rubygems_version: 2.2.2
115
116
  signing_key:
116
117
  specification_version: 4
117
118
  summary: Server Sent Events server written in rack on top of thin inspired by Juggernaut
118
119
  for real time push
119
120
  test_files:
121
+ - spec/acceptance/allowed_channels_spec.rb
120
122
  - spec/acceptance/stream_and_publish_spec.rb
121
123
  - spec/benchmark/max_connections.rb
122
124
  - spec/spec_helper.rb