satellite 0.0.0 → 0.1.0
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/Gemfile +0 -3
- data/Gemfile.lock +20 -0
- data/VERSION +1 -1
- data/lib/satellite/adapters/google_analytics.rb +281 -0
- data/lib/satellite/controllers/google_analytics.rb +38 -0
- data/lib/satellite.rb +45 -57
- data/lib/support/object.rb +34 -0
- data/lib/support/string.rb +65 -0
- data/satellite.gemspec +63 -0
- data/test/helper.rb +3 -0
- data/test/test_satellite.rb +53 -2
- metadata +10 -4
data/Gemfile
CHANGED
data/Gemfile.lock
ADDED
@@ -0,0 +1,20 @@
|
|
1
|
+
GEM
|
2
|
+
remote: http://rubygems.org/
|
3
|
+
specs:
|
4
|
+
git (1.2.5)
|
5
|
+
jeweler (1.6.4)
|
6
|
+
bundler (~> 1.0)
|
7
|
+
git (>= 1.2.5)
|
8
|
+
rake
|
9
|
+
rake (0.9.2)
|
10
|
+
rcov (0.9.10)
|
11
|
+
shoulda (2.11.3)
|
12
|
+
|
13
|
+
PLATFORMS
|
14
|
+
ruby
|
15
|
+
|
16
|
+
DEPENDENCIES
|
17
|
+
bundler (~> 1.0.0)
|
18
|
+
jeweler (~> 1.6.4)
|
19
|
+
rcov
|
20
|
+
shoulda
|
data/VERSION
CHANGED
@@ -1 +1 @@
|
|
1
|
-
0.
|
1
|
+
0.1.0
|
@@ -0,0 +1,281 @@
|
|
1
|
+
module Satellite
|
2
|
+
module Adapters
|
3
|
+
class GoogleAnalytics
|
4
|
+
|
5
|
+
def initialize(params, use_ssl=false)
|
6
|
+
self.utm_params = extend_with_default_params(params)
|
7
|
+
self.utm_location = (use_ssl ? 'https://ssl' : 'http://www') + UTM_GIF_LOCATION
|
8
|
+
end
|
9
|
+
|
10
|
+
def track
|
11
|
+
#puts utm_params.inspect
|
12
|
+
|
13
|
+
utm_url = tracking_url
|
14
|
+
|
15
|
+
puts "--------sending request to GA-----------------------"
|
16
|
+
puts utm_url
|
17
|
+
|
18
|
+
open(utm_url, { "User-Agent" => 'Satellite/0.0.0', "Accept-Language" => 'de' })
|
19
|
+
|
20
|
+
# reset events / custom variables here
|
21
|
+
utm_params.delete(:utme)
|
22
|
+
true
|
23
|
+
end
|
24
|
+
|
25
|
+
def tracking_url
|
26
|
+
utm_location + "?" + utm_params.to_query
|
27
|
+
end
|
28
|
+
|
29
|
+
def track_event(category, action, label=nil, value=nil)
|
30
|
+
utm_params[:utme].set_event(category, action, label, value)
|
31
|
+
track
|
32
|
+
end
|
33
|
+
|
34
|
+
def track_page_view(path=nil)
|
35
|
+
utm_params.merge({ :utmp => path }) if path
|
36
|
+
track
|
37
|
+
end
|
38
|
+
|
39
|
+
def set_custom_variable(index, name, value, scope=nil)
|
40
|
+
utm_params[:utme].set_custom_variable(index, name, value, scope)
|
41
|
+
end
|
42
|
+
|
43
|
+
def unset_custom_variable(index)
|
44
|
+
utm_params[:utme].unset_custom_variable(index)
|
45
|
+
end
|
46
|
+
|
47
|
+
def []=(key, value)
|
48
|
+
value = Utme.parse(value) if key.to_s == 'utme'
|
49
|
+
utm_params[key] = value
|
50
|
+
end
|
51
|
+
|
52
|
+
def [](key)
|
53
|
+
utm_params[key]
|
54
|
+
end
|
55
|
+
|
56
|
+
class << self
|
57
|
+
attr_accessor :account_id
|
58
|
+
end
|
59
|
+
|
60
|
+
protected
|
61
|
+
|
62
|
+
attr_accessor :utm_params, :utm_location
|
63
|
+
|
64
|
+
private
|
65
|
+
|
66
|
+
# seems to be the current version
|
67
|
+
# search for 'utmwv' in http://www.google-analytics.com/ga.js
|
68
|
+
VERSION = "4.4sh" #"5.1.5"
|
69
|
+
UTM_GIF_LOCATION = ".google-analytics.com/__utm.gif"
|
70
|
+
|
71
|
+
# adds default params
|
72
|
+
def extend_with_default_params(params)
|
73
|
+
utme = params.delete(:utme)
|
74
|
+
{
|
75
|
+
:utmac => self.class.account_id,
|
76
|
+
:utmcc => '__utma%3D999.999.999.999.999.1%3B', # stub for non-existent cookie,
|
77
|
+
:utmcs => 'UTF-8',
|
78
|
+
:utme => Utme.parse(utme),
|
79
|
+
:utmhid => rand(0x7fffffff).to_s,
|
80
|
+
:utmn => rand(0x7fffffff).to_s,
|
81
|
+
:utmvid => rand(0x7fffffff).to_s,
|
82
|
+
:utmwv => VERSION,
|
83
|
+
# should get configured when initializing
|
84
|
+
#:utmhn => 'google-analytics.satellite.local',
|
85
|
+
#:utmr => 'https://rubygems.org/gems/satellite',
|
86
|
+
#:utmp => '/google-analytics',
|
87
|
+
#:utmip => '127.0.0.1',
|
88
|
+
}.merge(params)
|
89
|
+
end
|
90
|
+
|
91
|
+
end
|
92
|
+
end
|
93
|
+
end
|
94
|
+
|
95
|
+
module Satellite
|
96
|
+
module Adapters
|
97
|
+
class GoogleAnalytics::Utme
|
98
|
+
|
99
|
+
def initialize
|
100
|
+
@custom_variables = CustomVariables.new
|
101
|
+
end
|
102
|
+
|
103
|
+
def set_event(category, action, label=nil, value=nil)
|
104
|
+
@event = Event.new(category, action, label, value)
|
105
|
+
self
|
106
|
+
end
|
107
|
+
|
108
|
+
def set_custom_variable(slot, name, value, scope=nil)
|
109
|
+
@custom_variables.set_custom_variable(slot, CustomVariable.new(name, value, scope))
|
110
|
+
self
|
111
|
+
end
|
112
|
+
|
113
|
+
def unset_custom_variable(slot)
|
114
|
+
@custom_variables.unset_custom_variable(slot)
|
115
|
+
self
|
116
|
+
end
|
117
|
+
|
118
|
+
def to_s
|
119
|
+
@event.to_s + @custom_variables.to_s
|
120
|
+
end
|
121
|
+
|
122
|
+
alias_method :to_param, :to_s
|
123
|
+
|
124
|
+
class << self
|
125
|
+
|
126
|
+
@@regex_event = /5\((\w+)\*(\w+)(\*(\w+))?\)(\((\d+)\))?/
|
127
|
+
@@regex_custom_variables = /8\(([^\)]*)\)9\(([^\)]*)\)(11\(([^\)]*)\))?/
|
128
|
+
@@regex_custom_variable_value = /((\d)!)?(\w+)/
|
129
|
+
|
130
|
+
def parse(args)
|
131
|
+
return self.new if args.nil?
|
132
|
+
case args
|
133
|
+
when String
|
134
|
+
return self.from_string(args)
|
135
|
+
when self
|
136
|
+
return args
|
137
|
+
else
|
138
|
+
raise ArgumentError, "Could parse argument neither as String nor GATracker::Utme"
|
139
|
+
end
|
140
|
+
end
|
141
|
+
|
142
|
+
def from_string(str)
|
143
|
+
utme = self.new
|
144
|
+
|
145
|
+
# parse event
|
146
|
+
str.gsub!(@@regex_event) do |match|
|
147
|
+
utme.set_event($1, $2, $4, $6)
|
148
|
+
''
|
149
|
+
end
|
150
|
+
|
151
|
+
# parse custom variables
|
152
|
+
str.gsub!(@@regex_custom_variables) do |match|
|
153
|
+
custom_vars = { }
|
154
|
+
match_names, match_values, match_scopes = $1, $2, $4
|
155
|
+
|
156
|
+
names = match_names.to_s.split('*')
|
157
|
+
values = match_values.to_s.split('*')
|
158
|
+
scopes = match_scopes.to_s.split('*')
|
159
|
+
|
160
|
+
raise ArgumentError, "Each custom variable must have a value defined." if names.length != values.length
|
161
|
+
|
162
|
+
names.each_with_index do |raw_name, i|
|
163
|
+
match_data = raw_name.match(@@regex_custom_variable_value)
|
164
|
+
slot, name = (match_data[2] || i+1).to_i, match_data[3]
|
165
|
+
custom_vars[slot] = { :name => name }
|
166
|
+
end
|
167
|
+
|
168
|
+
values.each_with_index do |raw_value, i|
|
169
|
+
match_data = raw_value.match(@@regex_custom_variable_value)
|
170
|
+
slot, value = (match_data[2] || i+1).to_i, match_data[3]
|
171
|
+
custom_vars[slot][:value] = value
|
172
|
+
end
|
173
|
+
|
174
|
+
scopes.each_with_index do |raw_scope, i|
|
175
|
+
match_data = raw_scope.match(@@regex_custom_variable_value)
|
176
|
+
slot, scope = (match_data[2] || i+1).to_i, match_data[3]
|
177
|
+
# silently ignore scope if there's no corresponding custom variable
|
178
|
+
custom_vars[slot][:scope] = scope if custom_vars[slot]
|
179
|
+
end
|
180
|
+
|
181
|
+
# finally set all the gathered custom vars
|
182
|
+
custom_vars.each do |key, custom_var|
|
183
|
+
utme.set_custom_variable(key, custom_var[:name], custom_var[:value], custom_var[:scope])
|
184
|
+
end
|
185
|
+
''
|
186
|
+
end
|
187
|
+
|
188
|
+
utme
|
189
|
+
end
|
190
|
+
end
|
191
|
+
|
192
|
+
private
|
193
|
+
|
194
|
+
Event = Struct.new(:category, :action, :opt_label, :opt_value) do
|
195
|
+
def to_s
|
196
|
+
output = "5(#{category}*#{action}"
|
197
|
+
output += "*#{opt_label}" if opt_label
|
198
|
+
output += ")"
|
199
|
+
output += "(#{opt_value})" if opt_value
|
200
|
+
output
|
201
|
+
end
|
202
|
+
end
|
203
|
+
|
204
|
+
CustomVariable = Struct.new(:name, :value, :opt_scope)
|
205
|
+
|
206
|
+
class CustomVariables
|
207
|
+
|
208
|
+
@@valid_keys = 1..5
|
209
|
+
|
210
|
+
def initialize
|
211
|
+
@contents = { }
|
212
|
+
end
|
213
|
+
|
214
|
+
def set_custom_variable(slot, custom_variable)
|
215
|
+
raise ArgumentError, "Cannot set a slot other than #{@@valid_keys}. Given #{slot}" if not @@valid_keys.include?(slot)
|
216
|
+
@contents[slot] = custom_variable
|
217
|
+
end
|
218
|
+
|
219
|
+
def unset_custom_variable(slot)
|
220
|
+
raise ArgumentError, "Cannot unset a slot other than #{@@valid_keys}. Given #{slot}" if not @@valid_keys.include?(slot)
|
221
|
+
@contents.delete(slot)
|
222
|
+
end
|
223
|
+
|
224
|
+
# follows google custom variable format
|
225
|
+
#
|
226
|
+
# 8(NAMES)9(VALUES)11(SCOPES)
|
227
|
+
#
|
228
|
+
# best explained by examples
|
229
|
+
#
|
230
|
+
# 1)
|
231
|
+
# pageTracker._setCustomVar(1,"foo", "val", 1)
|
232
|
+
# ==> 8(foo)9(bar)11(1)
|
233
|
+
#
|
234
|
+
# 2)
|
235
|
+
# pageTracker._setCustomVar(1,"foo", "val", 1)
|
236
|
+
# pageTracker._setCustomVar(2,"bar", "vok", 3)
|
237
|
+
# ==> 8(foo*bar)9(val*vok)11(1*3)
|
238
|
+
#
|
239
|
+
# 3)
|
240
|
+
# pageTracker._setCustomVar(1,"foo", "val", 1)
|
241
|
+
# pageTracker._setCustomVar(2,"bar", "vok", 3)
|
242
|
+
# pageTracker._setCustomVar(4,"baz", "vol", 1)
|
243
|
+
# ==> 8(foo*bar*4!baz)9(val*vak*4!vol)11(1*3*4!1)
|
244
|
+
#
|
245
|
+
# 4)
|
246
|
+
# pageTracker._setCustomVar(4,"foo", "bar", 1)
|
247
|
+
# ==> 8(4!foo)9(4!bar)11(4!1)
|
248
|
+
#
|
249
|
+
def to_s
|
250
|
+
return '' if @contents.empty?
|
251
|
+
|
252
|
+
ordered_keys = @contents.keys.sort
|
253
|
+
names = values = scopes = ''
|
254
|
+
|
255
|
+
ordered_keys.each do |slot|
|
256
|
+
custom_variable = @contents[slot]
|
257
|
+
predecessor = @contents[slot-1]
|
258
|
+
|
259
|
+
has_predecessor = !!predecessor
|
260
|
+
has_scoped_predecessor = !!(predecessor.try(:opt_scope))
|
261
|
+
|
262
|
+
star = names.empty? ? '' : '*'
|
263
|
+
bang = (slot == 1 || has_predecessor) ? '' : "#{slot}!"
|
264
|
+
|
265
|
+
scope_star = scopes.empty? ? '' : '*'
|
266
|
+
scope_bang = (slot == 1 || has_scoped_predecessor) ? '' : "#{slot}!"
|
267
|
+
|
268
|
+
names += "#{star}#{bang}#{custom_variable.name}"
|
269
|
+
values += "#{star}#{bang}#{custom_variable.value}"
|
270
|
+
scopes += "#{scope_star}#{scope_bang}#{custom_variable.opt_scope}" if custom_variable.opt_scope
|
271
|
+
end
|
272
|
+
|
273
|
+
output = "8(#{names})9(#{values})"
|
274
|
+
output += "11(#{scopes})" if not scopes.empty?
|
275
|
+
output
|
276
|
+
end
|
277
|
+
|
278
|
+
end
|
279
|
+
end
|
280
|
+
end
|
281
|
+
end
|
@@ -0,0 +1,38 @@
|
|
1
|
+
module Satellite
|
2
|
+
module Controllers
|
3
|
+
class GoogleAnalyticsController
|
4
|
+
|
5
|
+
def tracker
|
6
|
+
@tracker ||= Satellite.get_tracker(:google_analytics, ga_params)
|
7
|
+
end
|
8
|
+
|
9
|
+
protected
|
10
|
+
|
11
|
+
def ga_visitor_id
|
12
|
+
"#{request.env["HTTP_USER_AGENT"]}#{rand(0x7fffffff).to_s}"
|
13
|
+
end
|
14
|
+
|
15
|
+
def ga_params
|
16
|
+
# domain specific stuff
|
17
|
+
domain_name = (request.env["SERVER_NAME"].nil? || request.env["SERVER_NAME"].blank?) ? "" : request.env["SERVER_NAME"]
|
18
|
+
referral = request.env['HTTP_REFERER'] || ''
|
19
|
+
path = request.env["REQUEST_URI"] || ''
|
20
|
+
|
21
|
+
# Capture the first three octects of the IP address and replace the forth
|
22
|
+
# with 0, e.g. 124.455.3.123 becomes 124.455.3.0
|
23
|
+
remote_address = request.env["REMOTE_ADDR"].to_s
|
24
|
+
ip = (remote_address.nil? || remote_address.blank?) ? '' : remote_address.gsub!(/([^.]+\.[^.]+\.[^.]+\.)[^.]+/, "\\1") + "0"
|
25
|
+
|
26
|
+
visitor_uuid = Digest::MD5.hexdigest(ga_visitor_id)
|
27
|
+
|
28
|
+
{
|
29
|
+
:utmhn => domain_name,
|
30
|
+
:utmr => referral,
|
31
|
+
:utmp => path,
|
32
|
+
:utmip => ip,
|
33
|
+
:utmvid => visitor_uuid
|
34
|
+
}
|
35
|
+
end
|
36
|
+
end
|
37
|
+
end
|
38
|
+
end
|
data/lib/satellite.rb
CHANGED
@@ -1,76 +1,64 @@
|
|
1
1
|
require 'open-uri'
|
2
2
|
|
3
|
-
|
4
|
-
|
5
|
-
|
6
|
-
|
7
|
-
self.utm_location = (use_ssl ? 'https://ssl' : 'http://www') + UTM_GIF_LOCATION
|
8
|
-
end
|
9
|
-
|
10
|
-
def track
|
3
|
+
# stub some ActiveSupport functionality
|
4
|
+
unless Object.const_defined?("ActiveSupport")
|
5
|
+
Dir.glob(File.dirname(__FILE__) + '/support/*') { |file| require file }
|
6
|
+
end
|
11
7
|
|
12
|
-
|
8
|
+
# load tracking adapters
|
9
|
+
Dir.glob(File.dirname(__FILE__) + '/satellite/adapters/*') { |file| require file }
|
13
10
|
|
14
|
-
|
15
|
-
puts utm_url
|
16
|
-
open(utm_url)
|
11
|
+
module Satellite
|
17
12
|
|
18
|
-
|
19
|
-
utm_params.delete(:utme)
|
13
|
+
class NoAdapterError < NameError
|
20
14
|
end
|
21
15
|
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
16
|
+
class TrackerInterface
|
17
|
+
def initialize(adapter)
|
18
|
+
@adapter = adapter
|
19
|
+
end
|
26
20
|
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
end
|
21
|
+
def track_page_view(path=nil)
|
22
|
+
@adapter.track_page_view(path)
|
23
|
+
end
|
31
24
|
|
32
|
-
|
33
|
-
|
34
|
-
|
25
|
+
def track_event(category, action, label=nil, value=nil)
|
26
|
+
@adapter.track_event(category, action, label, value)
|
27
|
+
end
|
35
28
|
|
36
|
-
|
37
|
-
|
38
|
-
|
29
|
+
def set_custom_variable(slot, name, value, scope=nil)
|
30
|
+
@adapter.set_custom_variable(slot, name, value, scope)
|
31
|
+
end
|
39
32
|
|
40
|
-
|
41
|
-
|
42
|
-
|
43
|
-
end
|
44
|
-
|
45
|
-
def [](key)
|
46
|
-
utm_params[key]
|
47
|
-
end
|
33
|
+
def unset_custom_variable(slot)
|
34
|
+
@adapter.unset_custom_variable(slot)
|
35
|
+
end
|
48
36
|
|
49
|
-
|
50
|
-
|
51
|
-
|
37
|
+
def tracking_url
|
38
|
+
@adapter.tracking_url
|
39
|
+
end
|
52
40
|
|
53
|
-
|
41
|
+
def type
|
42
|
+
@adapter.class
|
43
|
+
end
|
54
44
|
|
55
|
-
|
45
|
+
def []=(key, value)
|
46
|
+
@adapter[key] = value
|
47
|
+
end
|
56
48
|
|
57
|
-
|
49
|
+
def [](key)
|
50
|
+
@adapter[key]
|
51
|
+
end
|
52
|
+
end
|
58
53
|
|
59
|
-
|
60
|
-
|
61
|
-
|
62
|
-
|
54
|
+
def self.get_tracker(type, params = { })
|
55
|
+
begin
|
56
|
+
tracker_klass = "Satellite::Adapters::#{type.to_s.camelcase}".constantize
|
57
|
+
rescue
|
58
|
+
raise NoAdapterError, "There is no such adapter like 'Satellite::Adapters::#{type.to_s.camelcase}'"
|
59
|
+
end
|
63
60
|
|
64
|
-
|
65
|
-
def extend_with_default_params(params)
|
66
|
-
params.reverse_merge({
|
67
|
-
:utme => Utme.parse(params[:utme]),
|
68
|
-
:utmwv => VERSION,
|
69
|
-
:utmn => rand(0x7fffffff).to_s,
|
70
|
-
:utmac => GATracker.account_id
|
71
|
-
})
|
61
|
+
TrackerInterface.new(tracker_klass.new(params))
|
72
62
|
end
|
73
63
|
|
74
|
-
end
|
75
|
-
|
76
|
-
require 'satellite/utme'
|
64
|
+
end
|
@@ -0,0 +1,34 @@
|
|
1
|
+
unless Object.const_defined?("ActiveSupport")
|
2
|
+
class Object
|
3
|
+
def to_query(key)
|
4
|
+
require 'cgi' unless defined?(CGI) && defined?(CGI::escape)
|
5
|
+
|
6
|
+
puts self.inspect
|
7
|
+
puts to_param
|
8
|
+
|
9
|
+
"#{CGI.escape(key.to_s).gsub(/%(5B|5D)/n) { [$1].pack('H*') }}=#{CGI.escape(to_param.to_s)}"
|
10
|
+
end
|
11
|
+
|
12
|
+
def to_param
|
13
|
+
to_s
|
14
|
+
end
|
15
|
+
|
16
|
+
def try(method, *args, &block)
|
17
|
+
begin
|
18
|
+
send(method, *args, &block)
|
19
|
+
rescue
|
20
|
+
nil
|
21
|
+
end
|
22
|
+
end
|
23
|
+
end
|
24
|
+
|
25
|
+
class Hash
|
26
|
+
def to_param(namespace = nil)
|
27
|
+
collect do |key, value|
|
28
|
+
value.to_query(namespace ? "#{namespace}[#{key}]" : key)
|
29
|
+
end.sort * '&'
|
30
|
+
end
|
31
|
+
|
32
|
+
alias_method :to_query, :to_param
|
33
|
+
end
|
34
|
+
end
|
@@ -0,0 +1,65 @@
|
|
1
|
+
unless Object.const_defined?("ActiveSupport")
|
2
|
+
class String
|
3
|
+
def camelize(first_letter = :upper)
|
4
|
+
case first_letter
|
5
|
+
when :upper then
|
6
|
+
ActiveSupport::Inflector.camelize(self, true)
|
7
|
+
when :lower then
|
8
|
+
ActiveSupport::Inflector.camelize(self, false)
|
9
|
+
end
|
10
|
+
end
|
11
|
+
|
12
|
+
alias_method :camelcase, :camelize
|
13
|
+
|
14
|
+
def constantize
|
15
|
+
ActiveSupport::Inflector.constantize(self)
|
16
|
+
end
|
17
|
+
|
18
|
+
def underscore
|
19
|
+
ActiveSupport::Inflector.underscore(self)
|
20
|
+
end
|
21
|
+
|
22
|
+
def demodulize
|
23
|
+
ActiveSupport::Inflector.demodulize(self)
|
24
|
+
end
|
25
|
+
end
|
26
|
+
|
27
|
+
module ActiveSupport
|
28
|
+
module Inflector
|
29
|
+
extend self
|
30
|
+
|
31
|
+
def camelize(lower_case_and_underscored_word, first_letter_in_uppercase = true)
|
32
|
+
if first_letter_in_uppercase
|
33
|
+
lower_case_and_underscored_word.to_s.gsub(/\/(.?)/) { "::#{$1.upcase}" }.gsub(/(?:^|_)(.)/) { $1.upcase }
|
34
|
+
else
|
35
|
+
lower_case_and_underscored_word.to_s[0].chr.downcase + camelize(lower_case_and_underscored_word)[1..-1]
|
36
|
+
end
|
37
|
+
end
|
38
|
+
|
39
|
+
def underscore(camel_cased_word)
|
40
|
+
word = camel_cased_word.to_s.dup
|
41
|
+
word.gsub!(/::/, '/')
|
42
|
+
word.gsub!(/([A-Z]+)([A-Z][a-z])/, '\1_\2')
|
43
|
+
word.gsub!(/([a-z\d])([A-Z])/, '\1_\2')
|
44
|
+
word.tr!("-", "_")
|
45
|
+
word.downcase!
|
46
|
+
word
|
47
|
+
end
|
48
|
+
|
49
|
+
def demodulize(class_name_in_module)
|
50
|
+
class_name_in_module.to_s.gsub(/^.*::/, '')
|
51
|
+
end
|
52
|
+
|
53
|
+
def constantize(camel_cased_word)
|
54
|
+
names = camel_cased_word.split('::')
|
55
|
+
names.shift if names.empty? || names.first.empty?
|
56
|
+
|
57
|
+
constant = Object
|
58
|
+
names.each do |name|
|
59
|
+
constant = constant.const_defined?(name) ? constant.const_get(name) : constant.const_missing(name)
|
60
|
+
end
|
61
|
+
constant
|
62
|
+
end
|
63
|
+
end
|
64
|
+
end
|
65
|
+
end
|
data/satellite.gemspec
ADDED
@@ -0,0 +1,63 @@
|
|
1
|
+
# Generated by jeweler
|
2
|
+
# DO NOT EDIT THIS FILE DIRECTLY
|
3
|
+
# Instead, edit Jeweler::Tasks in Rakefile, and run 'rake gemspec'
|
4
|
+
# -*- encoding: utf-8 -*-
|
5
|
+
|
6
|
+
Gem::Specification.new do |s|
|
7
|
+
s.name = %q{satellite}
|
8
|
+
s.version = "0.1.0"
|
9
|
+
|
10
|
+
s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
|
11
|
+
s.authors = [%q{Maik Vlcek}]
|
12
|
+
s.date = %q{2011-08-25}
|
13
|
+
s.description = %q{Ruby on Rails server-side Analytics Tracker for Google and more}
|
14
|
+
s.email = %q{maik.vlcek@mymobai.de}
|
15
|
+
s.extra_rdoc_files = [
|
16
|
+
"LICENSE.txt",
|
17
|
+
"README.rdoc"
|
18
|
+
]
|
19
|
+
s.files = [
|
20
|
+
".document",
|
21
|
+
"Gemfile",
|
22
|
+
"Gemfile.lock",
|
23
|
+
"LICENSE.txt",
|
24
|
+
"README.rdoc",
|
25
|
+
"Rakefile",
|
26
|
+
"VERSION",
|
27
|
+
"lib/satellite.rb",
|
28
|
+
"lib/satellite/adapters/google_analytics.rb",
|
29
|
+
"lib/satellite/controllers/google_analytics.rb",
|
30
|
+
"lib/support/object.rb",
|
31
|
+
"lib/support/string.rb",
|
32
|
+
"satellite.gemspec",
|
33
|
+
"test/helper.rb",
|
34
|
+
"test/test_satellite.rb"
|
35
|
+
]
|
36
|
+
s.homepage = %q{http://github.com/mediavrog/satellite}
|
37
|
+
s.licenses = [%q{MIT}]
|
38
|
+
s.require_paths = [%q{lib}]
|
39
|
+
s.rubygems_version = %q{1.8.9}
|
40
|
+
s.summary = %q{Ruby on Rails server-side Analytics Tracker for Google and more}
|
41
|
+
|
42
|
+
if s.respond_to? :specification_version then
|
43
|
+
s.specification_version = 3
|
44
|
+
|
45
|
+
if Gem::Version.new(Gem::VERSION) >= Gem::Version.new('1.2.0') then
|
46
|
+
s.add_development_dependency(%q<shoulda>, [">= 0"])
|
47
|
+
s.add_development_dependency(%q<bundler>, ["~> 1.0.0"])
|
48
|
+
s.add_development_dependency(%q<jeweler>, ["~> 1.6.4"])
|
49
|
+
s.add_development_dependency(%q<rcov>, [">= 0"])
|
50
|
+
else
|
51
|
+
s.add_dependency(%q<shoulda>, [">= 0"])
|
52
|
+
s.add_dependency(%q<bundler>, ["~> 1.0.0"])
|
53
|
+
s.add_dependency(%q<jeweler>, ["~> 1.6.4"])
|
54
|
+
s.add_dependency(%q<rcov>, [">= 0"])
|
55
|
+
end
|
56
|
+
else
|
57
|
+
s.add_dependency(%q<shoulda>, [">= 0"])
|
58
|
+
s.add_dependency(%q<bundler>, ["~> 1.0.0"])
|
59
|
+
s.add_dependency(%q<jeweler>, ["~> 1.6.4"])
|
60
|
+
s.add_dependency(%q<rcov>, [">= 0"])
|
61
|
+
end
|
62
|
+
end
|
63
|
+
|
data/test/helper.rb
CHANGED
@@ -14,5 +14,8 @@ $LOAD_PATH.unshift(File.join(File.dirname(__FILE__), '..', 'lib'))
|
|
14
14
|
$LOAD_PATH.unshift(File.dirname(__FILE__))
|
15
15
|
require 'satellite'
|
16
16
|
|
17
|
+
# used for storing private data like google account_id
|
18
|
+
require 'local_conf' if File.exists?('local_conf.rb')
|
19
|
+
|
17
20
|
class Test::Unit::TestCase
|
18
21
|
end
|
data/test/test_satellite.rb
CHANGED
@@ -1,7 +1,58 @@
|
|
1
1
|
require 'helper'
|
2
2
|
|
3
3
|
class TestSatellite < Test::Unit::TestCase
|
4
|
-
|
5
|
-
|
4
|
+
|
5
|
+
should "create a proper google adapter" do
|
6
|
+
tracker = Satellite.get_tracker(:google_analytics)
|
7
|
+
assert_equal tracker.type, Satellite::Adapters::GoogleAnalytics
|
8
|
+
end
|
9
|
+
|
10
|
+
should "return any created tracker as tracker interface" do
|
11
|
+
tracker = Satellite.get_tracker(:google_analytics)
|
12
|
+
assert_equal tracker.class, Satellite::TrackerInterface
|
13
|
+
end
|
14
|
+
|
15
|
+
context 'google_adapter' do
|
16
|
+
|
17
|
+
#http://www.google-analytics.com/__utm.gif?
|
18
|
+
#utmwv
|
19
|
+
#utms
|
20
|
+
#utmn
|
21
|
+
#utmhn
|
22
|
+
#utme
|
23
|
+
#utmcs
|
24
|
+
#utmsr
|
25
|
+
#utmsc
|
26
|
+
#utmul
|
27
|
+
#utmje
|
28
|
+
#utmfl
|
29
|
+
#utmdt=
|
30
|
+
#utmhid
|
31
|
+
#utmr
|
32
|
+
#utmp
|
33
|
+
#utmac
|
34
|
+
#utmcc
|
35
|
+
#utmu
|
36
|
+
should "properly track a page view" do
|
37
|
+
tracker = Satellite.get_tracker(:google_analytics, {
|
38
|
+
:utms => 1,
|
39
|
+
#:utmn => 123456789, autogenerated
|
40
|
+
:utmhn => 'api.mymobai.com',
|
41
|
+
:utme => '5(controller*action*coupon_redeem)(10)8(test)9(Please_track_this)11(1)',
|
42
|
+
:utmcn => 1,
|
43
|
+
:utmcs => 'UTF-8',
|
44
|
+
:utmsr => '1440x900',
|
45
|
+
:utmul => 'de',
|
46
|
+
:utmje => '1',
|
47
|
+
:utmfl => '10.3%20r183',
|
48
|
+
:utmdt => 'Properly track a page view',
|
49
|
+
#:utmhid => '1655425535', auto
|
50
|
+
:utmr => 'test.local/properly track a page view',
|
51
|
+
:utmp => '/test/properly-track-page-view',
|
52
|
+
:utmac => GOOGLE_ACCOUNT_ID
|
53
|
+
})
|
54
|
+
|
55
|
+
assert_equal tracker.track_page_view, true
|
56
|
+
end
|
6
57
|
end
|
7
58
|
end
|
metadata
CHANGED
@@ -1,13 +1,13 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: satellite
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
hash:
|
4
|
+
hash: 27
|
5
5
|
prerelease:
|
6
6
|
segments:
|
7
7
|
- 0
|
8
|
+
- 1
|
8
9
|
- 0
|
9
|
-
|
10
|
-
version: 0.0.0
|
10
|
+
version: 0.1.0
|
11
11
|
platform: ruby
|
12
12
|
authors:
|
13
13
|
- Maik Vlcek
|
@@ -15,7 +15,7 @@ autorequire:
|
|
15
15
|
bindir: bin
|
16
16
|
cert_chain: []
|
17
17
|
|
18
|
-
date: 2011-08-
|
18
|
+
date: 2011-08-25 00:00:00 Z
|
19
19
|
dependencies:
|
20
20
|
- !ruby/object:Gem::Dependency
|
21
21
|
version_requirements: &id001 !ruby/object:Gem::Requirement
|
@@ -89,11 +89,17 @@ extra_rdoc_files:
|
|
89
89
|
files:
|
90
90
|
- .document
|
91
91
|
- Gemfile
|
92
|
+
- Gemfile.lock
|
92
93
|
- LICENSE.txt
|
93
94
|
- README.rdoc
|
94
95
|
- Rakefile
|
95
96
|
- VERSION
|
96
97
|
- lib/satellite.rb
|
98
|
+
- lib/satellite/adapters/google_analytics.rb
|
99
|
+
- lib/satellite/controllers/google_analytics.rb
|
100
|
+
- lib/support/object.rb
|
101
|
+
- lib/support/string.rb
|
102
|
+
- satellite.gemspec
|
97
103
|
- test/helper.rb
|
98
104
|
- test/test_satellite.rb
|
99
105
|
homepage: http://github.com/mediavrog/satellite
|