acts_as_referred 0.0.1
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.
- checksums.yaml +7 -0
- data/MIT-LICENSE +20 -0
- data/README.rdoc +89 -0
- data/Rakefile +30 -0
- data/lib/acts_as_referred.rb +21 -0
- data/lib/acts_as_referred/class_methods.rb +14 -0
- data/lib/acts_as_referred/controller.rb +87 -0
- data/lib/acts_as_referred/instance_methods.rb +20 -0
- data/lib/acts_as_referred/model.rb +146 -0
- data/lib/acts_as_referred/version.rb +3 -0
- data/lib/tasks/acts_as_referred_tasks.rake +20 -0
- data/test/acts_as_referred_test.rb +97 -0
- data/test/dummy/README.rdoc +28 -0
- data/test/dummy/Rakefile +6 -0
- data/test/dummy/app/assets/javascripts/application.js +13 -0
- data/test/dummy/app/assets/javascripts/bookings.js +2 -0
- data/test/dummy/app/assets/javascripts/orders.js +2 -0
- data/test/dummy/app/assets/javascripts/referees.js +2 -0
- data/test/dummy/app/assets/stylesheets/application.css +13 -0
- data/test/dummy/app/assets/stylesheets/bookings.css +4 -0
- data/test/dummy/app/assets/stylesheets/orders.css +4 -0
- data/test/dummy/app/assets/stylesheets/referees.css +4 -0
- data/test/dummy/app/assets/stylesheets/scaffold.css +56 -0
- data/test/dummy/app/controllers/application_controller.rb +8 -0
- data/test/dummy/app/controllers/bookings_controller.rb +58 -0
- data/test/dummy/app/controllers/orders_controller.rb +58 -0
- data/test/dummy/app/helpers/referees_helper.rb +2 -0
- data/test/dummy/app/models/booking.rb +3 -0
- data/test/dummy/app/models/order.rb +3 -0
- data/test/dummy/app/views/bookings/_form.html.erb +25 -0
- data/test/dummy/app/views/bookings/edit.html.erb +6 -0
- data/test/dummy/app/views/bookings/index.html.erb +29 -0
- data/test/dummy/app/views/bookings/new.html.erb +5 -0
- data/test/dummy/app/views/bookings/show.html.erb +18 -0
- data/test/dummy/app/views/layouts/application.html.erb +14 -0
- data/test/dummy/app/views/orders/_form.html.erb +25 -0
- data/test/dummy/app/views/orders/edit.html.erb +6 -0
- data/test/dummy/app/views/orders/index.html.erb +29 -0
- data/test/dummy/app/views/orders/new.html.erb +5 -0
- data/test/dummy/app/views/orders/show.html.erb +14 -0
- data/test/dummy/bin/bundle +3 -0
- data/test/dummy/bin/rails +4 -0
- data/test/dummy/bin/rake +4 -0
- data/test/dummy/config.ru +4 -0
- data/test/dummy/config/application.rb +23 -0
- data/test/dummy/config/boot.rb +5 -0
- data/test/dummy/config/database.yml +25 -0
- data/test/dummy/config/environment.rb +5 -0
- data/test/dummy/config/environments/development.rb +29 -0
- data/test/dummy/config/environments/production.rb +80 -0
- data/test/dummy/config/environments/test.rb +36 -0
- data/test/dummy/config/initializers/backtrace_silencers.rb +7 -0
- data/test/dummy/config/initializers/filter_parameter_logging.rb +4 -0
- data/test/dummy/config/initializers/inflections.rb +16 -0
- data/test/dummy/config/initializers/mime_types.rb +5 -0
- data/test/dummy/config/initializers/secret_token.rb +12 -0
- data/test/dummy/config/initializers/session_store.rb +3 -0
- data/test/dummy/config/initializers/wrap_parameters.rb +14 -0
- data/test/dummy/config/locales/en.yml +23 -0
- data/test/dummy/config/routes.rb +59 -0
- data/test/dummy/db/development.sqlite3 +0 -0
- data/test/dummy/db/migrate/20130926092411_create_bookings.rb +10 -0
- data/test/dummy/db/migrate/20131001152526_create_referee.rb +19 -0
- data/test/dummy/db/schema.rb +40 -0
- data/test/dummy/db/test.sqlite3 +0 -0
- data/test/dummy/lib/tasks/acts_as_referred_tasks.rake +20 -0
- data/test/dummy/log/development.log +2650 -0
- data/test/dummy/log/test.log +7254 -0
- data/test/dummy/public/404.html +58 -0
- data/test/dummy/public/422.html +58 -0
- data/test/dummy/public/500.html +57 -0
- data/test/dummy/public/favicon.ico +0 -0
- data/test/dummy/tmp/cache/assets/development/sprockets/00e0c908a950734c71f87d732990a88e +0 -0
- data/test/dummy/tmp/cache/assets/development/sprockets/0bd337b765d2a19a6d65ec976c83d97e +0 -0
- data/test/dummy/tmp/cache/assets/development/sprockets/12274417909f62d494c4179d6f8bcbe3 +0 -0
- data/test/dummy/tmp/cache/assets/development/sprockets/13fe41fee1fe35b49d145bcc06610705 +0 -0
- data/test/dummy/tmp/cache/assets/development/sprockets/2f5173deea6c795b8fdde723bb4b63af +0 -0
- data/test/dummy/tmp/cache/assets/development/sprockets/2fdee9aa34e89b0182a7523c4484e5f6 +0 -0
- data/test/dummy/tmp/cache/assets/development/sprockets/31da0321b4952412da9e1d9a1118e056 +0 -0
- data/test/dummy/tmp/cache/assets/development/sprockets/357970feca3ac29060c1e3861e2c0953 +0 -0
- data/test/dummy/tmp/cache/assets/development/sprockets/36a1fb9df9acb7490c5ac1284b2de56b +0 -0
- data/test/dummy/tmp/cache/assets/development/sprockets/371bf96e99717688ed7313a0c53f4212 +0 -0
- data/test/dummy/tmp/cache/assets/development/sprockets/510da110ae528e2d22533be39ff696c5 +0 -0
- data/test/dummy/tmp/cache/assets/development/sprockets/5c9d9893cd8a52cf99a46b89383cc603 +0 -0
- data/test/dummy/tmp/cache/assets/development/sprockets/6fc757c2c8329244ca95d6909865bbc2 +0 -0
- data/test/dummy/tmp/cache/assets/development/sprockets/7fa2dc3bb1d9661e45d7e10e8b2f9190 +0 -0
- data/test/dummy/tmp/cache/assets/development/sprockets/a3756bfb305f629747ba5349a5b02be0 +0 -0
- data/test/dummy/tmp/cache/assets/development/sprockets/b1e18c11e5c99b4c7871deabd029f38e +0 -0
- data/test/dummy/tmp/cache/assets/development/sprockets/b78b6f63e1fe791ab77083cd45eb5105 +0 -0
- data/test/dummy/tmp/cache/assets/development/sprockets/bb1f3aab6b0702db7f17992ade69175a +0 -0
- data/test/dummy/tmp/cache/assets/development/sprockets/cb9b952d9398fec90275bc0ef98f4b0c +0 -0
- data/test/dummy/tmp/cache/assets/development/sprockets/cffd775d018f68ce5dba1ee0d951a994 +0 -0
- data/test/dummy/tmp/cache/assets/development/sprockets/d1558f1aaf36f9640ae86479f11375df +0 -0
- data/test/dummy/tmp/cache/assets/development/sprockets/d771ace226fc8215a3572e0aa35bb0d6 +0 -0
- data/test/dummy/tmp/cache/assets/development/sprockets/e4468469b981ba614a29626880137332 +0 -0
- data/test/dummy/tmp/cache/assets/development/sprockets/e66cbc95d30d07acdf168b5c0de354d7 +0 -0
- data/test/dummy/tmp/cache/assets/development/sprockets/f464df872844f50aadec7fd7d56783af +0 -0
- data/test/dummy/tmp/cache/assets/development/sprockets/f7cbd26ba1d28d48de824f0e94586655 +0 -0
- data/test/dummy/tmp/cache/assets/development/sprockets/fd365928616248fd8efc56ed88d265ad +0 -0
- data/test/test_helper.rb +15 -0
- metadata +261 -0
checksums.yaml
ADDED
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
---
|
|
2
|
+
SHA1:
|
|
3
|
+
metadata.gz: 42d5ef44865bb5d0ba9ed490390891ef07c74a6d
|
|
4
|
+
data.tar.gz: 9745dd1b1913d9cb7a735c012149a532883063f3
|
|
5
|
+
SHA512:
|
|
6
|
+
metadata.gz: c93d99f61e5aed0cedc4e2706e2f9b7c70607fde113cdc7e08d63e593509cbf5634d11b2c9615667a9a7aabd3af9237b6642b141812117be884586627089fe32
|
|
7
|
+
data.tar.gz: f3d48468214d25ae3ff4fecf8641205daf72079c891746c30f25e2e95346779083e75c676d3a26a0f60df65021dc006861e3d39d31b6a3f280e36242ca9b84ed
|
data/MIT-LICENSE
ADDED
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
Copyright 2013 rene paulokat
|
|
2
|
+
|
|
3
|
+
Permission is hereby granted, free of charge, to any person obtaining
|
|
4
|
+
a copy of this software and associated documentation files (the
|
|
5
|
+
"Software"), to deal in the Software without restriction, including
|
|
6
|
+
without limitation the rights to use, copy, modify, merge, publish,
|
|
7
|
+
distribute, sublicense, and/or sell copies of the Software, and to
|
|
8
|
+
permit persons to whom the Software is furnished to do so, subject to
|
|
9
|
+
the following conditions:
|
|
10
|
+
|
|
11
|
+
The above copyright notice and this permission notice shall be
|
|
12
|
+
included in all copies or substantial portions of the Software.
|
|
13
|
+
|
|
14
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
|
15
|
+
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
|
16
|
+
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
|
17
|
+
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
|
|
18
|
+
LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
|
|
19
|
+
OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
|
20
|
+
WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
data/README.rdoc
ADDED
|
@@ -0,0 +1,89 @@
|
|
|
1
|
+
= ActsAsReferred
|
|
2
|
+
|
|
3
|
+
A gentle gem which offers the possibility to track referrer and campaigning.
|
|
4
|
+
After an ActiveRecord-instance that includes +acts_as_referred+ gets persistet to your database a relational +Referee+ is persistet as well.
|
|
5
|
+
|
|
6
|
+
A +before_action+ included to ApplicationController scans the incoming request for specific data supplied in the request-url.
|
|
7
|
+
|
|
8
|
+
This information is stored in a cookie and in the session as well. The created cookie is valid for 1 month.
|
|
9
|
+
|
|
10
|
+
The action then makes this data available to your model. When supplied with +acts_as_referred+ your pimped model will make use of a +after_create+ action to create a relational +Referee+ after it was created.
|
|
11
|
+
|
|
12
|
+
|
|
13
|
+
== Status
|
|
14
|
+
|
|
15
|
+
not yet production ready
|
|
16
|
+
|
|
17
|
+
== Install
|
|
18
|
+
|
|
19
|
+
at this stage only by github:
|
|
20
|
+
so add to your Gemfile
|
|
21
|
+
|
|
22
|
+
gem 'acts_as_referred', :git => 'git://github.com/erpe/acts_as_referred.git'
|
|
23
|
+
|
|
24
|
+
afterwards run the rake task to create necessary database table
|
|
25
|
+
|
|
26
|
+
rake acts_as_referred:create_table
|
|
27
|
+
|
|
28
|
+
add +acts_as_referred+ to your model e.g.
|
|
29
|
+
|
|
30
|
+
class Order < ActiveRecord::Base
|
|
31
|
+
acts_as_referred
|
|
32
|
+
end
|
|
33
|
+
|
|
34
|
+
and the final step - adopt your ApplicationController with:
|
|
35
|
+
|
|
36
|
+
class ApplicationController < ActionController::Base
|
|
37
|
+
include ActsAsReferred::Controller
|
|
38
|
+
end
|
|
39
|
+
|
|
40
|
+
|
|
41
|
+
+acts_as_referred+ supports manual tagged campaigns
|
|
42
|
+
|
|
43
|
+
If you use google-adwords you have to define manual-url-tagging instead of googles default auto-tagging
|
|
44
|
+
|
|
45
|
+
Auto-tagging (gclid) is recognized as campaign but can not be resolved.
|
|
46
|
+
(could be by parsing e.g. google-analytics cookies - but i think its kind of bad practice to relay on googles cookie-syntax)
|
|
47
|
+
|
|
48
|
+
|
|
49
|
+
== Usage
|
|
50
|
+
|
|
51
|
+
A example Order-model which includes +acts_as_referred+ has a relation to *Referee* on creation
|
|
52
|
+
you can query referees after relational order was created:
|
|
53
|
+
|
|
54
|
+
|
|
55
|
+
[order.referee.is_campaign]
|
|
56
|
+
returns true if request supplied campaign-arguments
|
|
57
|
+
|
|
58
|
+
[order.referee.campaign]
|
|
59
|
+
returns campaign name if supplied by tagging
|
|
60
|
+
|
|
61
|
+
[order.referee.keywords]
|
|
62
|
+
returns supplied keywords in the request.
|
|
63
|
+
|
|
64
|
+
[order.referee.host]
|
|
65
|
+
returns referrer-hostname
|
|
66
|
+
|
|
67
|
+
[order.referee.path]
|
|
68
|
+
returns path part of request
|
|
69
|
+
|
|
70
|
+
[Referee.campaigns]
|
|
71
|
+
returns collection of referee-instances connected to a campaign
|
|
72
|
+
|
|
73
|
+
|
|
74
|
+
== Background
|
|
75
|
+
|
|
76
|
+
whenever a request travels through ApplicationController and initializes a session the delivered referrer is persisted in the session.
|
|
77
|
+
As soon as an ActiveRecord which includes +acts_as_referred+ gets created the stored referrer will be used to build a new *Referee*
|
|
78
|
+
|
|
79
|
+
[A typical request coming in from adwords (non-auto-tagging!) looks like]
|
|
80
|
+
|
|
81
|
+
http://example.com/terror-in-baskets?utm_campaign=NSA&utm_term=PRISM&utm_medium=intercepted&utm_source=fbook
|
|
82
|
+
|
|
83
|
+
[If you prefer - what i'd apreciate - Piwik as privacy-aware tracking]
|
|
84
|
+
|
|
85
|
+
http://example.com/terror-in-baskets?pk_campaign=NSA&pk_kwd=PRISM
|
|
86
|
+
|
|
87
|
+
+ActsAsReferred+ stores the supplied campaign and keywords with in a +Referee+
|
|
88
|
+
|
|
89
|
+
|
data/Rakefile
ADDED
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
begin
|
|
2
|
+
require 'bundler/setup'
|
|
3
|
+
rescue LoadError
|
|
4
|
+
puts 'You must `gem install bundler` and `bundle install` to run rake tasks'
|
|
5
|
+
end
|
|
6
|
+
|
|
7
|
+
require 'rdoc/task'
|
|
8
|
+
|
|
9
|
+
Dir.glob('lib/tasks/*.rake').each {|r| import r}
|
|
10
|
+
|
|
11
|
+
RDoc::Task.new(:rdoc) do |rdoc|
|
|
12
|
+
rdoc.rdoc_dir = 'rdoc'
|
|
13
|
+
rdoc.title = 'ActsAsReferred'
|
|
14
|
+
rdoc.options << '--line-numbers'
|
|
15
|
+
rdoc.rdoc_files.include('README.rdoc')
|
|
16
|
+
rdoc.rdoc_files.include('lib/**/*.rb')
|
|
17
|
+
end
|
|
18
|
+
|
|
19
|
+
Bundler::GemHelper.install_tasks
|
|
20
|
+
|
|
21
|
+
require 'rake/testtask'
|
|
22
|
+
|
|
23
|
+
Rake::TestTask.new(:test) do |t|
|
|
24
|
+
t.libs << 'lib'
|
|
25
|
+
t.libs << 'test'
|
|
26
|
+
t.pattern = 'test/**/*_test.rb'
|
|
27
|
+
t.verbose = false
|
|
28
|
+
end
|
|
29
|
+
|
|
30
|
+
task default: :test
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
require 'acts_as_referred/instance_methods'
|
|
2
|
+
require 'acts_as_referred/model'
|
|
3
|
+
require 'acts_as_referred/class_methods'
|
|
4
|
+
require 'acts_as_referred/controller'
|
|
5
|
+
|
|
6
|
+
module ActsAsReferred
|
|
7
|
+
extend ActiveSupport::Concern
|
|
8
|
+
|
|
9
|
+
included do
|
|
10
|
+
end
|
|
11
|
+
|
|
12
|
+
# provide rake-tasks to create db-migration
|
|
13
|
+
class RakeTasks < Rails::Railtie
|
|
14
|
+
rake_tasks do
|
|
15
|
+
Dir[File.join(File.dirname(__FILE__),'tasks/*.rake')].each { |f| load f }
|
|
16
|
+
end
|
|
17
|
+
end
|
|
18
|
+
|
|
19
|
+
end
|
|
20
|
+
|
|
21
|
+
ActiveRecord::Base.send :include, ActsAsReferred
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
module ActsAsReferred
|
|
2
|
+
module ClassMethods
|
|
3
|
+
|
|
4
|
+
# Hook to serve behavior to ActiveRecord-Descendants
|
|
5
|
+
def acts_as_referred(options = {})
|
|
6
|
+
|
|
7
|
+
has_one :referee, as: :referable, dependent: :destroy, class_name: 'Referee'
|
|
8
|
+
after_create :create_referrer
|
|
9
|
+
|
|
10
|
+
include ActsAsReferred::InstanceMethods
|
|
11
|
+
end
|
|
12
|
+
|
|
13
|
+
end
|
|
14
|
+
end
|
|
@@ -0,0 +1,87 @@
|
|
|
1
|
+
module ActsAsReferred
|
|
2
|
+
|
|
3
|
+
# Namespce for controller-related functionality
|
|
4
|
+
module Controller
|
|
5
|
+
extend ActiveSupport::Concern
|
|
6
|
+
|
|
7
|
+
included do
|
|
8
|
+
before_filter :_check_cookie_and_session
|
|
9
|
+
before_filter :_supply_model_hook
|
|
10
|
+
end
|
|
11
|
+
|
|
12
|
+
protected
|
|
13
|
+
|
|
14
|
+
# The before_filter which processes necessary data for
|
|
15
|
+
# +acts_as_referred+ - models
|
|
16
|
+
def _supply_model_hook
|
|
17
|
+
|
|
18
|
+
# 3.2.1 -> adwords auto-tagging - (show hint to manual tag adwords):
|
|
19
|
+
# ?gclid=xxxx
|
|
20
|
+
# 3.2.2 -> manual tagging
|
|
21
|
+
# ?utm_source=google&utm_medium=cpc&utm_term=my_keyword&utm_campaign=my_summerdeal
|
|
22
|
+
# 3.2.3 -> manual url-tagging specific for piwik
|
|
23
|
+
# ?pk_campaign=my_summerdeal&pk_kwd=my_keyword
|
|
24
|
+
# cookie / session persisted:
|
|
25
|
+
# e.g.: "req=http://foo/baz?utm_campaign=plonk|ref=http://google.com/search|count=0"
|
|
26
|
+
|
|
27
|
+
tmp = session[:__reqref]
|
|
28
|
+
_struct = nil
|
|
29
|
+
if tmp
|
|
30
|
+
arr = tmp.split('|')
|
|
31
|
+
_struct = OpenStruct.new(
|
|
32
|
+
request_url: arr[0].split('=',2)[1],
|
|
33
|
+
referrer_url: minlength_or_nil(arr[1].split('=',2)[1]),
|
|
34
|
+
visit_count: arr[2].split('=',2)[1].to_i
|
|
35
|
+
)
|
|
36
|
+
end
|
|
37
|
+
|
|
38
|
+
ActiveRecord::Base.send(
|
|
39
|
+
:define_method,
|
|
40
|
+
'_get_reqref',
|
|
41
|
+
proc{ _struct }
|
|
42
|
+
)
|
|
43
|
+
end
|
|
44
|
+
|
|
45
|
+
|
|
46
|
+
private
|
|
47
|
+
|
|
48
|
+
# checks for existing +__reqref+ key in session
|
|
49
|
+
# if not found checks for signed cookie with key +__reqref+
|
|
50
|
+
# if this is the initial request to our site, we write a cookie with
|
|
51
|
+
# referrer and request.url
|
|
52
|
+
def _check_cookie_and_session
|
|
53
|
+
args = {}
|
|
54
|
+
if session[:__reqref]
|
|
55
|
+
tmp = session[:__reqref]
|
|
56
|
+
else
|
|
57
|
+
if cookies.signed[:__reqref]
|
|
58
|
+
tmp = cookies.signed[:__reqref]
|
|
59
|
+
tmp = _increment_returning_count(tmp)
|
|
60
|
+
_set_cookie(__reqref: tmp)
|
|
61
|
+
else
|
|
62
|
+
tmp = "req=#{request.url}|ref=#{request.referrer}|ret=0"
|
|
63
|
+
_set_cookie(__reqref: tmp)
|
|
64
|
+
end
|
|
65
|
+
session[:__reqref] = tmp
|
|
66
|
+
end
|
|
67
|
+
end
|
|
68
|
+
|
|
69
|
+
def _set_cookie(args={})
|
|
70
|
+
args.each_pair do |k,v|
|
|
71
|
+
cookies.signed[k] = { value: v, expires: 1.month.from_now }
|
|
72
|
+
end
|
|
73
|
+
end
|
|
74
|
+
|
|
75
|
+
def _increment_returning_count(tmp)
|
|
76
|
+
arr = tmp.split("|")
|
|
77
|
+
arr[-1] = "ret=#{arr[-1].split('=')[-1].to_i + 1}"
|
|
78
|
+
arr.join('|')
|
|
79
|
+
end
|
|
80
|
+
|
|
81
|
+
def minlength_or_nil(string)
|
|
82
|
+
URI.parse(string).host ? string : nil
|
|
83
|
+
end
|
|
84
|
+
|
|
85
|
+
end
|
|
86
|
+
|
|
87
|
+
end
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
module ActsAsReferred
|
|
2
|
+
module InstanceMethods
|
|
3
|
+
|
|
4
|
+
private
|
|
5
|
+
|
|
6
|
+
# after create hook to create a corresponding +Referee+
|
|
7
|
+
def create_referrer
|
|
8
|
+
if struct = _get_reqref
|
|
9
|
+
|
|
10
|
+
self.create_referee(
|
|
11
|
+
origin: struct.referrer_url,
|
|
12
|
+
request: struct.request_url,
|
|
13
|
+
visits: struct.visit_count
|
|
14
|
+
)
|
|
15
|
+
end
|
|
16
|
+
end
|
|
17
|
+
|
|
18
|
+
end
|
|
19
|
+
end
|
|
20
|
+
|
|
@@ -0,0 +1,146 @@
|
|
|
1
|
+
module ActsAsReferred
|
|
2
|
+
|
|
3
|
+
# Namespace for ActsAsReferred-model
|
|
4
|
+
module Model
|
|
5
|
+
|
|
6
|
+
# Represents a Referee -
|
|
7
|
+
# *attributes*
|
|
8
|
+
# [origin] the full URI of referrer
|
|
9
|
+
# [origin_host] host-part of referrer
|
|
10
|
+
# [request] the full request as string
|
|
11
|
+
# [request_query] the query-string - may be nil
|
|
12
|
+
# [campaign] the supplied campaign-name in query
|
|
13
|
+
# [keywords] the supplied keywords in query
|
|
14
|
+
# [is_campaign] if this referee is from campaign
|
|
15
|
+
# [visits] number of visits before conversion
|
|
16
|
+
#
|
|
17
|
+
class ::Referee < ActiveRecord::Base
|
|
18
|
+
|
|
19
|
+
self.table_name = 'referees'
|
|
20
|
+
|
|
21
|
+
belongs_to :referable, polymorphic: true
|
|
22
|
+
|
|
23
|
+
before_create :process_request_and_referrer
|
|
24
|
+
|
|
25
|
+
# all referees which where created throughout a
|
|
26
|
+
# campaign-based request
|
|
27
|
+
scope :campaigns, -> { where('is_campaign=?', true) }
|
|
28
|
+
|
|
29
|
+
# returns referrer as instance of URI
|
|
30
|
+
def origin_uri
|
|
31
|
+
has_referrer? ? URI.parse(origin) : nil
|
|
32
|
+
end
|
|
33
|
+
|
|
34
|
+
# returns host-part of referrer
|
|
35
|
+
# may be nil
|
|
36
|
+
def host
|
|
37
|
+
origin_host
|
|
38
|
+
end
|
|
39
|
+
|
|
40
|
+
# returns path part of request
|
|
41
|
+
# may be nil
|
|
42
|
+
def request_path
|
|
43
|
+
URI.parse(request).path
|
|
44
|
+
end
|
|
45
|
+
|
|
46
|
+
def has_referrer?
|
|
47
|
+
true if origin
|
|
48
|
+
end
|
|
49
|
+
|
|
50
|
+
def has_request?
|
|
51
|
+
true if request
|
|
52
|
+
end
|
|
53
|
+
|
|
54
|
+
def has_query?
|
|
55
|
+
true if request_query
|
|
56
|
+
end
|
|
57
|
+
|
|
58
|
+
private
|
|
59
|
+
|
|
60
|
+
def process_request_and_referrer
|
|
61
|
+
process_origin if origin
|
|
62
|
+
|
|
63
|
+
if request && URI.parse(request).query
|
|
64
|
+
self.request_query = URI.parse(request).query
|
|
65
|
+
if process_request
|
|
66
|
+
self.is_campaign = true
|
|
67
|
+
end
|
|
68
|
+
end
|
|
69
|
+
end
|
|
70
|
+
|
|
71
|
+
def process_request
|
|
72
|
+
if self.request_query
|
|
73
|
+
if self.request_query.match(/utm_campaign/) || self.request_query.match(/utm_term/)
|
|
74
|
+
return process_google_tagged(self.request_query)
|
|
75
|
+
end
|
|
76
|
+
if self.request_query.match(/pk_campaign/) || self.request_query.match(/pk_term/)
|
|
77
|
+
return process_piwik_tagged(self.request_query)
|
|
78
|
+
end
|
|
79
|
+
if self.request_query.match(/gclid/)
|
|
80
|
+
return process_google_auto_tagged(self.request_query)
|
|
81
|
+
end
|
|
82
|
+
end
|
|
83
|
+
end
|
|
84
|
+
|
|
85
|
+
|
|
86
|
+
# a.t.m. only care about campaign name and keywords
|
|
87
|
+
def process_google_tagged(string)
|
|
88
|
+
hash = Hash[* string.split('&').collect { |i| i.split('=') }.flatten]
|
|
89
|
+
retval = nil
|
|
90
|
+
hash.keys.each do |key|
|
|
91
|
+
case key
|
|
92
|
+
#when 'utm_source'
|
|
93
|
+
# source = hash[key]
|
|
94
|
+
when 'utm_campaign'
|
|
95
|
+
self.campaign = hash[key]
|
|
96
|
+
retval = true
|
|
97
|
+
#when 'utm_medium'
|
|
98
|
+
# medium = hash[key]
|
|
99
|
+
when 'utm_term'
|
|
100
|
+
self.keywords = hash[key]
|
|
101
|
+
retval = true
|
|
102
|
+
end
|
|
103
|
+
end
|
|
104
|
+
retval
|
|
105
|
+
end
|
|
106
|
+
|
|
107
|
+
# standard piwik campaign-tracking
|
|
108
|
+
def process_piwik_tagged(string)
|
|
109
|
+
hash = Hash[*(string.split('&').collect { |i| i.split('=') }.flatten)]
|
|
110
|
+
retval = nil
|
|
111
|
+
hash.keys.each do |key|
|
|
112
|
+
case key
|
|
113
|
+
when 'pk_campaign'
|
|
114
|
+
self.campaign = hash[key]
|
|
115
|
+
retval = true
|
|
116
|
+
when 'pk_kwd'
|
|
117
|
+
self.keywords = hash[key]
|
|
118
|
+
retval = true
|
|
119
|
+
end
|
|
120
|
+
end
|
|
121
|
+
retval
|
|
122
|
+
end
|
|
123
|
+
|
|
124
|
+
# adwords set to autotagging
|
|
125
|
+
# no chance to get campaign info by url
|
|
126
|
+
# would have to do cookie parsing - what would suck
|
|
127
|
+
def process_google_auto_tagged(string)
|
|
128
|
+
hash = Hash[* string.split('|').collect { |i| i.split('=') }.flatten]
|
|
129
|
+
retval = nil
|
|
130
|
+
if hash['gclid']
|
|
131
|
+
self.campaign = "Adwords - autotagged: #{hash['gclid']}"
|
|
132
|
+
self.is_campaign = true
|
|
133
|
+
retval = true
|
|
134
|
+
end
|
|
135
|
+
retval
|
|
136
|
+
end
|
|
137
|
+
|
|
138
|
+
def process_origin
|
|
139
|
+
self.origin_host = URI.parse(origin).host
|
|
140
|
+
end
|
|
141
|
+
|
|
142
|
+
end
|
|
143
|
+
|
|
144
|
+
end
|
|
145
|
+
|
|
146
|
+
end
|