rpush 2.3.1-java → 2.3.2-java

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.
Files changed (66) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG.md +6 -0
  3. data/README.md +36 -28
  4. data/lib/rpush/configuration.rb +1 -0
  5. data/lib/rpush/daemon/feeder.rb +16 -12
  6. data/lib/rpush/daemon/interruptible_sleep.rb +26 -5
  7. data/lib/rpush/daemon/store/active_record.rb +4 -0
  8. data/lib/rpush/daemon/store/interface.rb +1 -1
  9. data/lib/rpush/daemon/store/redis.rb +10 -0
  10. data/lib/rpush/embed.rb +1 -0
  11. data/lib/rpush/logger.rb +1 -0
  12. data/lib/rpush/push.rb +1 -2
  13. data/lib/rpush/version.rb +1 -1
  14. data/spec/functional/adm_spec.rb +6 -8
  15. data/spec/functional/apns_spec.rb +9 -9
  16. data/spec/functional/embed_spec.rb +3 -3
  17. data/spec/functional/gcm_spec.rb +6 -8
  18. data/spec/functional/new_app_spec.rb +5 -20
  19. data/spec/functional/retry_spec.rb +8 -12
  20. data/spec/functional/synchronization_spec.rb +1 -1
  21. data/spec/functional/wpns_spec.rb +7 -7
  22. data/spec/functional_spec_helper.rb +4 -5
  23. data/spec/spec_helper.rb +1 -1
  24. data/spec/unit/apns_feedback_spec.rb +4 -4
  25. data/spec/unit/client/active_record/adm/app_spec.rb +12 -12
  26. data/spec/unit/client/active_record/adm/notification_spec.rb +9 -9
  27. data/spec/unit/client/active_record/apns/app_spec.rb +4 -4
  28. data/spec/unit/client/active_record/apns/feedback_spec.rb +2 -2
  29. data/spec/unit/client/active_record/apns/notification_spec.rb +46 -46
  30. data/spec/unit/client/active_record/app_spec.rb +6 -6
  31. data/spec/unit/client/active_record/gcm/notification_spec.rb +7 -7
  32. data/spec/unit/client/active_record/notification_spec.rb +2 -2
  33. data/spec/unit/client/active_record/wpns/notification_spec.rb +2 -8
  34. data/spec/unit/configuration_spec.rb +5 -5
  35. data/spec/unit/daemon/adm/delivery_spec.rb +69 -69
  36. data/spec/unit/daemon/apns/delivery_spec.rb +13 -13
  37. data/spec/unit/daemon/apns/feedback_receiver_spec.rb +24 -26
  38. data/spec/unit/daemon/app_runner_spec.rb +29 -29
  39. data/spec/unit/daemon/batch_spec.rb +30 -30
  40. data/spec/unit/daemon/delivery_error_spec.rb +2 -2
  41. data/spec/unit/daemon/delivery_spec.rb +6 -6
  42. data/spec/unit/daemon/dispatcher/http_spec.rb +5 -5
  43. data/spec/unit/daemon/dispatcher/tcp_spec.rb +4 -4
  44. data/spec/unit/daemon/dispatcher_loop_spec.rb +9 -9
  45. data/spec/unit/daemon/feeder_spec.rb +22 -23
  46. data/spec/unit/daemon/gcm/delivery_spec.rb +56 -56
  47. data/spec/unit/daemon/retryable_error_spec.rb +2 -2
  48. data/spec/unit/daemon/service_config_methods_spec.rb +5 -5
  49. data/spec/unit/daemon/signal_handler_spec.rb +13 -13
  50. data/spec/unit/daemon/store/active_record/reconnectable_spec.rb +13 -13
  51. data/spec/unit/daemon/store/active_record_spec.rb +49 -49
  52. data/spec/unit/daemon/tcp_connection_spec.rb +50 -50
  53. data/spec/unit/daemon/wpns/delivery_spec.rb +36 -36
  54. data/spec/unit/daemon_spec.rb +33 -30
  55. data/spec/unit/deprecatable_spec.rb +3 -3
  56. data/spec/unit/deprecation_spec.rb +2 -2
  57. data/spec/unit/embed_spec.rb +7 -7
  58. data/spec/unit/logger_spec.rb +25 -25
  59. data/spec/unit/notification_shared.rb +7 -7
  60. data/spec/unit/plugin_spec.rb +1 -1
  61. data/spec/unit/push_spec.rb +8 -8
  62. data/spec/unit/reflectable_spec.rb +5 -5
  63. data/spec/unit/reflection_collection_spec.rb +2 -2
  64. data/spec/unit/rpush_spec.rb +1 -1
  65. data/spec/unit_spec_helper.rb +4 -5
  66. metadata +10 -4
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: db242aa007028a120a9feda8864ac82fc80c03e8
4
- data.tar.gz: a51af79635b86921dfc06805ec7b8bf0d22188c6
3
+ metadata.gz: 781a6d71dd94117ad91ad2f72da207d25e61d3ea
4
+ data.tar.gz: 460ef2c7fb2f5f00168f913f0eb3207697090501
5
5
  SHA512:
6
- metadata.gz: d6556717fa5851670234e1a105a12b7f3f04ef577e1a6f32ebd5433c96111e74fa12fedf62d554a456de36b3990efb6983b6a1068decc4e574225d897359cd25
7
- data.tar.gz: 06c11662bf521575e6641b6cd6629206415203e629e34663fc2a5011aecd1ef4394c3ada86a351ba746906e9c1ca2ab6f4722dfbd51c57abcf8fa44a99a4dbca
6
+ metadata.gz: 0e039767bf42481ec7f34ed89be0dc0991670a9683ccff6bc92907a5ea9bad29c84b204ab0176e5936f766b245ba36477c67066e002790f0c60fdeaf47e72a84
7
+ data.tar.gz: 9229d9d37108f5cef4eabfcea7b46c527e1eab2e2da689ad3f5bc8d250b40bd3bdc0feba84d860e7e151fe2be1810c91c47fd77e5eee31a72847b00cc225f03d
@@ -1,3 +1,9 @@
1
+ ## 2.3.2 (Jan 30, 2015)
2
+ Bug fixes:
3
+ * Internal sleep mechanism would sometimes no wait for the full duration specified.
4
+ * Rpush.push nows delivers all pending notifications before returning.
5
+ * Require thor >= 0.18.1 (#121).
6
+
1
7
  ## 2.3.1 (Jan 24, 2015)
2
8
  * Fix CPU thrashing while waiting for an APNs connection be established (#119).
3
9
 
data/README.md CHANGED
@@ -7,24 +7,27 @@
7
7
 
8
8
  ### Rpush. The push notification service for Ruby.
9
9
 
10
- * Supported services:
10
+ Rpush aims to be the *de facto* gem for sending push notifications in Ruby. Its core goals are ease of use, reliability and a rich feature set. Rpush provides numerous advanced features not found in others gems, giving you greater control & insight as your project grows. These are a few of the reasons why companies worldwide rely on Rpush to deliver their notifications.
11
+
12
+ #### Supported Services
13
+
11
14
  * [**Apple Push Notification Service**](#apple-push-notification-service)
12
15
  * Including Safari Push Notifications.
13
16
  * [**Google Cloud Messaging**](#google-cloud-messaging)
14
17
  * [**Amazon Device Messaging**](#amazon-device-messaging)
15
18
  * [**Windows Phone Push Notification Service**](#windows-phone-notification-service)
16
19
 
17
- * Supported storage backends:
18
- * [**ActiveRecord**](https://github.com/rpush/rpush/wiki/Using-ActiveRecord)
19
- * [**Redis**](https://github.com/rpush/rpush/wiki/Using-Redis)
20
+ #### Feature Highlights
20
21
 
21
- * Optional Rails integration (version 3 & 4).
22
+ * Use [**ActiveRecord**](https://github.com/rpush/rpush/wiki/Using-ActiveRecord) or [**Redis**](https://github.com/rpush/rpush/wiki/Using-Redis) for storage.
23
+ * Plugins for [**Bugsnag**](https://github.com/rpush/rpush-plugin-bugsnag),
24
+ [**Sentry**](https://github.com/rpush/rpush-plugin-sentry), [**StatsD**](https://github.com/rpush/rpush-plugin-statsd).
25
+ * Seamless integration with your projects, including **Rails**.
26
+ * Run as a [daemon](https://github.com/rpush/rpush#as-a-daemon-recommended), inside a [job queue](https://github.com/rpush/rpush/wiki/Push-API), on the [command-line](https://github.com/rpush/rpush#on-the-command-line) or [embedded](https://github.com/rpush/rpush/wiki/Embedding-API) in another process.
22
27
  * Scales vertically (threading) and horizontally (multiple processes).
23
28
  * Designed for uptime - new apps are loaded automatically, signal `HUP` to update running apps.
24
- * Run as a daemon or inside an [existing process](https://github.com/rpush/rpush/wiki/Embedding-API).
25
- * Use in a scheduler for low-workload deployments ([Push API](https://github.com/rpush/rpush/wiki/Push-API)).
26
29
  * Hooks for fine-grained instrumentation and error handling ([Reflection API](https://github.com/rpush/rpush/wiki/Reflection-API)).
27
- * Works with MRI, JRuby and Rubinius.
30
+ * Works with **MRI**, **JRuby** and **Rubinius**.
28
31
 
29
32
 
30
33
  ### Getting Started
@@ -35,11 +38,11 @@ Add it to your Gemfile:
35
38
  gem 'rpush'
36
39
  ```
37
40
 
38
- Initialize Rpush into your project. Rails will be detected automatically.
41
+ Initialize Rpush into your project. **Rails will be detected automatically.**
39
42
 
40
- ```
41
- cd /path/to/project
42
- rpush init
43
+ ```sh
44
+ $ cd /path/to/project
45
+ $ rpush init
43
46
  ```
44
47
 
45
48
  ### Create an App & Notification
@@ -134,24 +137,24 @@ n.save!
134
137
 
135
138
  It is recommended to run Rpush as a separate process in most cases, though embedding and manual modes are provided for low-workload environments.
136
139
 
137
- #### As a daemon (recommended):
138
-
139
- ```
140
- cd /path/to/project
141
- rpush start
142
- ```
143
-
144
140
  See `rpush help` for all available commands and options.
145
141
 
146
- #### One-off, manual
147
-
148
- On the command-line:
142
+ #### As a daemon
149
143
 
144
+ ```sh
145
+ $ cd /path/to/project
146
+ $ rpush start
150
147
  ```
151
- rpush push
148
+
149
+ #### On the command-line
150
+
151
+ ```sh
152
+ $ rpush push
152
153
  ```
153
154
 
154
- In your code:
155
+ Rpush will deliver all pending notifications and then exit.
156
+
157
+ #### In a scheduled job
155
158
 
156
159
  ```ruby
157
160
  Rpush.push
@@ -163,11 +166,16 @@ See [Push API](https://github.com/rpush/rpush/wiki/Push-API) for more details.
163
166
  #### Embedded inside an existing process
164
167
 
165
168
  ```ruby
166
- # Call this during startup of your application, for example, by adding it to the end of config/rpush.rb
167
- Rpush.embed
169
+ if defined?(Rails)
170
+ ActiveSupport.on_load(:after_initialize) do
171
+ Rpush.embed
172
+ end
173
+ else
174
+ Rpush.embed
175
+ end
168
176
  ```
169
177
 
170
- See [Embedding API](https://github.com/rpush/rpush/wiki/Embedding-API) for more details.
178
+ Call this during startup of your application, for example, by adding it to the end of `config/rpush.rb`. See [Embedding API](https://github.com/rpush/rpush/wiki/Embedding-API) for more details.
171
179
 
172
180
  ### Configuration
173
181
 
@@ -177,7 +185,7 @@ See [Configuration](https://github.com/rpush/rpush/wiki/Configuration) for a lis
177
185
 
178
186
  You should run `rpush init` after upgrading Rpush to check for configuration and migration changes.
179
187
 
180
- ### Wiki
188
+ ### From The Wiki
181
189
 
182
190
  ### General
183
191
  * [Using Redis](https://github.com/rpush/rpush/wiki/Using-Redis)
@@ -77,6 +77,7 @@ module Rpush
77
77
  self.pid_file = 'tmp/rpush.pid'
78
78
  self.log_level = (defined?(Rails) && Rails.logger) ? Rails.logger.level : ::Logger::Severity::INFO
79
79
  self.plugin = OpenStruct.new
80
+ self.foreground = false
80
81
 
81
82
  # Internal options.
82
83
  self.embedded = false
@@ -3,9 +3,15 @@ module Rpush
3
3
  class Feeder
4
4
  extend Reflectable
5
5
 
6
- def self.start
6
+ def self.start(push_mode = false)
7
7
  self.should_stop = false
8
- Rpush.config.push ? enqueue_notifications : feed_forever
8
+
9
+ @thread = Thread.new do
10
+ push_mode ? feed_all : feed_forever
11
+ Rpush::Daemon.store.release_connection
12
+ end
13
+
14
+ @thread.join
9
15
  end
10
16
 
11
17
  def self.stop
@@ -22,18 +28,16 @@ module Rpush
22
28
  attr_accessor :should_stop
23
29
  end
24
30
 
25
- def self.feed_forever
26
- @thread = Thread.new do
27
- loop do
28
- enqueue_notifications
29
- interruptible_sleeper.sleep
30
- break if should_stop
31
- end
31
+ def self.feed_all
32
+ enqueue_notifications until Rpush::Daemon.store.pending_delivery_count == 0
33
+ end
32
34
 
33
- Rpush::Daemon.store.release_connection
35
+ def self.feed_forever
36
+ loop do
37
+ enqueue_notifications
38
+ interruptible_sleeper.sleep
39
+ break if should_stop
34
40
  end
35
-
36
- @thread.join
37
41
  end
38
42
 
39
43
  def self.enqueue_notifications
@@ -5,15 +5,21 @@ module Rpush
5
5
  class InterruptibleSleep
6
6
  def initialize(duration)
7
7
  @duration = duration
8
- @obj = Object.new
9
- @obj.extend(MonitorMixin)
10
- @condition = @obj.new_cond
11
8
  @stop = false
9
+
10
+ @wakeup_obj = Object.new
11
+ @wakeup_obj.extend(MonitorMixin)
12
+ @wakeup_condition = @wakeup_obj.new_cond
13
+
14
+ @sleep_obj = Object.new
15
+ @sleep_obj.extend(MonitorMixin)
16
+ @sleep_condition = @sleep_obj.new_cond
12
17
  end
13
18
 
14
19
  def sleep
15
20
  return if @stop
16
- @obj.synchronize { @condition.wait(100_000) }
21
+ goto_sleep
22
+ wait_for_wakeup
17
23
  end
18
24
 
19
25
  def start
@@ -21,6 +27,7 @@ module Rpush
21
27
 
22
28
  @thread = Thread.new do
23
29
  loop do
30
+ wait_for_sleeper
24
31
  break if @stop
25
32
  Kernel.sleep(@duration)
26
33
  wakeup
@@ -35,7 +42,21 @@ module Rpush
35
42
  end
36
43
 
37
44
  def wakeup
38
- @obj.synchronize { @condition.signal }
45
+ @wakeup_obj.synchronize { @wakeup_condition.signal }
46
+ end
47
+
48
+ private
49
+
50
+ def goto_sleep
51
+ @sleep_obj.synchronize { @sleep_condition.signal }
52
+ end
53
+
54
+ def wait_for_wakeup
55
+ @wakeup_obj.synchronize { @wakeup_condition.wait(@duration * 2) }
56
+ end
57
+
58
+ def wait_for_sleeper
59
+ @sleep_obj.synchronize { @sleep_condition.wait }
39
60
  end
40
61
  end
41
62
  end
@@ -165,6 +165,10 @@ module Rpush
165
165
  Rpush.logger.error(e)
166
166
  end
167
167
 
168
+ def pending_delivery_count
169
+ ready_for_delivery.count
170
+ end
171
+
168
172
  private
169
173
 
170
174
  def create_gcm_like_notification(notification, attrs, data, registration_ids, deliver_after, app) # rubocop:disable ParameterLists
@@ -8,7 +8,7 @@ module Rpush
8
8
  :create_gcm_notification, :create_adm_notification, :update_app,
9
9
  :update_notification, :release_connection,
10
10
  :all_apps, :app, :mark_ids_failed, :mark_ids_retryable,
11
- :reopen_log]
11
+ :reopen_log, :pending_delivery_count]
12
12
 
13
13
  def self.check(klass)
14
14
  missing = PUBLIC_METHODS - klass.instance_methods.map(&:to_sym)
@@ -106,6 +106,15 @@ module Rpush
106
106
  def reopen_log
107
107
  end
108
108
 
109
+ def pending_delivery_count
110
+ Modis.with_connection do |redis|
111
+ pending = redis.zrange(Rpush::Client::Redis::Notification.absolute_pending_namespace, 0, -1)
112
+ retryable = redis.zrangebyscore(Rpush::Client::Redis::Notification.absolute_retryable_namespace, 0, Time.now.to_i)
113
+
114
+ pending.count + retryable.count
115
+ end
116
+ end
117
+
109
118
  private
110
119
 
111
120
  def create_gcm_like_notification(notification, attrs, data, registration_ids, deliver_after, app) # rubocop:disable ParameterLists
@@ -133,6 +142,7 @@ module Rpush
133
142
  end
134
143
 
135
144
  def pending_notification_ids(limit)
145
+ limit = [0, limit - 1].max # 'zrange key 0 1' will return 2 values, not 1.
136
146
  pending_ns = Rpush::Client::Redis::Notification.absolute_pending_namespace
137
147
 
138
148
  Modis.with_connection do |redis|
@@ -9,6 +9,7 @@ module Rpush
9
9
  config = Rpush::ConfigurationWithoutDefaults.new
10
10
  options.each { |k, v| config.send("#{k}=", v) }
11
11
  config.embedded = true
12
+ config.foreground = true
12
13
  Rpush.config.update(config)
13
14
  Kernel.at_exit { shutdown }
14
15
  @embed_thread = Thread.new { Rpush::Daemon.start }
@@ -69,6 +69,7 @@ module Rpush
69
69
  end
70
70
 
71
71
  formatted_msg = "[#{Time.now.to_s(:db)}] "
72
+ formatted_msg << '[rpush] ' if Rpush.config.embedded
72
73
  formatted_msg << "[#{prefix}] " if prefix
73
74
  formatted_msg << msg
74
75
 
@@ -9,8 +9,7 @@ module Rpush
9
9
 
10
10
  Rpush::Daemon.common_init
11
11
  Rpush::Daemon::Synchronizer.sync
12
- Rpush::Daemon::Feeder.start
13
- # TODO: Wait until there are no more notifications.
12
+ Rpush::Daemon::Feeder.start(true) # non-blocking
14
13
  Rpush::Daemon::AppRunner.stop
15
14
  end
16
15
  end
@@ -1,3 +1,3 @@
1
1
  module Rpush
2
- VERSION = '2.3.1'
2
+ VERSION = '2.3.2'
3
3
  end
@@ -20,11 +20,11 @@ describe 'ADM' do
20
20
  notification.data = { message: 'test' }
21
21
  notification.save!
22
22
 
23
- Net::HTTP::Persistent.stub(new: http)
23
+ allow(Net::HTTP::Persistent).to receive_messages(new: http)
24
24
  end
25
25
 
26
26
  it 'delivers a notification successfully' do
27
- response.stub(body: JSON.dump(registrationID: notification.registration_ids.first.to_s))
27
+ allow(response).to receive_messages(body: JSON.dump(registrationID: notification.registration_ids.first.to_s))
28
28
 
29
29
  expect do
30
30
  Rpush.push
@@ -33,12 +33,10 @@ describe 'ADM' do
33
33
  end
34
34
 
35
35
  it 'fails to deliver a notification successfully' do
36
- response.stub(code: 400, body: JSON.dump(reason: 'error', registrationID: notification.registration_ids.first.to_s))
37
-
38
- expect do
39
- Rpush.push
40
- notification.reload
41
- end.to_not change(notification, :delivered).to(true)
36
+ allow(response).to receive_messages(code: 400, body: JSON.dump(reason: 'error', registrationID: notification.registration_ids.first.to_s))
37
+ Rpush.push
38
+ notification.reload
39
+ expect(notification.delivered).to eq(false)
42
40
  end
43
41
 
44
42
  it 'retries notification that fail due to a SocketError' do
@@ -33,8 +33,8 @@ describe 'APNs' do
33
33
  end
34
34
 
35
35
  def stub_tcp_connection
36
- Rpush::Daemon::TcpConnection.any_instance.stub(connect_socket: [tcp_socket, ssl_socket])
37
- Rpush::Daemon::TcpConnection.any_instance.stub(setup_ssl_context: double.as_null_object)
36
+ allow_any_instance_of(Rpush::Daemon::TcpConnection).to receive_messages(connect_socket: [tcp_socket, ssl_socket])
37
+ allow_any_instance_of(Rpush::Daemon::TcpConnection).to receive_messages(setup_ssl_context: double.as_null_object)
38
38
  stub_const('Rpush::Daemon::TcpConnection::IO', io_double)
39
39
  end
40
40
 
@@ -55,13 +55,13 @@ describe 'APNs' do
55
55
  end
56
56
 
57
57
  def fail_notification(notification)
58
- ssl_socket.stub(read: [8, 4, notification.id].pack('ccN'))
58
+ allow(ssl_socket).to receive_messages(read: [8, 4, notification.id].pack('ccN'))
59
59
  enable_io_select
60
60
  end
61
61
 
62
62
  def enable_io_select
63
63
  called = false
64
- io_double.stub(:select) do
64
+ allow(io_double).to receive(:select) do
65
65
  if called
66
66
  nil
67
67
  else
@@ -88,9 +88,9 @@ describe 'APNs' do
88
88
  allow(ssl_socket).to receive(:read).and_return(tuple, nil)
89
89
  Rpush.apns_feedback
90
90
  feedback = Rpush::Apns::Feedback.all.first
91
- feedback.should_not be_nil
92
- feedback.app_id.should eq(app.id)
93
- feedback.device_token.should eq('834f786655eb9f84614a05ad7d00af31e5cfe93ac3ea078f1da44d2a4eb0ce17')
91
+ expect(feedback).not_to be_nil
92
+ expect(feedback.app_id).to eq(app.id)
93
+ expect(feedback.device_token).to eq('834f786655eb9f84614a05ad7d00af31e5cfe93ac3ea078f1da44d2a4eb0ce17')
94
94
  end
95
95
 
96
96
  describe 'delivery failures' do
@@ -132,7 +132,7 @@ describe 'APNs' do
132
132
 
133
133
  describe 'with a failed connection' do
134
134
  it 'retries all notifications' do
135
- Rpush::Daemon::TcpConnection.any_instance.stub(sleep: nil)
135
+ allow_any_instance_of(Rpush::Daemon::TcpConnection).to receive_messages(sleep: nil)
136
136
  expect(ssl_socket).to receive(:write).at_least(1).times.and_raise(Errno::EPIPE)
137
137
  notifications = 2.times.map { create_notification }
138
138
  notifications.each { |n| wait_for_notification_to_retry(n) }
@@ -159,7 +159,7 @@ describe 'APNs' do
159
159
 
160
160
  expect(failed_ids).to_not include(notification1.id)
161
161
  notification1.reload
162
- notification1.delivered.should be_true
162
+ expect(notification1.delivered).to eq(true)
163
163
  end
164
164
 
165
165
  it 'marks notifications following the failed one as retryable' do
@@ -23,10 +23,10 @@ describe 'embedding' do
23
23
  end
24
24
 
25
25
  def stub_tcp_connection
26
- Rpush::Daemon::TcpConnection.any_instance.stub(connect_socket: [tcp_socket, ssl_socket])
27
- Rpush::Daemon::TcpConnection.any_instance.stub(setup_ssl_context: double.as_null_object)
26
+ allow_any_instance_of(Rpush::Daemon::TcpConnection).to receive_messages(connect_socket: [tcp_socket, ssl_socket])
27
+ allow_any_instance_of(Rpush::Daemon::TcpConnection).to receive_messages(setup_ssl_context: double.as_null_object)
28
28
  stub_const('Rpush::Daemon::TcpConnection::IO', io_double)
29
- Rpush::Daemon::Apns::FeedbackReceiver.stub(new: double.as_null_object)
29
+ allow(Rpush::Daemon::Apns::FeedbackReceiver).to receive_messages(new: double.as_null_object)
30
30
  end
31
31
 
32
32
  before do
@@ -16,11 +16,11 @@ describe 'GCM' do
16
16
  notification.data = { message: 'test' }
17
17
  notification.save!
18
18
 
19
- Net::HTTP::Persistent.stub(new: http)
19
+ allow(Net::HTTP::Persistent).to receive_messages(new: http)
20
20
  end
21
21
 
22
22
  it 'delivers a notification successfully' do
23
- response.stub(body: JSON.dump(results: [{ message_id: notification.registration_ids.first.to_s }]))
23
+ allow(response).to receive_messages(body: JSON.dump(results: [{ message_id: notification.registration_ids.first.to_s }]))
24
24
 
25
25
  expect do
26
26
  Rpush.push
@@ -29,12 +29,10 @@ describe 'GCM' do
29
29
  end
30
30
 
31
31
  it 'fails to deliver a notification successfully' do
32
- response.stub(body: JSON.dump(results: [{ error: 'Err' }]))
33
-
34
- expect do
35
- Rpush.push
36
- notification.reload
37
- end.to_not change(notification, :delivered).to(true)
32
+ allow(response).to receive_messages(body: JSON.dump(results: [{ error: 'Err' }]))
33
+ Rpush.push
34
+ notification.reload
35
+ expect(notification.delivered).to eq(false)
38
36
  end
39
37
 
40
38
  it 'retries notification that fail due to a SocketError' do