unipush 0.1.4 → 0.1.5
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.
- data/lib/unipush.rb +72 -34
- metadata +3 -3
data/lib/unipush.rb
CHANGED
@@ -1,5 +1,8 @@
|
|
1
|
+
require 'openssl'
|
2
|
+
require 'socket'
|
3
|
+
require 'active_support/core_ext'
|
1
4
|
class Unipush
|
2
|
-
attr_accessor :ios_cert_path
|
5
|
+
attr_accessor :ios_cert_path, :ssl, :socket, :ret # пусть к файлу сертификата
|
3
6
|
|
4
7
|
|
5
8
|
def initialize(mode='production')
|
@@ -19,6 +22,12 @@ class Unipush
|
|
19
22
|
@android_push_url = 'https://android.apis.google.com/c2dm/send'
|
20
23
|
|
21
24
|
@last_error = []
|
25
|
+
@unsent_messages = []
|
26
|
+
|
27
|
+
@sock = nil
|
28
|
+
@ssl = nil
|
29
|
+
|
30
|
+
@apns_feedback_conn = nil
|
22
31
|
end
|
23
32
|
|
24
33
|
def get_last_error
|
@@ -29,8 +38,44 @@ class Unipush
|
|
29
38
|
@unsent_messages.nil? ? false : @unsent_messages
|
30
39
|
end
|
31
40
|
|
41
|
+
def apns_connect
|
42
|
+
cert_path = @ios_cert_path
|
43
|
+
if FileTest.exist?(cert_path)
|
44
|
+
certificate = File.read(cert_path)
|
45
|
+
context = OpenSSL::SSL::SSLContext.new
|
46
|
+
context.key = OpenSSL::PKey::RSA.new(certificate)
|
47
|
+
context.cert = OpenSSL::X509::Certificate.new(certificate)
|
48
|
+
@sock = TCPSocket.new(@ios_push_url, @ios_push_port)
|
49
|
+
@ssl = OpenSSL::SSL::SSLSocket.new(@sock, context)
|
50
|
+
@ssl.sync = true
|
51
|
+
@ssl.connect
|
52
|
+
else
|
53
|
+
@last_error.push("Certificate file does not exist")
|
54
|
+
false
|
55
|
+
end
|
56
|
+
end
|
57
|
+
|
58
|
+
|
59
|
+
def apns_check_conn
|
60
|
+
if @ssl && @sock
|
61
|
+
unless @ssl.state == "SSLOK "
|
62
|
+
self.apns_connect
|
63
|
+
end
|
64
|
+
else
|
65
|
+
self.apns_connect
|
66
|
+
end
|
67
|
+
@ssl.state == "SSLOK "
|
68
|
+
end
|
69
|
+
|
70
|
+
def apns_close
|
71
|
+
if @ssl
|
72
|
+
@ssl.close
|
73
|
+
@sock.close
|
74
|
+
end
|
75
|
+
end
|
76
|
+
|
32
77
|
#message={:text=>"", :badge=>0, :newsstand=>true, :track=>true, :add=>{:param1=>1, :param2=>2}}
|
33
|
-
def prepare_ios_message(token, message)
|
78
|
+
def prepare_ios_message(token, message, message_id=0)
|
34
79
|
json = ""
|
35
80
|
if message[:newsstand]
|
36
81
|
json = '{"aps":{"content-available":1}}'
|
@@ -53,7 +98,7 @@ class Unipush
|
|
53
98
|
|
54
99
|
if message[:track]
|
55
100
|
tt = Time.now + 1.day
|
56
|
-
mes = [1,
|
101
|
+
mes = [1, message_id, tt.to_i, 0, 32, token, 0, json.bytesize, json].pack("cNNcca*cca*")
|
57
102
|
else
|
58
103
|
mes = [0, 0, 32, token, 0, json.bytesize, json].pack("ccca*cca*")
|
59
104
|
end
|
@@ -64,43 +109,36 @@ class Unipush
|
|
64
109
|
# messages = [message2, message2, ...]
|
65
110
|
# message=[token, message={:text=>"", :badge=>0, :newsstand=>true, :track=>true, :add=>{:param1=>1, :param2=>2}}]
|
66
111
|
def send_ios_messages(messages)
|
67
|
-
|
68
|
-
|
69
|
-
|
70
|
-
|
71
|
-
|
72
|
-
|
73
|
-
|
74
|
-
|
75
|
-
|
76
|
-
|
77
|
-
ssl.connect
|
78
|
-
messages.each_with_index do |m, k|
|
79
|
-
mes = prepare_ios_message(m[0], m[1])
|
80
|
-
if mes
|
81
|
-
ssl.write(mes)
|
82
|
-
if ssl.pending >0 && m[1][:track]
|
83
|
-
tmp = ssl.readline
|
112
|
+
begin
|
113
|
+
messages.each_with_index do |m, k|
|
114
|
+
mes = prepare_ios_message(m[0], m[1], k)
|
115
|
+
if mes
|
116
|
+
if self.apns_check_conn
|
117
|
+
cnt = 0
|
118
|
+
@ssl.write(mes)
|
119
|
+
begin
|
120
|
+
cnt += 1
|
121
|
+
tmp = @ssl.read_nonblock(8)
|
84
122
|
reply = tmp.unpack("CCN")
|
85
|
-
@unsent_messages.push(
|
86
|
-
@last_error.push("Could not send message #{
|
123
|
+
@unsent_messages.push(reply[2])
|
124
|
+
@last_error.push("Could not send message #{reply[2]} width error: "+reply.join(", "))
|
125
|
+
self.apns_close
|
126
|
+
break
|
127
|
+
rescue IO::WaitReadable
|
128
|
+
retry if cnt<1000
|
87
129
|
end
|
88
|
-
|
89
|
-
@unsent_messages = [] if @unsent_messages.nil?
|
90
|
-
@unsent_messages.push(k)
|
130
|
+
puts k, cnt
|
91
131
|
end
|
132
|
+
else
|
133
|
+
@unsent_messages = [] if @unsent_messages.nil?
|
134
|
+
@unsent_messages.push(k)
|
92
135
|
end
|
93
|
-
ssl.close
|
94
|
-
socket.close
|
95
|
-
rescue
|
96
|
-
@last_error.push("Could not send messages. Exception: #{$!.inspect}")
|
97
|
-
false
|
98
|
-
else
|
99
|
-
true
|
100
136
|
end
|
101
|
-
|
102
|
-
@last_error.push("
|
137
|
+
rescue
|
138
|
+
@last_error.push("Could not send messages. Exception: #{$!.inspect}")
|
103
139
|
false
|
140
|
+
else
|
141
|
+
true
|
104
142
|
end
|
105
143
|
end
|
106
144
|
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: unipush
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.1.
|
4
|
+
version: 0.1.5
|
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:
|
12
|
+
date: 2013-08-12 00:00:00.000000000 Z
|
13
13
|
dependencies: []
|
14
14
|
description: A simple push notification sender for iOS and Android
|
15
15
|
email: alexey.s.kirov@gmail.com
|
@@ -38,7 +38,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
38
38
|
version: '0'
|
39
39
|
requirements: []
|
40
40
|
rubyforge_project:
|
41
|
-
rubygems_version: 1.8.
|
41
|
+
rubygems_version: 1.8.23
|
42
42
|
signing_key:
|
43
43
|
specification_version: 3
|
44
44
|
summary: Unipush
|