rapns 3.3.0 → 3.3.1

Sign up to get free protection for your applications and to get access to all the features.
@@ -1,3 +1,10 @@
1
+ ## 3.3.1 (June 2, 2013)
2
+ * Fix compatibility with postgres_ext (#104).
3
+ * Add ability to switch the logger (@maxsz).
4
+ * Do not validate presence of alert, badge or sound - not actually required by the APNs (#129) (@wilg).
5
+ * Catch IOError from an APNs connection. (@maxsz).
6
+ * Allow nested hashes in APNs notification attributes (@perezda).
7
+
1
8
  ## 3.3.0 (April 21, 2013)
2
9
  * GCM: collapse_key is no longer required to set expiry (time_to_live).
3
10
  * Add reflection for GCM canonical IDs.
data/README.md CHANGED
@@ -89,14 +89,18 @@ As a daemon:
89
89
 
90
90
  Inside an existing process (see [Embedding API](https://github.com/ileitch/rapns/wiki/Embedding-API)):
91
91
 
92
- Rapns.embed
92
+ ```ruby
93
+ Rapns.embed
94
+ ```
93
95
 
94
96
  *Please note that only ever a single instance of Rapns should be running.*
95
97
 
96
98
  In a scheduler (see [Push API](https://github.com/ileitch/rapns/wiki/Push-API)):
97
99
 
98
- Rapns.push
99
- Rapns.apns_feedback
100
+ ```ruby
101
+ Rapns.push
102
+ Rapns.apns_feedback
103
+ ```
100
104
 
101
105
  See [Configuration](https://github.com/ileitch/rapns/wiki/Configuration) for a list of options, or run `rapns --help`.
102
106
 
@@ -115,6 +119,7 @@ After updating you should run `rails g rapns` to check for any new migrations.
115
119
  * [Reflection API](https://github.com/ileitch/rapns/wiki/Reflection-API)
116
120
  * [Push API](https://github.com/ileitch/rapns/wiki/Push-API)
117
121
  * [Embedding API](https://github.com/ileitch/rapns/wiki/Embedding-API)
122
+ * [Implementing your own storage backend](https://github.com/ileitch/rapns/wiki/Implementing-your-own-storage-backend)
118
123
 
119
124
  ### APNs
120
125
  * [Generating Certificates](https://github.com/ileitch/rapns/wiki/Generating-Certificates)
@@ -158,3 +163,6 @@ Thank you to the following wonderful people for contributing:
158
163
  * [@jeffarena](https://github.com/jeffarena)
159
164
  * [@DianthuDia](https://github.com/DianthuDia)
160
165
  * [@dup2](https://github.com/dup2)
166
+ * [@maxsz](https://github.com/maxsz)
167
+ * [@wilg](https://github.com/wilg)
168
+ * [@perezda](https://github.com/perezda)
@@ -23,6 +23,9 @@
23
23
  # Path to write PID file. Relative to Rails root unless absolute.
24
24
  # config.pid_file = '/path/to/rapns.pid'
25
25
 
26
+ # Define a custom logger.
27
+ # config.logger = MyLogger.new
28
+
26
29
  end
27
30
 
28
31
  Rapns.reflect do |on|
@@ -17,7 +17,6 @@ require 'rapns/upgraded'
17
17
 
18
18
  require 'rapns/apns/binary_notification_validator'
19
19
  require 'rapns/apns/device_token_format_validator'
20
- require 'rapns/apns/required_fields_validator'
21
20
  require 'rapns/apns/notification'
22
21
  require 'rapns/apns/feedback'
23
22
  require 'rapns/apns/app'
@@ -8,7 +8,6 @@ module Rapns
8
8
 
9
9
  validates_with Rapns::Apns::DeviceTokenFormatValidator
10
10
  validates_with Rapns::Apns::BinaryNotificationValidator
11
- validates_with Rapns::Apns::RequiredFieldsValidator
12
11
 
13
12
  alias_method :attributes_for_device=, :data=
14
13
  alias_method :attributes_for_device, :data
@@ -69,7 +68,7 @@ module Rapns
69
68
 
70
69
  if attributes_for_device
71
70
  non_aps_attributes = attributes_for_device.reject { |k, v| k == CONTENT_AVAILABLE_KEY }
72
- non_aps_attributes.each { |k, v| json[k.to_s] = v.to_s }
71
+ non_aps_attributes.each { |k, v| json[k.to_s] = v }
73
72
  end
74
73
  end
75
74
 
@@ -9,7 +9,7 @@ module Rapns
9
9
 
10
10
  CONFIG_ATTRS = [:foreground, :push_poll, :feedback_poll, :embedded,
11
11
  :airbrake_notify, :check_for_errors, :pid_file, :batch_size,
12
- :push, :store]
12
+ :push, :store, :logger]
13
13
 
14
14
  class ConfigurationWithoutDefaults < Struct.new(*CONFIG_ATTRS)
15
15
  end
@@ -39,6 +39,10 @@ module Rapns
39
39
  end
40
40
  end
41
41
 
42
+ def logger=(logger)
43
+ super(logger)
44
+ end
45
+
42
46
  def foreground=(bool)
43
47
  if Rapns.jruby?
44
48
  # The JVM does not support fork().
@@ -53,8 +57,6 @@ module Rapns
53
57
  end
54
58
  deprecated(:on_apns_feedback, 3.2, "Please use the Rapns.reflect API instead.")
55
59
 
56
- private
57
-
58
60
  def set_defaults
59
61
  if Rapns.jruby?
60
62
  # The JVM does not support fork().
@@ -71,6 +73,7 @@ module Rapns
71
73
  self.pid_file = nil
72
74
  self.apns_feedback_callback = nil
73
75
  self.store = :active_record
76
+ self.logger = nil
74
77
 
75
78
  # Internal options.
76
79
  self.embedded = false
@@ -49,7 +49,7 @@ module Rapns
49
49
 
50
50
  begin
51
51
  write_data(data)
52
- rescue Errno::EPIPE, Errno::ETIMEDOUT, OpenSSL::SSL::SSLError => e
52
+ rescue Errno::EPIPE, Errno::ETIMEDOUT, OpenSSL::SSL::SSLError, IOError => e
53
53
  retry_count += 1;
54
54
 
55
55
  if retry_count == 1
@@ -6,12 +6,7 @@ module Rapns
6
6
  begin
7
7
  log = File.open(File.join(Rails.root, 'log', 'rapns.log'), 'a')
8
8
  log.sync = true
9
- if defined?(ActiveSupport::BufferedLogger)
10
- @logger = ActiveSupport::BufferedLogger.new(log, Rails.logger.level)
11
- @logger.auto_flushing = Rails.logger.respond_to?(:auto_flushing) ? Rails.logger.auto_flushing : true
12
- else
13
- @logger = ActiveSupport::Logger.new(log, Rails.logger.level)
14
- end
9
+ setup_logger(log)
15
10
  rescue Errno::ENOENT, Errno::EPERM => e
16
11
  @logger = nil
17
12
  error(e)
@@ -34,6 +29,17 @@ module Rapns
34
29
 
35
30
  private
36
31
 
32
+ def setup_logger(log)
33
+ if Rapns.config.logger
34
+ @logger = Rapns.config.logger
35
+ elsif defined?(ActiveSupport::BufferedLogger)
36
+ @logger = ActiveSupport::BufferedLogger.new(log, Rails.logger.level)
37
+ @logger.auto_flushing = Rails.logger.respond_to?(:auto_flushing) ? Rails.logger.auto_flushing : true
38
+ else
39
+ @logger = ActiveSupport::Logger.new(log, Rails.logger.level)
40
+ end
41
+ end
42
+
37
43
  def log(where, msg, prefix = nil, io = STDOUT)
38
44
  if msg.is_a?(Exception)
39
45
  formatted_backtrace = msg.backtrace.join("\n")
@@ -22,7 +22,7 @@ module Rapns
22
22
  }
23
23
 
24
24
  scope :for_apps, lambda { |apps|
25
- where(:app_id => apps.map(&:id))
25
+ where('app_id IN (?)', apps.map(&:id))
26
26
  }
27
27
 
28
28
  def initialize(*args)
@@ -1,3 +1,3 @@
1
1
  module Rapns
2
- VERSION = '3.3.0'
2
+ VERSION = '3.3.1'
3
3
  end
@@ -31,16 +31,6 @@ describe Rapns::Apns::Notification do
31
31
  it "should default the expiry to 1 day" do
32
32
  notification.expiry.should == 1.day.to_i
33
33
  end
34
-
35
- # The notification must contain one of alert, sound or badge.
36
- # @see https://developer.apple.com/library/ios/#documentation/NetworkingInternet/Conceptual/RemoteNotificationsPG/ApplePushService/ApplePushService.html
37
- it "should not be valid if there is none of alert,sound,badge present" do
38
- notification.alert = nil
39
- notification.sound = nil
40
- notification.badge = nil
41
- notification.valid?.should be_false
42
- notification.errors[:base].should include("APN Notification must contain one of alert, badge, or sound")
43
- end
44
34
  end
45
35
 
46
36
  describe Rapns::Apns::Notification, "when assigning the device token" do
@@ -97,6 +87,13 @@ describe Rapns::Apns::Notification, "as_json" do
97
87
  notification.as_json["omg"].should == "lol"
98
88
  notification.as_json["wtf"].should == "dunno"
99
89
  end
90
+
91
+ it "should allow attributes to include a hash" do
92
+ notification = Rapns::Apns::Notification.new
93
+ notification.attributes_for_device = {:omg => {:ilike => :hashes}}
94
+ notification.as_json["omg"]["ilike"].should == "hashes"
95
+ end
96
+
100
97
  end
101
98
 
102
99
  describe Rapns::Apns::Notification, 'MDM' do
@@ -185,6 +185,14 @@ describe Rapns::Daemon::Apns::Connection do
185
185
  end
186
186
  end
187
187
 
188
+ describe "when write raises an IOError" do
189
+ it_should_behave_like "when the write fails"
190
+
191
+ def error_type
192
+ IOError
193
+ end
194
+ end
195
+
188
196
  describe "when reconnecting" do
189
197
  it 'closes the socket' do
190
198
  connection.should_receive(:close)
@@ -7,7 +7,8 @@ describe Rapns::Daemon, "when starting" do
7
7
  let(:certificate) { stub }
8
8
  let(:password) { stub }
9
9
  let(:config) { stub(:pid_file => nil, :airbrake_notify => false,
10
- :foreground => true, :embedded => false, :push => false, :store => :active_record) }
10
+ :foreground => true, :embedded => false, :push => false,
11
+ :store => :active_record, :logger => nil) }
11
12
  let(:logger) { stub(:logger, :info => nil, :error => nil, :warn => nil) }
12
13
 
13
14
  before do
@@ -102,6 +103,7 @@ end
102
103
 
103
104
  describe Rapns::Daemon, "when being shutdown" do
104
105
  let(:config) { stub(:pid_file => '/rails_root/rapns.pid') }
106
+ let(:logger) { stub(:info => nil, :error => nil, :warn => nil) }
105
107
 
106
108
  before do
107
109
  Rapns.stub(:config => config)
@@ -55,6 +55,14 @@ describe Rapns::Logger do
55
55
  Rapns::Logger.new(:foreground => true)
56
56
  end
57
57
 
58
+ it 'uses the user-defined logger' do
59
+ my_logger = stub
60
+ Rapns.config.logger = my_logger
61
+ logger = Rapns::Logger.new({})
62
+ my_logger.should_receive(:info)
63
+ logger.info('test')
64
+ end
65
+
58
66
  it "should print out the msg if running in the foreground" do
59
67
  logger = Rapns::Logger.new(:foreground => true)
60
68
  STDOUT.should_receive(:puts).with(/hi mom/)
@@ -75,6 +75,7 @@ RSpec.configure do |config|
75
75
  config.after(:each) do
76
76
  Rapns.logger = nil
77
77
  Rapns::Daemon.store = nil
78
+ Rapns.config.set_defaults if Rapns.config.kind_of?(Rapns::Configuration)
78
79
  end
79
80
  end
80
81
 
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: rapns
3
3
  version: !ruby/object:Gem::Version
4
- version: 3.3.0
4
+ version: 3.3.1
5
5
  prerelease:
6
6
  platform: ruby
7
7
  authors:
@@ -9,7 +9,7 @@ authors:
9
9
  autorequire:
10
10
  bindir: bin
11
11
  cert_chain: []
12
- date: 2013-04-21 00:00:00.000000000 Z
12
+ date: 2013-06-02 00:00:00.000000000 Z
13
13
  dependencies:
14
14
  - !ruby/object:Gem::Dependency
15
15
  name: multi_json
@@ -68,7 +68,6 @@ files:
68
68
  - lib/rapns/apns/device_token_format_validator.rb
69
69
  - lib/rapns/apns/feedback.rb
70
70
  - lib/rapns/apns/notification.rb
71
- - lib/rapns/apns/required_fields_validator.rb
72
71
  - lib/rapns/apns_feedback.rb
73
72
  - lib/rapns/app.rb
74
73
  - lib/rapns/configuration.rb
@@ -175,7 +174,7 @@ required_ruby_version: !ruby/object:Gem::Requirement
175
174
  version: '0'
176
175
  segments:
177
176
  - 0
178
- hash: -3085387548794744992
177
+ hash: -138032401300594712
179
178
  required_rubygems_version: !ruby/object:Gem::Requirement
180
179
  none: false
181
180
  requirements:
@@ -184,7 +183,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
184
183
  version: '0'
185
184
  segments:
186
185
  - 0
187
- hash: -3085387548794744992
186
+ hash: -138032401300594712
188
187
  requirements: []
189
188
  rubyforge_project:
190
189
  rubygems_version: 1.8.25
@@ -1,14 +0,0 @@
1
- module Rapns
2
- module Apns
3
- class RequiredFieldsValidator < ActiveModel::Validator
4
-
5
- # Notifications must contain one of alert, badge or sound as per:
6
- # https://developer.apple.com/library/ios/#documentation/NetworkingInternet/Conceptual/RemoteNotificationsPG/ApplePushService/ApplePushService.html
7
- def validate(record)
8
- if record.alert.nil? && record.badge.nil? && record.sound.nil?
9
- record.errors[:base] << "APN Notification must contain one of alert, badge, or sound"
10
- end
11
- end
12
- end
13
- end
14
- end