mixpanel-ruby 1.7.0 → 2.0.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +7 -0
- data/.travis.yml +1 -0
- data/Readme.rdoc +7 -0
- data/demo/faraday_consumer.rb +3 -3
- data/demo/out_of_process_consumer.rb +1 -1
- data/lib/mixpanel-ruby/consumer.rb +38 -20
- data/lib/mixpanel-ruby/events.rb +30 -21
- data/lib/mixpanel-ruby/people.rb +31 -44
- data/lib/mixpanel-ruby/tracker.rb +12 -7
- data/lib/mixpanel-ruby/version.rb +1 -1
- data/mixpanel-ruby.gemspec +2 -0
- data/spec/mixpanel-ruby/consumer_spec.rb +12 -12
- metadata +17 -25
checksums.yaml
ADDED
@@ -0,0 +1,7 @@
|
|
1
|
+
---
|
2
|
+
SHA1:
|
3
|
+
metadata.gz: 84920bc74cc457ded903c7d7ca1175b1b72a4bd1
|
4
|
+
data.tar.gz: d860d1aabfa9cbd03c5b946f2c1ed58d927ff271
|
5
|
+
SHA512:
|
6
|
+
metadata.gz: fd13c103e5cc9b3f6bd447feb365f8457c3c8b71c1ed0ebdbd019040f15a7f0d1d063b85aa1bfaea57f7c768f6d42711c8aecbf750e7fefe3e3ea1635fe0e099
|
7
|
+
data.tar.gz: bb93ec5c1594bf5eabae0a8a92252d4049856b5b7bc21cd6443adbe9fcdd7b613e7d855b8c5377f3c93515a4cd69401d68c9586e845b5f3c0faffa043eb5c19d
|
data/.travis.yml
CHANGED
data/Readme.rdoc
CHANGED
@@ -49,6 +49,13 @@ In particular, for Rails apps, the following projects are currently actively mai
|
|
49
49
|
|
50
50
|
== Changes
|
51
51
|
|
52
|
+
== 2.0.0
|
53
|
+
* Raise mixpanel server and connection errors in Mixpanel::Consumer.
|
54
|
+
* All public methods in Mixpanel::Event, Mixpanel::People, and subsequently Mixpanel::Tracker
|
55
|
+
rescue Mixpanel errors and return false in the case of an error, return true otherwise
|
56
|
+
* Deprecate Mixpanel::Consumer#send, replace with Mixpanel::Consumer#send!
|
57
|
+
* Require ruby version minimum of 2.0.0
|
58
|
+
|
52
59
|
== 1.4.0
|
53
60
|
* Allow unset to unset multiple properties
|
54
61
|
|
data/demo/faraday_consumer.rb
CHANGED
@@ -20,7 +20,7 @@ if __FILE__ == $0
|
|
20
20
|
faraday_consumer = FaradayConsumer.new
|
21
21
|
|
22
22
|
faraday_tracker = Mixpanel::Tracker.new(DEMO_TOKEN) do |type, message|
|
23
|
-
faraday_consumer.send(type, message)
|
23
|
+
faraday_consumer.send!(type, message)
|
24
24
|
end
|
25
25
|
faraday_tracker.track('ID', 'Event tracked through Faraday')
|
26
26
|
|
@@ -28,11 +28,11 @@ if __FILE__ == $0
|
|
28
28
|
# consumer.
|
29
29
|
|
30
30
|
buffered_faraday_consumer = Mixpanel::BufferedConsumer.new do |type, message|
|
31
|
-
faraday_consumer.send(type, message)
|
31
|
+
faraday_consumer.send!(type, message)
|
32
32
|
end
|
33
33
|
|
34
34
|
buffered_faraday_tracker = Mixpanel::Tracker.new(DEMO_TOKEN) do |type, message|
|
35
|
-
buffered_faraday_consumer.send(type, message)
|
35
|
+
buffered_faraday_consumer.send!(type, message)
|
36
36
|
end
|
37
37
|
|
38
38
|
buffered_faraday_tracker.track('ID', 'Event tracked (buffered) through faraday')
|
@@ -3,7 +3,13 @@ require 'net/https'
|
|
3
3
|
require 'json'
|
4
4
|
|
5
5
|
module Mixpanel
|
6
|
-
class
|
6
|
+
class MixpanelError < StandardError
|
7
|
+
end
|
8
|
+
|
9
|
+
class ConnectionError < MixpanelError
|
10
|
+
end
|
11
|
+
|
12
|
+
class ServerError < MixpanelError
|
7
13
|
end
|
8
14
|
|
9
15
|
@@init_http = nil
|
@@ -35,7 +41,7 @@ module Mixpanel
|
|
35
41
|
# file, or do whatever else you might find useful.
|
36
42
|
#
|
37
43
|
# You can provide your own consumer to your Mixpanel::Trackers,
|
38
|
-
# either by passing in an argument with a #send method when you construct
|
44
|
+
# either by passing in an argument with a #send! method when you construct
|
39
45
|
# the tracker, or just passing a block to Mixpanel::Tracker.new
|
40
46
|
#
|
41
47
|
# tracker = Mixpanel::Tracker.new(MY_TOKEN) do |type, message|
|
@@ -50,7 +56,7 @@ module Mixpanel
|
|
50
56
|
# mixpanel = Mixpanel::Consumer
|
51
57
|
# while true
|
52
58
|
# message_json = @kestrel.get(ANALYTICS_QUEUE)
|
53
|
-
# mixpanel.send(*JSON.load(message_json))
|
59
|
+
# mixpanel.send!(*JSON.load(message_json))
|
54
60
|
# end
|
55
61
|
#
|
56
62
|
# Mixpanel::Consumer is the default consumer. It sends each message,
|
@@ -70,15 +76,15 @@ module Mixpanel
|
|
70
76
|
# Send the given string message to Mixpanel. Type should be
|
71
77
|
# one of :event, :profile_update or :import, which will determine the endpoint.
|
72
78
|
#
|
73
|
-
# Mixpanel::Consumer#send sends messages to Mixpanel immediately on
|
79
|
+
# Mixpanel::Consumer#send! sends messages to Mixpanel immediately on
|
74
80
|
# each call. To reduce the overall bandwidth you use when communicating
|
75
81
|
# with Mixpanel, you can also use Mixpanel::BufferedConsumer
|
76
|
-
def send(type, message)
|
82
|
+
def send!(type, message)
|
77
83
|
type = type.to_sym
|
78
84
|
endpoint = {
|
79
85
|
:event => @events_endpoint,
|
80
86
|
:profile_update => @update_endpoint,
|
81
|
-
:import => @import_endpoint
|
87
|
+
:import => @import_endpoint,
|
82
88
|
}[type]
|
83
89
|
|
84
90
|
decoded_message = JSON.load(message)
|
@@ -88,7 +94,11 @@ module Mixpanel
|
|
88
94
|
form_data = {"data" => data, "verbose" => 1}
|
89
95
|
form_data.merge!("api_key" => api_key) if api_key
|
90
96
|
|
91
|
-
|
97
|
+
begin
|
98
|
+
response_code, response_body = request(endpoint, form_data)
|
99
|
+
rescue => e
|
100
|
+
raise ConnectionError.new("Could not connect to Mixpanel, with error \"#{e.message}\".")
|
101
|
+
end
|
92
102
|
|
93
103
|
succeeded = nil
|
94
104
|
if response_code.to_i == 200
|
@@ -96,11 +106,17 @@ module Mixpanel
|
|
96
106
|
succeeded = result['status'] == 1
|
97
107
|
end
|
98
108
|
|
99
|
-
if !
|
100
|
-
raise
|
109
|
+
if !succeeded
|
110
|
+
raise ServerError.new("Could not write to Mixpanel, server responded with #{response_code} returning: '#{response_body}'")
|
101
111
|
end
|
102
112
|
end
|
103
113
|
|
114
|
+
# This method was deprecated in release 2.0.0, please use send! instead
|
115
|
+
def send(type, message)
|
116
|
+
warn '[DEPRECATION] send has been deprecated as of release 2.0.0, please use send! instead'
|
117
|
+
send!(type, message)
|
118
|
+
end
|
119
|
+
|
104
120
|
# Request takes an endpoint HTTP or HTTPS url, and a Hash of data
|
105
121
|
# to post to that url. It should return a pair of
|
106
122
|
#
|
@@ -125,10 +141,11 @@ module Mixpanel
|
|
125
141
|
response = client.request(request)
|
126
142
|
[response.code, response.body]
|
127
143
|
end
|
144
|
+
|
128
145
|
end
|
129
146
|
|
130
147
|
# BufferedConsumer buffers messages in memory, and sends messages as
|
131
|
-
# a batch. This can improve performance, but calls to #send may
|
148
|
+
# a batch. This can improve performance, but calls to #send! may
|
132
149
|
# still block if the buffer is full. If you use this consumer, you
|
133
150
|
# should call #flush when your application exits or the messages
|
134
151
|
# remaining in the buffer will not be sent.
|
@@ -139,7 +156,7 @@ module Mixpanel
|
|
139
156
|
# buffered_consumer = Mixpanel::BufferedConsumer.new
|
140
157
|
# begin
|
141
158
|
# buffered_tracker = Mixpanel::Tracker.new(YOUR_TOKEN) do |type, message|
|
142
|
-
# buffered_consumer.send(type, message)
|
159
|
+
# buffered_consumer.send!(type, message)
|
143
160
|
# end
|
144
161
|
# # Do some tracking here
|
145
162
|
# ...
|
@@ -169,16 +186,17 @@ module Mixpanel
|
|
169
186
|
# ignored.
|
170
187
|
def initialize(events_endpoint=nil, update_endpoint=nil, import_endpoint=nil, max_buffer_length=MAX_LENGTH, &block)
|
171
188
|
@max_length = [max_buffer_length, MAX_LENGTH].min
|
189
|
+
@buffers = {
|
190
|
+
:event => [],
|
191
|
+
:profile_update => [],
|
192
|
+
}
|
193
|
+
|
172
194
|
if block
|
173
195
|
@sink = block
|
174
196
|
else
|
175
197
|
consumer = Consumer.new(events_endpoint, update_endpoint, import_endpoint)
|
176
|
-
@sink = consumer.method(:send)
|
198
|
+
@sink = consumer.method(:send!)
|
177
199
|
end
|
178
|
-
@buffers = {
|
179
|
-
:event => [],
|
180
|
-
:profile_update => [],
|
181
|
-
}
|
182
200
|
end
|
183
201
|
|
184
202
|
# Stores a message for Mixpanel in memory. When the buffer
|
@@ -187,13 +205,12 @@ module Mixpanel
|
|
187
205
|
#
|
188
206
|
# Currently, only :event and :profile_update messages are buffered,
|
189
207
|
# :import messages will be send immediately on call.
|
190
|
-
def send(type, message)
|
208
|
+
def send!(type, message)
|
191
209
|
type = type.to_sym
|
210
|
+
|
192
211
|
if @buffers.has_key? type
|
193
212
|
@buffers[type] << message
|
194
|
-
if @buffers[type].length >= @max_length
|
195
|
-
flush_type(type)
|
196
|
-
end
|
213
|
+
flush_type(type) if @buffers[type].length >= @max_length
|
197
214
|
else
|
198
215
|
@sink.call(type, message)
|
199
216
|
end
|
@@ -218,6 +235,7 @@ module Mixpanel
|
|
218
235
|
end
|
219
236
|
|
220
237
|
private
|
238
|
+
|
221
239
|
def self.with_http(http)
|
222
240
|
if @@init_http
|
223
241
|
@@init_http.call(http)
|
data/lib/mixpanel-ruby/events.rb
CHANGED
@@ -22,11 +22,12 @@ module Mixpanel
|
|
22
22
|
#
|
23
23
|
def initialize(token, &block)
|
24
24
|
@token = token
|
25
|
+
|
25
26
|
if block
|
26
27
|
@sink = block
|
27
28
|
else
|
28
29
|
consumer = Consumer.new
|
29
|
-
@sink = consumer.method(:send)
|
30
|
+
@sink = consumer.method(:send!)
|
30
31
|
end
|
31
32
|
end
|
32
33
|
|
@@ -49,26 +50,29 @@ module Mixpanel
|
|
49
50
|
# })
|
50
51
|
def track(distinct_id, event, properties={}, ip=nil)
|
51
52
|
properties = {
|
52
|
-
|
53
|
-
|
54
|
-
|
55
|
-
|
56
|
-
|
53
|
+
'distinct_id' => distinct_id,
|
54
|
+
'token' => @token,
|
55
|
+
'time' => Time.now.to_i,
|
56
|
+
'mp_lib' => 'ruby',
|
57
|
+
'$lib_version' => Mixpanel::VERSION,
|
57
58
|
}.merge(properties)
|
58
|
-
if ip
|
59
|
-
properties['ip'] = ip
|
60
|
-
end
|
59
|
+
properties['ip'] = ip if ip
|
61
60
|
|
62
61
|
data = {
|
63
62
|
'event' => event,
|
64
|
-
'properties' => properties
|
63
|
+
'properties' => properties,
|
65
64
|
}
|
66
65
|
|
67
|
-
message = {
|
68
|
-
|
69
|
-
|
66
|
+
message = {'data' => data}
|
67
|
+
|
68
|
+
ret = true
|
69
|
+
begin
|
70
|
+
@sink.call(:event, message.to_json)
|
71
|
+
rescue MixpanelError
|
72
|
+
ret = false
|
73
|
+
end
|
70
74
|
|
71
|
-
|
75
|
+
ret
|
72
76
|
end
|
73
77
|
|
74
78
|
# Imports an event that has occurred in the past, along with a distinct_id
|
@@ -94,23 +98,28 @@ module Mixpanel
|
|
94
98
|
'token' => @token,
|
95
99
|
'time' => Time.now.to_i,
|
96
100
|
'mp_lib' => 'ruby',
|
97
|
-
'$lib_version' => Mixpanel::VERSION
|
101
|
+
'$lib_version' => Mixpanel::VERSION,
|
98
102
|
}.merge(properties)
|
99
|
-
if ip
|
100
|
-
properties['ip'] = ip
|
101
|
-
end
|
103
|
+
properties['ip'] = ip if ip
|
102
104
|
|
103
105
|
data = {
|
104
106
|
'event' => event,
|
105
|
-
'properties' => properties
|
107
|
+
'properties' => properties,
|
106
108
|
}
|
107
109
|
|
108
110
|
message = {
|
109
111
|
'data' => data,
|
110
|
-
'api_key' => api_key
|
112
|
+
'api_key' => api_key,
|
111
113
|
}
|
112
114
|
|
113
|
-
|
115
|
+
ret = true
|
116
|
+
begin
|
117
|
+
@sink.call(:import, message.to_json)
|
118
|
+
rescue MixpanelError
|
119
|
+
ret = false
|
120
|
+
end
|
121
|
+
|
122
|
+
ret
|
114
123
|
end
|
115
124
|
end
|
116
125
|
end
|
data/lib/mixpanel-ruby/people.rb
CHANGED
@@ -27,7 +27,7 @@ module Mixpanel
|
|
27
27
|
@sink = block
|
28
28
|
else
|
29
29
|
consumer = Consumer.new
|
30
|
-
@sink = consumer.method(:send)
|
30
|
+
@sink = consumer.method(:send!)
|
31
31
|
end
|
32
32
|
end
|
33
33
|
|
@@ -48,13 +48,10 @@ module Mixpanel
|
|
48
48
|
def set(distinct_id, properties, ip=nil, optional_params={})
|
49
49
|
properties = fix_property_dates(properties)
|
50
50
|
message = {
|
51
|
-
|
52
|
-
|
51
|
+
'$distinct_id' => distinct_id,
|
52
|
+
'$set' => properties,
|
53
53
|
}.merge(optional_params)
|
54
|
-
|
55
|
-
if ip
|
56
|
-
message['$ip'] = ip
|
57
|
-
end
|
54
|
+
message['$ip'] = ip if ip
|
58
55
|
|
59
56
|
update(message)
|
60
57
|
end
|
@@ -72,13 +69,10 @@ module Mixpanel
|
|
72
69
|
def set_once(distinct_id, properties, ip=nil, optional_params={})
|
73
70
|
properties = fix_property_dates(properties)
|
74
71
|
message = {
|
75
|
-
|
76
|
-
|
72
|
+
'$distinct_id' => distinct_id,
|
73
|
+
'$set_once' => properties,
|
77
74
|
}.merge(optional_params)
|
78
|
-
|
79
|
-
if ip
|
80
|
-
message['$ip'] = ip
|
81
|
-
end
|
75
|
+
message['$ip'] = ip if ip
|
82
76
|
|
83
77
|
update(message)
|
84
78
|
end
|
@@ -98,13 +92,10 @@ module Mixpanel
|
|
98
92
|
def increment(distinct_id, properties, ip=nil, optional_params={})
|
99
93
|
properties = fix_property_dates(properties)
|
100
94
|
message = {
|
101
|
-
|
102
|
-
|
95
|
+
'$distinct_id' => distinct_id,
|
96
|
+
'$add' => properties,
|
103
97
|
}.merge(optional_params)
|
104
|
-
|
105
|
-
if ip
|
106
|
-
message['$ip'] = ip
|
107
|
-
end
|
98
|
+
message['$ip'] = ip if ip
|
108
99
|
|
109
100
|
update(message)
|
110
101
|
end
|
@@ -133,13 +124,10 @@ module Mixpanel
|
|
133
124
|
def append(distinct_id, properties, ip=nil, optional_params={})
|
134
125
|
properties = fix_property_dates(properties)
|
135
126
|
message = {
|
136
|
-
|
137
|
-
|
127
|
+
'$distinct_id' => distinct_id,
|
128
|
+
'$append' => properties,
|
138
129
|
}.merge(optional_params)
|
139
|
-
|
140
|
-
if ip
|
141
|
-
message['$ip'] = ip
|
142
|
-
end
|
130
|
+
message['$ip'] = ip if ip
|
143
131
|
|
144
132
|
update(message)
|
145
133
|
end
|
@@ -158,13 +146,10 @@ module Mixpanel
|
|
158
146
|
def union(distinct_id, properties, ip=nil, optional_params={})
|
159
147
|
properties = fix_property_dates(properties)
|
160
148
|
message = {
|
161
|
-
|
162
|
-
|
149
|
+
'$distinct_id' => distinct_id,
|
150
|
+
'$union' => properties,
|
163
151
|
}.merge(optional_params)
|
164
|
-
|
165
|
-
if ip
|
166
|
-
message['$ip'] = ip
|
167
|
-
end
|
152
|
+
message['$ip'] = ip if ip
|
168
153
|
|
169
154
|
update(message)
|
170
155
|
end
|
@@ -182,13 +167,10 @@ module Mixpanel
|
|
182
167
|
def unset(distinct_id, properties, ip=nil, optional_params={})
|
183
168
|
properties = [properties] unless properties.is_a?(Array)
|
184
169
|
message = {
|
185
|
-
|
186
|
-
|
170
|
+
'$distinct_id' => distinct_id,
|
171
|
+
'$unset' => properties,
|
187
172
|
}.merge(optional_params)
|
188
|
-
|
189
|
-
if ip
|
190
|
-
message['$ip'] = ip
|
191
|
-
end
|
173
|
+
message['$ip'] = ip if ip
|
192
174
|
|
193
175
|
update(message)
|
194
176
|
end
|
@@ -222,8 +204,8 @@ module Mixpanel
|
|
222
204
|
# {"$ignore_alias"=>true}
|
223
205
|
def delete_user(distinct_id, optional_params={})
|
224
206
|
update({
|
225
|
-
|
226
|
-
|
207
|
+
'$distinct_id' => distinct_id,
|
208
|
+
'$delete' => '',
|
227
209
|
}.merge(optional_params))
|
228
210
|
end
|
229
211
|
|
@@ -238,14 +220,19 @@ module Mixpanel
|
|
238
220
|
def update(message)
|
239
221
|
data = {
|
240
222
|
'$token' => @token,
|
241
|
-
'$time' => ((Time.now.to_f) * 1000.0).to_i
|
223
|
+
'$time' => ((Time.now.to_f) * 1000.0).to_i,
|
242
224
|
}.merge(message)
|
243
225
|
|
244
|
-
message = {
|
245
|
-
|
246
|
-
|
226
|
+
message = {'data' => data}
|
227
|
+
|
228
|
+
ret = true
|
229
|
+
begin
|
230
|
+
@sink.call(:profile_update, message.to_json)
|
231
|
+
rescue MixpanelError
|
232
|
+
ret = false
|
233
|
+
end
|
247
234
|
|
248
|
-
|
235
|
+
ret
|
249
236
|
end
|
250
237
|
|
251
238
|
private
|
@@ -40,8 +40,8 @@ module Mixpanel
|
|
40
40
|
# end
|
41
41
|
#
|
42
42
|
# If a block is provided, it is passed a type (one of :event or :profile_update)
|
43
|
-
# and a string message. This same format is accepted by Mixpanel::Consumer#send
|
44
|
-
# and Mixpanel::BufferedConsumer#send
|
43
|
+
# and a string message. This same format is accepted by Mixpanel::Consumer#send!
|
44
|
+
# and Mixpanel::BufferedConsumer#send!
|
45
45
|
def initialize(token, &block)
|
46
46
|
super(token, &block)
|
47
47
|
@token = token
|
@@ -116,15 +116,20 @@ module Mixpanel
|
|
116
116
|
'properties' => {
|
117
117
|
'distinct_id' => real_id,
|
118
118
|
'alias' => alias_id,
|
119
|
-
'token' => @token
|
119
|
+
'token' => @token,
|
120
120
|
}
|
121
121
|
}
|
122
122
|
|
123
|
-
message = {
|
124
|
-
|
125
|
-
|
123
|
+
message = {'data' => data}
|
124
|
+
|
125
|
+
ret = true
|
126
|
+
begin
|
127
|
+
consumer.send!(:event, message.to_json)
|
128
|
+
rescue MixpanelError
|
129
|
+
ret = false
|
130
|
+
end
|
126
131
|
|
127
|
-
|
132
|
+
ret
|
128
133
|
end
|
129
134
|
end
|
130
135
|
end
|
data/mixpanel-ruby.gemspec
CHANGED
@@ -12,6 +12,8 @@ spec = Gem::Specification.new do |spec|
|
|
12
12
|
spec.homepage = 'https://mixpanel.com/help/reference/ruby'
|
13
13
|
spec.license = 'Apache License 2.0'
|
14
14
|
|
15
|
+
spec.required_ruby_version = '>= 2.0.0'
|
16
|
+
|
15
17
|
spec.add_development_dependency 'rake'
|
16
18
|
spec.add_development_dependency 'rspec', '~> 3.0.0'
|
17
19
|
spec.add_development_dependency 'webmock', '~> 1.18.0'
|
@@ -9,35 +9,35 @@ describe Mixpanel::Consumer do
|
|
9
9
|
shared_examples_for 'consumer' do
|
10
10
|
it 'should send a request to api.mixpanel.com/track on events' do
|
11
11
|
stub_request(:any, 'https://api.mixpanel.com/track').to_return({:body => '{"status": 1, "error": null}'})
|
12
|
-
subject.send(:event, {'data' => 'TEST EVENT MESSAGE'}.to_json)
|
12
|
+
subject.send!(:event, {'data' => 'TEST EVENT MESSAGE'}.to_json)
|
13
13
|
expect(WebMock).to have_requested(:post, 'https://api.mixpanel.com/track').
|
14
14
|
with(:body => {'data' => 'IlRFU1QgRVZFTlQgTUVTU0FHRSI=', 'verbose' => '1' })
|
15
15
|
end
|
16
16
|
|
17
17
|
it 'should send a request to api.mixpanel.com/people on profile updates' do
|
18
18
|
stub_request(:any, 'https://api.mixpanel.com/engage').to_return({:body => '{"status": 1, "error": null}'})
|
19
|
-
subject.send(:profile_update, {'data' => 'TEST EVENT MESSAGE'}.to_json)
|
19
|
+
subject.send!(:profile_update, {'data' => 'TEST EVENT MESSAGE'}.to_json)
|
20
20
|
expect(WebMock).to have_requested(:post, 'https://api.mixpanel.com/engage').
|
21
21
|
with(:body => {'data' => 'IlRFU1QgRVZFTlQgTUVTU0FHRSI=', 'verbose' => '1' })
|
22
22
|
end
|
23
23
|
|
24
24
|
it 'should send a request to api.mixpanel.com/import on event imports' do
|
25
25
|
stub_request(:any, 'https://api.mixpanel.com/import').to_return({:body => '{"status": 1, "error": null}'})
|
26
|
-
subject.send(:import, {'data' => 'TEST EVENT MESSAGE', 'api_key' => 'API_KEY','verbose' => '1' }.to_json)
|
26
|
+
subject.send!(:import, {'data' => 'TEST EVENT MESSAGE', 'api_key' => 'API_KEY','verbose' => '1' }.to_json)
|
27
27
|
expect(WebMock).to have_requested(:post, 'https://api.mixpanel.com/import').
|
28
28
|
with(:body => {'data' => 'IlRFU1QgRVZFTlQgTUVTU0FHRSI=', 'api_key' => 'API_KEY', 'verbose' => '1' })
|
29
29
|
end
|
30
30
|
|
31
31
|
it 'should encode long messages without newlines' do
|
32
32
|
stub_request(:any, 'https://api.mixpanel.com/track').to_return({:body => '{"status": 1, "error": null}'})
|
33
|
-
subject.send(:event, {'data' => 'BASE64-ENCODED VERSION OF BIN. THIS METHOD COMPLIES WITH RFC 2045. LINE FEEDS ARE ADDED TO EVERY 60 ENCODED CHARACTORS. IN RUBY 1.8 WE NEED TO JUST CALL ENCODE64 AND REMOVE THE LINE FEEDS, IN RUBY 1.9 WE CALL STRIC_ENCODED64 METHOD INSTEAD'}.to_json)
|
33
|
+
subject.send!(:event, {'data' => 'BASE64-ENCODED VERSION OF BIN. THIS METHOD COMPLIES WITH RFC 2045. LINE FEEDS ARE ADDED TO EVERY 60 ENCODED CHARACTORS. IN RUBY 1.8 WE NEED TO JUST CALL ENCODE64 AND REMOVE THE LINE FEEDS, IN RUBY 1.9 WE CALL STRIC_ENCODED64 METHOD INSTEAD'}.to_json)
|
34
34
|
expect(WebMock).to have_requested(:post, 'https://api.mixpanel.com/track').
|
35
35
|
with(:body => {'data' => 'IkJBU0U2NC1FTkNPREVEIFZFUlNJT04gT0YgQklOLiBUSElTIE1FVEhPRCBDT01QTElFUyBXSVRIIFJGQyAyMDQ1LiBMSU5FIEZFRURTIEFSRSBBRERFRCBUTyBFVkVSWSA2MCBFTkNPREVEIENIQVJBQ1RPUlMuIElOIFJVQlkgMS44IFdFIE5FRUQgVE8gSlVTVCBDQUxMIEVOQ09ERTY0IEFORCBSRU1PVkUgVEhFIExJTkUgRkVFRFMsIElOIFJVQlkgMS45IFdFIENBTEwgU1RSSUNfRU5DT0RFRDY0IE1FVEhPRCBJTlNURUFEIg==', 'verbose' => '1'})
|
36
36
|
end
|
37
37
|
|
38
38
|
it 'should provide thorough information in case mixpanel fails' do
|
39
39
|
stub_request(:any, 'https://api.mixpanel.com/track').to_return({:status => 401, :body => "nutcakes"})
|
40
|
-
expect { subject.send(:event, {'data' => 'TEST EVENT MESSAGE'}.to_json) }.to raise_exception('Could not write to Mixpanel, server responded with 401 returning: \'nutcakes\'')
|
40
|
+
expect { subject.send!(:event, {'data' => 'TEST EVENT MESSAGE'}.to_json) }.to raise_exception('Could not write to Mixpanel, server responded with 401 returning: \'nutcakes\'')
|
41
41
|
end
|
42
42
|
end
|
43
43
|
|
@@ -77,7 +77,7 @@ describe Mixpanel::BufferedConsumer do
|
|
77
77
|
|
78
78
|
it 'should not send a request for a single message until flush is called' do
|
79
79
|
stub_request(:any, 'https://api.mixpanel.com/track').to_return({:body => '{"status": 1, "error": null}'})
|
80
|
-
subject.send(:event, {'data' => 'TEST EVENT 1'}.to_json)
|
80
|
+
subject.send!(:event, {'data' => 'TEST EVENT 1'}.to_json)
|
81
81
|
expect(WebMock).to have_not_requested(:post, 'https://api.mixpanel.com/track')
|
82
82
|
|
83
83
|
subject.flush()
|
@@ -89,7 +89,7 @@ describe Mixpanel::BufferedConsumer do
|
|
89
89
|
stub_request(:any, 'https://api.mixpanel.com/track').to_return({:body => '{"status": 1, "error": null}'})
|
90
90
|
|
91
91
|
max_length.times do |i|
|
92
|
-
subject.send(:event, {'data' => "x #{i}"}.to_json)
|
92
|
+
subject.send!(:event, {'data' => "x #{i}"}.to_json)
|
93
93
|
end
|
94
94
|
|
95
95
|
expect(WebMock).to have_requested(:post, 'https://api.mixpanel.com/track').
|
@@ -98,10 +98,10 @@ describe Mixpanel::BufferedConsumer do
|
|
98
98
|
|
99
99
|
it 'should send one message per api key on import' do
|
100
100
|
stub_request(:any, 'https://api.mixpanel.com/import').to_return({:body => '{"status": 1, "error": null}'})
|
101
|
-
subject.send(:import, {'data' => 'TEST EVENT 1', 'api_key' => 'KEY 1'}.to_json)
|
102
|
-
subject.send(:import, {'data' => 'TEST EVENT 1', 'api_key' => 'KEY 2'}.to_json)
|
103
|
-
subject.send(:import, {'data' => 'TEST EVENT 2', 'api_key' => 'KEY 1'}.to_json)
|
104
|
-
subject.send(:import, {'data' => 'TEST EVENT 2', 'api_key' => 'KEY 2'}.to_json)
|
101
|
+
subject.send!(:import, {'data' => 'TEST EVENT 1', 'api_key' => 'KEY 1'}.to_json)
|
102
|
+
subject.send!(:import, {'data' => 'TEST EVENT 1', 'api_key' => 'KEY 2'}.to_json)
|
103
|
+
subject.send!(:import, {'data' => 'TEST EVENT 2', 'api_key' => 'KEY 1'}.to_json)
|
104
|
+
subject.send!(:import, {'data' => 'TEST EVENT 2', 'api_key' => 'KEY 2'}.to_json)
|
105
105
|
subject.flush
|
106
106
|
|
107
107
|
expect(WebMock).to have_requested(:post, 'https://api.mixpanel.com/import').
|
@@ -122,7 +122,7 @@ describe Mixpanel::BufferedConsumer do
|
|
122
122
|
|
123
123
|
it 'should call block instead of making default requests on flush' do
|
124
124
|
3.times do |i|
|
125
|
-
subject.send(:event, {'data' => "x #{i}"}.to_json)
|
125
|
+
subject.send!(:event, {'data' => "x #{i}"}.to_json)
|
126
126
|
end
|
127
127
|
|
128
128
|
expect(messages_seen).to match_array(
|
metadata
CHANGED
@@ -1,62 +1,55 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: mixpanel-ruby
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version:
|
5
|
-
prerelease:
|
4
|
+
version: 2.0.0
|
6
5
|
platform: ruby
|
7
6
|
authors:
|
8
7
|
- Mixpanel
|
9
8
|
autorequire:
|
10
9
|
bindir: bin
|
11
10
|
cert_chain: []
|
12
|
-
date: 2015-
|
11
|
+
date: 2015-03-12 00:00:00.000000000 Z
|
13
12
|
dependencies:
|
14
13
|
- !ruby/object:Gem::Dependency
|
15
14
|
name: rake
|
16
15
|
requirement: !ruby/object:Gem::Requirement
|
17
|
-
none: false
|
18
16
|
requirements:
|
19
|
-
- -
|
17
|
+
- - ">="
|
20
18
|
- !ruby/object:Gem::Version
|
21
19
|
version: '0'
|
22
20
|
type: :development
|
23
21
|
prerelease: false
|
24
22
|
version_requirements: !ruby/object:Gem::Requirement
|
25
|
-
none: false
|
26
23
|
requirements:
|
27
|
-
- -
|
24
|
+
- - ">="
|
28
25
|
- !ruby/object:Gem::Version
|
29
26
|
version: '0'
|
30
27
|
- !ruby/object:Gem::Dependency
|
31
28
|
name: rspec
|
32
29
|
requirement: !ruby/object:Gem::Requirement
|
33
|
-
none: false
|
34
30
|
requirements:
|
35
|
-
- - ~>
|
31
|
+
- - "~>"
|
36
32
|
- !ruby/object:Gem::Version
|
37
33
|
version: 3.0.0
|
38
34
|
type: :development
|
39
35
|
prerelease: false
|
40
36
|
version_requirements: !ruby/object:Gem::Requirement
|
41
|
-
none: false
|
42
37
|
requirements:
|
43
|
-
- - ~>
|
38
|
+
- - "~>"
|
44
39
|
- !ruby/object:Gem::Version
|
45
40
|
version: 3.0.0
|
46
41
|
- !ruby/object:Gem::Dependency
|
47
42
|
name: webmock
|
48
43
|
requirement: !ruby/object:Gem::Requirement
|
49
|
-
none: false
|
50
44
|
requirements:
|
51
|
-
- - ~>
|
45
|
+
- - "~>"
|
52
46
|
- !ruby/object:Gem::Version
|
53
47
|
version: 1.18.0
|
54
48
|
type: :development
|
55
49
|
prerelease: false
|
56
50
|
version_requirements: !ruby/object:Gem::Requirement
|
57
|
-
none: false
|
58
51
|
requirements:
|
59
|
-
- - ~>
|
52
|
+
- - "~>"
|
60
53
|
- !ruby/object:Gem::Version
|
61
54
|
version: 1.18.0
|
62
55
|
description: The official Mixpanel tracking library for ruby
|
@@ -65,9 +58,9 @@ executables: []
|
|
65
58
|
extensions: []
|
66
59
|
extra_rdoc_files: []
|
67
60
|
files:
|
68
|
-
- .gitignore
|
69
|
-
- .rspec
|
70
|
-
- .travis.yml
|
61
|
+
- ".gitignore"
|
62
|
+
- ".rspec"
|
63
|
+
- ".travis.yml"
|
71
64
|
- Gemfile
|
72
65
|
- LICENSE
|
73
66
|
- Rakefile
|
@@ -90,26 +83,25 @@ files:
|
|
90
83
|
homepage: https://mixpanel.com/help/reference/ruby
|
91
84
|
licenses:
|
92
85
|
- Apache License 2.0
|
86
|
+
metadata: {}
|
93
87
|
post_install_message:
|
94
88
|
rdoc_options: []
|
95
89
|
require_paths:
|
96
90
|
- lib
|
97
91
|
required_ruby_version: !ruby/object:Gem::Requirement
|
98
|
-
none: false
|
99
92
|
requirements:
|
100
|
-
- -
|
93
|
+
- - ">="
|
101
94
|
- !ruby/object:Gem::Version
|
102
|
-
version:
|
95
|
+
version: 2.0.0
|
103
96
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
104
|
-
none: false
|
105
97
|
requirements:
|
106
|
-
- -
|
98
|
+
- - ">="
|
107
99
|
- !ruby/object:Gem::Version
|
108
100
|
version: '0'
|
109
101
|
requirements: []
|
110
102
|
rubyforge_project:
|
111
|
-
rubygems_version:
|
103
|
+
rubygems_version: 2.2.0
|
112
104
|
signing_key:
|
113
|
-
specification_version:
|
105
|
+
specification_version: 4
|
114
106
|
summary: Official Mixpanel tracking library for ruby
|
115
107
|
test_files: []
|