jubilee 1.1.0-java

Sign up to get free protection for your applications and to get access to all the features.
Files changed (155) hide show
  1. checksums.yaml +7 -0
  2. data/.ruby-version +1 -0
  3. data/.travis.yml +5 -0
  4. data/CHANGELOG +32 -0
  5. data/Gemfile +35 -0
  6. data/Gemfile.lock +244 -0
  7. data/Guardfile +24 -0
  8. data/KNOWN_ISSUES +6 -0
  9. data/LICENSE.txt +20 -0
  10. data/README.md +147 -0
  11. data/ROADMAP +5 -0
  12. data/Rakefile +98 -0
  13. data/bin/jubilee +6 -0
  14. data/bin/jubilee_d +13 -0
  15. data/examples/chatapp/Gemfile +5 -0
  16. data/examples/chatapp/Gemfile.lock +27 -0
  17. data/examples/chatapp/README.md +17 -0
  18. data/examples/chatapp/app.rb +57 -0
  19. data/examples/chatapp/config.ru +3 -0
  20. data/examples/chatapp/public/assets/javascripts/application.js +67 -0
  21. data/examples/chatapp/public/assets/javascripts/jquery.js +5 -0
  22. data/examples/chatapp/public/assets/javascripts/sockjs-0.3.4.min.js +27 -0
  23. data/examples/chatapp/public/assets/javascripts/vertxbus.js +216 -0
  24. data/examples/chatapp/public/assets/stylesheets/application.css +29 -0
  25. data/examples/client/sockjs-0.3.4.min.js +27 -0
  26. data/examples/client/vertxbus.js +216 -0
  27. data/examples/jubilee.conf.rb +12 -0
  28. data/examples/jubilee/keystore.jks +0 -0
  29. data/examples/jubilee/server-keystore.jks +0 -0
  30. data/jars/hazelcast-2.6.3.jar +0 -0
  31. data/jars/jackson-annotations-2.2.2.jar +0 -0
  32. data/jars/jackson-core-2.2.2.jar +0 -0
  33. data/jars/jackson-databind-2.2.2.jar +0 -0
  34. data/jars/netty-all-4.0.13.Final.jar +0 -0
  35. data/jars/vertx-core-2.1M3-SNAPSHOT.jar +0 -0
  36. data/jars/vertx-hazelcast-2.1M3-SNAPSHOT.jar +0 -0
  37. data/java/src/jubilee/JubileeService.java +20 -0
  38. data/java/src/org/jruby/jubilee/Const.java +32 -0
  39. data/java/src/org/jruby/jubilee/RackApplication.java +103 -0
  40. data/java/src/org/jruby/jubilee/RackEnvironment.java +150 -0
  41. data/java/src/org/jruby/jubilee/RackEnvironmentHash.java +449 -0
  42. data/java/src/org/jruby/jubilee/RackInput.java +62 -0
  43. data/java/src/org/jruby/jubilee/RackResponse.java +11 -0
  44. data/java/src/org/jruby/jubilee/RubyHttpServerResponse.java +88 -0
  45. data/java/src/org/jruby/jubilee/RubyServer.java +171 -0
  46. data/java/src/org/jruby/jubilee/deploy/Starter.java +26 -0
  47. data/java/src/org/jruby/jubilee/impl/RubyIORackInput.java +201 -0
  48. data/java/src/org/jruby/jubilee/impl/RubyNullIO.java +107 -0
  49. data/java/src/org/jruby/jubilee/utils/RubyHelper.java +37 -0
  50. data/java/src/org/jruby/jubilee/vertx/JubileeVertx.java +38 -0
  51. data/jubilee.gemspec +201 -0
  52. data/lib/jubilee.rb +17 -0
  53. data/lib/jubilee/application.rb +13 -0
  54. data/lib/jubilee/cli.rb +127 -0
  55. data/lib/jubilee/configuration.rb +177 -0
  56. data/lib/jubilee/const.rb +40 -0
  57. data/lib/jubilee/jubilee.jar +0 -0
  58. data/lib/jubilee/response.rb +69 -0
  59. data/lib/jubilee/server.rb +12 -0
  60. data/lib/jubilee/version.rb +10 -0
  61. data/lib/rack/chunked.rb +38 -0
  62. data/lib/rack/handler/jubilee.rb +44 -0
  63. data/lib/vertx.rb +26 -0
  64. data/lib/vertx/README.md +7 -0
  65. data/lib/vertx/buffer.rb +251 -0
  66. data/lib/vertx/event_bus.rb +206 -0
  67. data/lib/vertx/shared_data.rb +214 -0
  68. data/spec/apps/rack/basic/config.ru +50 -0
  69. data/spec/apps/rails4/basic/.gitignore +16 -0
  70. data/spec/apps/rails4/basic/Gemfile +41 -0
  71. data/spec/apps/rails4/basic/Gemfile.lock +127 -0
  72. data/spec/apps/rails4/basic/README.rdoc +28 -0
  73. data/spec/apps/rails4/basic/Rakefile +6 -0
  74. data/spec/apps/rails4/basic/app/assets/images/.keep +0 -0
  75. data/spec/apps/rails4/basic/app/assets/images/rails.png +0 -0
  76. data/spec/apps/rails4/basic/app/assets/javascripts/application.js +12 -0
  77. data/spec/apps/rails4/basic/app/assets/stylesheets/application.css +13 -0
  78. data/spec/apps/rails4/basic/app/controllers/application_controller.rb +5 -0
  79. data/spec/apps/rails4/basic/app/controllers/concerns/.keep +0 -0
  80. data/spec/apps/rails4/basic/app/controllers/reloader_controller.rb +11 -0
  81. data/spec/apps/rails4/basic/app/controllers/reloader_controller.rb.erb +11 -0
  82. data/spec/apps/rails4/basic/app/controllers/root_controller.rb +14 -0
  83. data/spec/apps/rails4/basic/app/helpers/application_helper.rb +2 -0
  84. data/spec/apps/rails4/basic/app/mailers/.keep +0 -0
  85. data/spec/apps/rails4/basic/app/models/.keep +0 -0
  86. data/spec/apps/rails4/basic/app/models/concerns/.keep +0 -0
  87. data/spec/apps/rails4/basic/app/views/layouts/application.html.erb +14 -0
  88. data/spec/apps/rails4/basic/app/views/reloader/index.html.erb +1 -0
  89. data/spec/apps/rails4/basic/app/views/root/index.html.erb +8 -0
  90. data/spec/apps/rails4/basic/app/views/root/streaming.html.erb +6 -0
  91. data/spec/apps/rails4/basic/bin/bundle +3 -0
  92. data/spec/apps/rails4/basic/bin/rails +4 -0
  93. data/spec/apps/rails4/basic/bin/rake +4 -0
  94. data/spec/apps/rails4/basic/config.ru +4 -0
  95. data/spec/apps/rails4/basic/config/application.rb +23 -0
  96. data/spec/apps/rails4/basic/config/boot.rb +4 -0
  97. data/spec/apps/rails4/basic/config/database.yml +20 -0
  98. data/spec/apps/rails4/basic/config/environment.rb +5 -0
  99. data/spec/apps/rails4/basic/config/environments/development.rb +29 -0
  100. data/spec/apps/rails4/basic/config/environments/production.rb +80 -0
  101. data/spec/apps/rails4/basic/config/environments/test.rb +36 -0
  102. data/spec/apps/rails4/basic/config/initializers/backtrace_silencers.rb +7 -0
  103. data/spec/apps/rails4/basic/config/initializers/filter_parameter_logging.rb +4 -0
  104. data/spec/apps/rails4/basic/config/initializers/inflections.rb +16 -0
  105. data/spec/apps/rails4/basic/config/initializers/mime_types.rb +5 -0
  106. data/spec/apps/rails4/basic/config/initializers/secret_token.rb +12 -0
  107. data/spec/apps/rails4/basic/config/initializers/session_store.rb +2 -0
  108. data/spec/apps/rails4/basic/config/initializers/wrap_parameters.rb +14 -0
  109. data/spec/apps/rails4/basic/config/locales/en.yml +23 -0
  110. data/spec/apps/rails4/basic/config/routes.rb +5 -0
  111. data/spec/apps/rails4/basic/db/seeds.rb +7 -0
  112. data/spec/apps/rails4/basic/lib/assets/.keep +0 -0
  113. data/spec/apps/rails4/basic/lib/tasks/.keep +0 -0
  114. data/spec/apps/rails4/basic/public/404.html +58 -0
  115. data/spec/apps/rails4/basic/public/422.html +58 -0
  116. data/spec/apps/rails4/basic/public/500.html +57 -0
  117. data/spec/apps/rails4/basic/public/favicon.ico +0 -0
  118. data/spec/apps/rails4/basic/public/robots.txt +5 -0
  119. data/spec/apps/rails4/basic/public/some_page.html +7 -0
  120. data/spec/apps/rails4/basic/test/controllers/.keep +0 -0
  121. data/spec/apps/rails4/basic/test/fixtures/.keep +0 -0
  122. data/spec/apps/rails4/basic/test/helpers/.keep +0 -0
  123. data/spec/apps/rails4/basic/test/integration/.keep +0 -0
  124. data/spec/apps/rails4/basic/test/mailers/.keep +0 -0
  125. data/spec/apps/rails4/basic/test/models/.keep +0 -0
  126. data/spec/apps/rails4/basic/test/test_helper.rb +15 -0
  127. data/spec/apps/rails4/basic/vendor/assets/javascripts/.keep +0 -0
  128. data/spec/apps/rails4/basic/vendor/assets/stylesheets/.keep +0 -0
  129. data/spec/apps/sinatra/basic/Gemfile +4 -0
  130. data/spec/apps/sinatra/basic/Gemfile.lock +20 -0
  131. data/spec/apps/sinatra/basic/basic.rb +27 -0
  132. data/spec/apps/sinatra/basic/config.ru +7 -0
  133. data/spec/apps/sinatra/basic/public/some_page.html +7 -0
  134. data/spec/apps/sinatra/basic/views/index.erb +4 -0
  135. data/spec/apps/sinatra/basic/views/posted.haml +2 -0
  136. data/spec/apps/sinatra/basic/views/poster.haml +4 -0
  137. data/spec/apps/sinatra/basic/views/request_mapping.haml +4 -0
  138. data/spec/integration/basic_rack_spec.rb +89 -0
  139. data/spec/integration/basic_rails4_spec.rb +64 -0
  140. data/spec/integration/basic_sinatra_spec.rb +80 -0
  141. data/spec/spec_helper.rb +13 -0
  142. data/test/.ruby-version +1 -0
  143. data/test/config/app.rb +5 -0
  144. data/test/jubilee/test_cli.rb +11 -0
  145. data/test/jubilee/test_configuration.rb +31 -0
  146. data/test/jubilee/test_rack_server.rb +137 -0
  147. data/test/jubilee/test_response.rb +272 -0
  148. data/test/jubilee/test_server.rb +72 -0
  149. data/test/jubilee/test_upload.rb +301 -0
  150. data/test/sinatra_app/app.rb +31 -0
  151. data/test/sinatra_app/config.ru +6 -0
  152. data/test/sinatra_app/public/test.html +10 -0
  153. data/test/sinatra_app/unicorn.conf.rb +29 -0
  154. data/test/test_helper.rb +93 -0
  155. metadata +242 -0
@@ -0,0 +1,206 @@
1
+ # Copyright 2011 the original author or authors.
2
+ #
3
+ # Licensed under the Apache License, Version 2.0 (the "License");
4
+ # you may not use this file except in compliance with the License.
5
+ # You may obtain a copy of the License at
6
+ #
7
+ # http://www.apache.org/licenses/LICENSE-2.0
8
+ #
9
+ # Unless required by applicable law or agreed to in writing, software
10
+ # distributed under the License is distributed on an "AS IS" BASIS,
11
+ # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12
+ # See the License for the specific language governing permissions and
13
+ # limitations under the License.
14
+
15
+ require 'rubygems'
16
+ require 'json'
17
+
18
+ module Vertx
19
+
20
+ # This class represents a distributed lightweight event bus which can encompass multiple vert.x instances.
21
+ # It is very useful for otherwise isolated vert.x application instances to communicate with each other.
22
+ #
23
+ # The event bus implements both publish / subscribe network and point to point messaging.
24
+ #
25
+ # For publish / subscribe, messages can be published to an address using one of the publish methods. An
26
+ # address is a simple String instance. Handlers are registered against an address. There can be multiple handlers
27
+ # registered against each address, and a particular handler can be registered against multiple addresses.
28
+ # The event bus will route a sent message to all handlers which are registered against that address.
29
+
30
+ # For point to point messaging, messages can be sent to an address using the send method.
31
+ # The messages will be delivered to a single handler, if one is registered on that address. If more than one
32
+ # handler is registered on the same address, Vert.x will choose one and deliver the message to that. Vert.x will
33
+ # aim to fairly distribute messages in a round-robin way, but does not guarantee strict round-robin under all
34
+ # circumstances.
35
+ #
36
+ # All messages sent over the bus are transient. On event of failure of all or part of the event bus messages
37
+ # may be lost. Applications should be coded to cope with lost messages, e.g. by resending them,
38
+ # and making application services idempotent.
39
+ #
40
+ # The order of messages received by any specific handler from a specific sender should match the order of messages
41
+ # sent from that sender.
42
+ #
43
+ # When sending a message, a reply handler can be provided. If so, it will be called when the reply from the receiver
44
+ # has been received. Reply messages can also be replied to, etc, ad infinitum.
45
+ #
46
+ # Different event bus instances can be clustered together over a network, to give a single logical event bus.
47
+ #
48
+ # When receiving a message in a handler the received object is an instance of EventBus::Message - this contains
49
+ # the actual message plus a reply method which can be used to reply to it.
50
+ #
51
+ # @author {http://tfox.org Tim Fox}
52
+ class EventBus
53
+
54
+ @@handler_map = {}
55
+
56
+ @@j_eventbus = org.jruby.jubilee.vertx.JubileeVertx.vertx().eventBus()
57
+
58
+ # Send a message on the event bus
59
+ # @param message [Hash] The message to send
60
+ # @param reply_handler [Block] An optional reply handler.
61
+ # It will be called when the reply from a receiver is received.
62
+ def EventBus.send(address, message, &reply_handler)
63
+ EventBus.send_or_pub(true, address, message, reply_handler)
64
+ self
65
+ end
66
+
67
+ # Publish a message on the event bus
68
+ # @param message [Hash] The message to publish
69
+ def EventBus.publish(address, message)
70
+ EventBus.send_or_pub(false, address, message)
71
+ self
72
+ end
73
+
74
+ # @private
75
+ def EventBus.send_or_pub(send, address, message, reply_handler = nil)
76
+ raise "An address must be specified" if !address
77
+ raise "A message must be specified" if message == nil
78
+ message = convert_msg(message)
79
+ if send
80
+ if reply_handler != nil
81
+ @@j_eventbus.send(address, message, InternalHandler.new(reply_handler))
82
+ else
83
+ @@j_eventbus.send(address, message)
84
+ end
85
+ else
86
+ @@j_eventbus.publish(address, message)
87
+ end
88
+ self
89
+ end
90
+
91
+ # Register a handler.
92
+ # @param address [String] The address to register for. Messages sent to that address will be
93
+ # received by the handler. A single handler can be registered against many addresses.
94
+ # @param local_only [Boolean] If true then handler won't be propagated across cluster
95
+ # @param message_hndlr [Block] The handler
96
+ # @return [FixNum] id of the handler which can be used in {EventBus.unregister_handler}
97
+ def EventBus.register_handler(address, local_only = false, &message_hndlr)
98
+ raise "An address must be specified" if !address
99
+ raise "A message handler must be specified" if !message_hndlr
100
+ internal = InternalHandler.new(message_hndlr)
101
+ if local_only
102
+ @@j_eventbus.registerLocalHandler(address, internal)
103
+ else
104
+ @@j_eventbus.registerHandler(address, internal)
105
+ end
106
+ id = java.util.UUID.randomUUID.toString
107
+ @@handler_map[id] = [address, internal]
108
+ id
109
+ end
110
+
111
+ # Registers a handler against a uniquely generated address, the address is returned as the id
112
+ # received by the handler. A single handler can be registered against many addresses.
113
+ # @param local_only [Boolean] If true then handler won't be propagated across cluster
114
+ # @param message_hndlr [Block] The handler
115
+ # @return [FixNum] id of the handler which can be used in {EventBus.unregister_handler}
116
+ def EventBus.register_simple_handler(local_only = false, &message_hndlr)
117
+ raise "A message handler must be specified" if !message_hndlr
118
+ internal = InternalHandler.new(message_hndlr)
119
+ id = java.util.UUID.randomUUID.toString
120
+ if local_only
121
+ @@j_eventbus.registerLocalHandler(id, internal)
122
+ else
123
+ @@j_eventbus.registerHandler(id, internal)
124
+ end
125
+ @@handler_map[id] = [id, internal]
126
+ id
127
+ end
128
+
129
+ # Unregisters a handler
130
+ # @param handler_id [FixNum] The id of the handler to unregister. Returned from {EventBus.register_handler}
131
+ def EventBus.unregister_handler(handler_id)
132
+ raise "A handler_id must be specified" if !handler_id
133
+ tuple = @@handler_map.delete(handler_id)
134
+ raise "Cannot find handler for id #{handler_id}" if !tuple
135
+ @@j_eventbus.unregisterHandler(tuple.first, tuple.last)
136
+ self
137
+ end
138
+
139
+ # @private
140
+ def EventBus.convert_msg(message)
141
+ if message.is_a? Hash
142
+ message = org.vertx.java.core.json.JsonObject.new(JSON.generate(message))
143
+ elsif message.is_a? Buffer
144
+ message = message._to_java_buffer
145
+ elsif message.is_a? Fixnum
146
+ message = java.lang.Long.new(message)
147
+ elsif message.is_a? Float
148
+ message = java.lang.Double.new(message)
149
+ end
150
+ message
151
+ end
152
+
153
+ end
154
+
155
+ # @private
156
+ class InternalHandler
157
+ include org.vertx.java.core.Handler
158
+
159
+ def initialize(hndlr)
160
+ @hndlr = hndlr
161
+ end
162
+
163
+ def handle(message)
164
+ @hndlr.call(Message.new(message))
165
+ end
166
+ end
167
+
168
+ # Represents a message received from the event bus
169
+ # @author {http://tfox.org Tim Fox}
170
+ class Message
171
+
172
+ attr_reader :body
173
+
174
+ # @private
175
+ def initialize(message)
176
+
177
+ @j_del = message
178
+ if message.body.is_a? org.vertx.java.core.json.JsonObject
179
+ @body = JSON.parse(message.body.encode)
180
+ elsif message.body.is_a? org.vertx.java.core.buffer.Buffer
181
+ @body = Buffer.new(message.body)
182
+ else
183
+ @body = message.body
184
+ end
185
+ end
186
+
187
+ # Reply to this message. If the message was sent specifying a receipt handler, that handler will be
188
+ # called when it has received a reply. If the message wasn't sent specifying a receipt handler
189
+ # this method does nothing.
190
+ # Replying to a message this way is equivalent to sending a message to an address which is the same as the message id
191
+ # of the original message.
192
+ # @param [Hash] Message send as reply
193
+ def reply(reply, &reply_handler)
194
+ raise "A reply message must be specified" if reply == nil
195
+ reply = EventBus.convert_msg(reply)
196
+ if reply_handler != nil
197
+ @j_del.reply(reply, InternalHandler.new(reply_handler))
198
+ else
199
+ @j_del.reply(reply)
200
+ end
201
+ end
202
+
203
+ end
204
+
205
+ end
206
+
@@ -0,0 +1,214 @@
1
+ # Copyright 2011 the original author or authors.
2
+ #
3
+ # Licensed under the Apache License, Version 2.0 (the "License");
4
+ # you may not use this file except in compliance with the License.
5
+ # You may obtain a copy of the License at
6
+ #
7
+ # http://www.apache.org/licenses/LICENSE-2.0
8
+ #
9
+ # Unless required by applicable law or agreed to in writing, software
10
+ # distributed under the License is distributed on an "AS IS" BASIS,
11
+ # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12
+ # See the License for the specific language governing permissions and
13
+ # limitations under the License.
14
+
15
+ require 'delegate'
16
+
17
+ module Vertx
18
+
19
+ # Sometimes it is desirable to share immutable data between different event loops, for example to implement a
20
+ # cache of data.
21
+ #
22
+ # This class allows data structures to be looked up and used from different event loops.
23
+ # The data structures themselves will only allow certain data types to be stored into them. This shields the
24
+ # user from worrying about any thread safety issues might occur if mutable objects were shared between event loops.
25
+ #
26
+ # The following types can be stored in a shareddata data structure:
27
+ #
28
+ # String
29
+ # FixNum
30
+ # Float
31
+ # {Buffer} this will be automatically copied, and the copy will be stored in the structure.
32
+ #
33
+ # @author {http://tfox.org Tim Fox}
34
+ class SharedData
35
+
36
+ @@j_sd = org.jruby.jubilee.vertx.JubileeVertx.vertx().sharedData()
37
+
38
+ # Return a Hash with the specific name. All invocations of this method with the same value of name
39
+ # are guaranteed to return the same Hash instance.
40
+ # @param [String] key. Get the hash with the key.
41
+ # @return [Hash] the hash.
42
+ def SharedData.get_hash(key)
43
+ map = @@j_sd.getMap(key)
44
+ SharedHash.new(map)
45
+ end
46
+
47
+ # Return a Set with the specific name. All invocations of this method with the same value of name
48
+ # are guaranteed to return the same Set instance.
49
+ # @param [String] key. Get the set with the key.
50
+ # @return [SharedSet] the set.
51
+ def SharedData.get_set(key)
52
+ set = @@j_sd.getSet(key)
53
+ SharedSet.new(set)
54
+ end
55
+
56
+ # Remove the hash
57
+ # @param [String] key. The key of the hash.
58
+ def SharedData.remove_hash(key)
59
+ @@j_sd.removeMap(key)
60
+ end
61
+
62
+ # Remove the set
63
+ # @param [String] key. The key of the set.
64
+ def SharedData.remove_set(key)
65
+ @@j_sd.removeSet(key)
66
+ end
67
+
68
+ # Convert to corresponding Java objects
69
+ # And make copies where appropriate (the underlying java map will also make copies for some data types too)
70
+ # @private
71
+ def SharedData.check_obj(obj)
72
+ if obj.is_a?(Buffer)
73
+ obj = obj._to_java_buffer
74
+ end
75
+ obj
76
+ end
77
+
78
+ # @private
79
+ class SharedHash < DelegateClass(Hash)
80
+
81
+ def initialize(hash)
82
+ @hash = hash
83
+ # Pass the object to be delegated to the superclass.
84
+ super(@hash)
85
+ end
86
+
87
+ def []=(key, val)
88
+ key = SharedData.check_obj(key)
89
+ val = SharedData.check_obj(val)
90
+ super(key, val)
91
+ end
92
+
93
+ alias store []=
94
+
95
+ def [](key)
96
+ # We call the java class directly
97
+ obj = @hash.get(key)
98
+ obj = Buffer.new(obj) if obj.is_a? org.vertx.java.core.buffer.Buffer
99
+ obj
100
+ end
101
+
102
+ def ==(other)
103
+ if other.is_a?(SharedHash)
104
+ @hash.equal?(other._to_java_map)
105
+ else
106
+ false
107
+ end
108
+ end
109
+
110
+ def _to_java_map
111
+ @hash
112
+ end
113
+
114
+ end
115
+
116
+ #
117
+ # @private
118
+ class SharedSet
119
+
120
+ # @private
121
+ def initialize(j_set)
122
+ @j_set = j_set
123
+ end
124
+
125
+ def ==(other)
126
+ if other.is_a?(SharedSet)
127
+ @j_set.equal?(other._to_java_set)
128
+ else
129
+ false
130
+ end
131
+ end
132
+
133
+ # Add an object to the set
134
+ # @param [Object] obj. The object to add
135
+ # @return [SharedSet} self
136
+ def add(obj)
137
+ obj = SharedData.check_obj(obj)
138
+ @j_set.add(obj)
139
+ self
140
+ end
141
+
142
+ # Add an object to the set
143
+ # @param [Object] obj. The object to add
144
+ # @return [SharedSet] self if the object is not already in the set, otherwise nil
145
+ def add?(obj)
146
+ obj = SharedData.check_obj(obj)
147
+ if !@j_set.contains(obj)
148
+ @j_set.add(obj)
149
+ self
150
+ else
151
+ nil
152
+ end
153
+ end
154
+
155
+ # Clear the set
156
+ def clear
157
+ @j_set.clear
158
+ end
159
+
160
+ # Delete an object from the set
161
+ # @param [Object] obj. The object to delete
162
+ def delete(obj)
163
+ @j_set.remove(obj)
164
+ end
165
+
166
+ # Delete an object from the set
167
+ # @param [Object] obj. The object to delete
168
+ # @return [SharedSet] self if the object was in the set before the remove, nil otherwise.
169
+ def delete?(obj)
170
+ if @j_set.contains(obj)
171
+ @j_set.remove(obj)
172
+ self
173
+ else
174
+ nil
175
+ end
176
+ end
177
+
178
+ # Call the block for every element of the set
179
+ # @param [Blovk] block. The block to call.
180
+ def each(&block)
181
+ iter = @j_set.iterator
182
+ while iter.hasNext do
183
+ obj = iter.next
184
+ obj = Buffer.new(obj) if obj.is_a? org.vertx.java.core.buffer.Buffer
185
+ block.call(obj)
186
+ end
187
+ end
188
+
189
+ # @return [Boolean] true if the set is empty
190
+ def empty?
191
+ @j_set.isEmpty
192
+ end
193
+
194
+ # Does the set contain an element?
195
+ # @param [Object] obj, the object to check if the set contains
196
+ # @return [Boolean] true if the object is contained in the set
197
+ def include?(obj)
198
+ obj = obj._to_java_buffer if obj.is_a? Buffer
199
+ @j_set.contains(obj)
200
+ end
201
+
202
+ # @return [FixNum] The number of elements in the set
203
+ def size
204
+ @j_set.size
205
+ end
206
+
207
+ # @private
208
+ def _to_java_set
209
+ @j_set
210
+ end
211
+
212
+ end
213
+ end
214
+ end
@@ -0,0 +1,50 @@
1
+ require 'rack'
2
+
3
+ class BasicMiddleware
4
+ def initialize(app, options={})
5
+ @app = app
6
+ end
7
+ def call(env)
8
+ # We had a bug triggered at one point by trying to access any HTTP
9
+ # header with a key less than 10 bytes long
10
+ env['HTTP_foo']
11
+ # Save off the accept header before Rack::Lint messes with it
12
+ env['tb.accept_header'] = env['HTTP_ACCEPT']
13
+ @app.call(env)
14
+ end
15
+ end
16
+
17
+ use BasicMiddleware
18
+ use Rack::Lint
19
+
20
+ app = lambda { |env|
21
+ body = <<-EOF
22
+ <div id='success' class='basic-rack'>it worked</div>
23
+ <div id='ruby-version'>#{RUBY_VERSION}</div>
24
+ <div id='path'>#{__FILE__}</div>
25
+ <div id='script_name'>#{env['SCRIPT_NAME']}</div>
26
+ <div id='path_info'>#{env['PATH_INFO']}</div>
27
+ <div id='request_uri'>#{env['REQUEST_URI']}</div>
28
+ <div id='accept_header'>#{env['tb.accept_header']}</div>
29
+ EOF
30
+ if env['REQUEST_METHOD'] == 'POST'
31
+ input = env['rack.input']
32
+ if env['PATH_INFO'] == '/basic-rack/gets'
33
+ posted = ''
34
+ posted_line = input.gets
35
+ while posted_line != nil
36
+ posted << posted_line
37
+ posted_line = input.gets
38
+ end
39
+ elsif env['PATH_INFO'] == '/basic-rack/read'
40
+ posted = input.read(2)
41
+ posted << input.read
42
+ elsif env['PATH_INFO'] == '/basic-rack/each'
43
+ posted = ""
44
+ input.each { |str| posted << str}
45
+ end
46
+ body << "<div id='posted'>#{posted}</div>"
47
+ end
48
+ [200, { 'Content-Type' => 'text/html' }, [body]]
49
+ }
50
+ run app