lanalytics-rails 0.2.9
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/Rakefile +43 -0
- data/app/assets/javascripts/lanalytics.js +17 -0
- data/app/assets/javascripts/lanalytics/lanalytics.framework.js.coffee +128 -0
- data/app/assets/javascripts/lanalytics/model/lanalytics.model.exp_api_statement.js.coffee +41 -0
- data/app/assets/javascripts/lanalytics/model/lanalytics.model.stmt_component.js.coffee +8 -0
- data/app/assets/javascripts/lanalytics/model/lanalytics.model.stmt_resource.js.coffee +16 -0
- data/app/assets/javascripts/lanalytics/model/lanalytics.model.stmt_user.js.coffee +14 -0
- data/app/assets/javascripts/lanalytics/model/lanalytics.model.stmt_verb.js.coffee +12 -0
- data/app/assets/javascripts/lanalytics/plugins/lanalytics.plugins.example.html5videoplayer.js.coffee +25 -0
- data/app/assets/javascripts/lanalytics/plugins/lanalytics.plugins.newplugintemplate.js.coffee +23 -0
- data/app/assets/javascripts/lanalytics/plugins/lanalytics.plugins.pageviewplugin.js.coffee +42 -0
- data/app/assets/javascripts/lanalytics/plugins/lanalytics.plugins.statichtmlevent.js.coffee +31 -0
- data/app/controllers/lanalytics/tracking_controller.rb +28 -0
- data/config/routes.rb +17 -0
- data/lib/lanalytics-rails.rb +10 -0
- data/lib/lanalytics/engine.rb +11 -0
- data/lib/lanalytics/lanalytics_controller_filter.rb +24 -0
- data/lib/lanalytics/version.rb +3 -0
- data/lib/tasks/lanalytics_tasks.rake +4 -0
- data/spec/controllers/tracking_controller_spec.rb +45 -0
- data/spec/dummy/README.rdoc +28 -0
- data/spec/dummy/Rakefile +6 -0
- data/spec/dummy/app/assets/javascripts/application.js +14 -0
- data/spec/dummy/app/assets/stylesheets/application.css +15 -0
- data/spec/dummy/app/controllers/application_controller.rb +9 -0
- data/spec/dummy/app/controllers/welcome_controller.rb +10 -0
- data/spec/dummy/app/helpers/application_helper.rb +2 -0
- data/spec/dummy/app/helpers/welcome_helper.rb +2 -0
- data/spec/dummy/app/views/layouts/application.html.erb +15 -0
- data/spec/dummy/app/views/welcome/index.html.erb +5 -0
- data/spec/dummy/bin/bundle +3 -0
- data/spec/dummy/bin/rails +4 -0
- data/spec/dummy/bin/rake +4 -0
- data/spec/dummy/config.ru +4 -0
- data/spec/dummy/config/application.rb +24 -0
- data/spec/dummy/config/boot.rb +5 -0
- data/spec/dummy/config/database.yml +25 -0
- data/spec/dummy/config/environment.rb +5 -0
- data/spec/dummy/config/environments/development.rb +37 -0
- data/spec/dummy/config/environments/production.rb +82 -0
- data/spec/dummy/config/environments/test.rb +39 -0
- data/spec/dummy/config/initializers/assets.rb +8 -0
- data/spec/dummy/config/initializers/backtrace_silencers.rb +7 -0
- data/spec/dummy/config/initializers/cookies_serializer.rb +3 -0
- data/spec/dummy/config/initializers/filter_parameter_logging.rb +4 -0
- data/spec/dummy/config/initializers/inflections.rb +16 -0
- data/spec/dummy/config/initializers/mime_types.rb +4 -0
- data/spec/dummy/config/initializers/session_store.rb +3 -0
- data/spec/dummy/config/initializers/wrap_parameters.rb +14 -0
- data/spec/dummy/config/locales/en.yml +23 -0
- data/spec/dummy/config/routes.rb +59 -0
- data/spec/dummy/config/secrets.yml +22 -0
- data/spec/dummy/public/404.html +67 -0
- data/spec/dummy/public/422.html +67 -0
- data/spec/dummy/public/500.html +66 -0
- data/spec/dummy/public/favicon.ico +0 -0
- data/spec/dummy/spec/controllers/welcome_controller_spec.rb +12 -0
- data/spec/dummy/spec/helpers/welcome_helper_spec.rb +15 -0
- data/spec/dummy/spec/javascripts/support/jasmine.yml +50 -0
- data/spec/dummy/spec/views/welcome/index.html.erb_spec.rb +5 -0
- data/spec/factories/exp_api_statement_factory.rb +7 -0
- data/spec/javascripts/foo.js.coffee +8 -0
- data/spec/javascripts/lanlaytics/model/exp_api_statement_spec.js.coffee +157 -0
- data/spec/javascripts/support/jasmine.yml +50 -0
- data/spec/rails_helper.rb +50 -0
- data/spec/spec_helper.rb +98 -0
- metadata +298 -0
checksums.yaml
ADDED
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
---
|
|
2
|
+
SHA1:
|
|
3
|
+
metadata.gz: bccfc3e4db4ed376314e8f978c475749316f58dc
|
|
4
|
+
data.tar.gz: 5e311be19936df67cf1028f9ed4b15694d8fa90a
|
|
5
|
+
SHA512:
|
|
6
|
+
metadata.gz: c5cde7057286068c228fd7bc03ebdb5a0ee09ab9672aab058fdadbe32b50c613820439fdaadfbd257f1bfce84ce9cff182d16fcacf4b91957cf80c61ceae10db
|
|
7
|
+
data.tar.gz: 218af978189ca12381fdc77a3f5d813aef704dd65a48a303f4df51e9d74d014e8a366c5ba1d5d2f8c45ffacd325e0f1a2c9e8861bf3a0c0c7cf4e2ebdbe268ff
|
data/MIT-LICENSE
ADDED
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
Copyright 2014 YOURNAME
|
|
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/Rakefile
ADDED
|
@@ -0,0 +1,43 @@
|
|
|
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 'geminabox/rake'
|
|
8
|
+
Geminabox::Rake.install host: 'https://gemuser:K6c1mcRWtrTQepS6aI8HRXc7DPoRYXbG@dev.xikolo.de/gems/',
|
|
9
|
+
dir: '.',
|
|
10
|
+
namespace: 'lanalytics-rails'
|
|
11
|
+
|
|
12
|
+
require 'rdoc/task'
|
|
13
|
+
|
|
14
|
+
RDoc::Task.new(:rdoc) do |rdoc|
|
|
15
|
+
rdoc.rdoc_dir = 'rdoc'
|
|
16
|
+
rdoc.title = 'Lanalytics'
|
|
17
|
+
rdoc.options << '--line-numbers'
|
|
18
|
+
rdoc.rdoc_files.include('README.rdoc')
|
|
19
|
+
rdoc.rdoc_files.include('lib/**/*.rb')
|
|
20
|
+
end
|
|
21
|
+
|
|
22
|
+
APP_RAKEFILE = File.expand_path("../spec/dummy/Rakefile", __FILE__)
|
|
23
|
+
load 'rails/tasks/engine.rake'
|
|
24
|
+
|
|
25
|
+
Bundler::GemHelper.install_tasks
|
|
26
|
+
|
|
27
|
+
require 'rspec/core'
|
|
28
|
+
require 'rspec/core/rake_task'
|
|
29
|
+
|
|
30
|
+
desc "Run all specs in spec directory (excluding plugin specs)"
|
|
31
|
+
RSpec::Core::RakeTask.new(:spec => 'app:db:test:prepare')
|
|
32
|
+
|
|
33
|
+
# require 'jasmine'
|
|
34
|
+
# load 'jasmine/tasks/jasmine.rake'
|
|
35
|
+
|
|
36
|
+
begin
|
|
37
|
+
require 'jasmine'
|
|
38
|
+
load 'jasmine/tasks/jasmine.rake'
|
|
39
|
+
rescue LoadError
|
|
40
|
+
task :jasmine do
|
|
41
|
+
abort "Jasmine is not available. In order to run jasmine, you must: (sudo) gem install jasmine"
|
|
42
|
+
end
|
|
43
|
+
end
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
// Including the files necessary for the Lanalytics service
|
|
2
|
+
|
|
3
|
+
//= require jquery
|
|
4
|
+
|
|
5
|
+
//= require ./lanalytics/model/lanalytics.model.stmt_component.js.coffee
|
|
6
|
+
//= require ./lanalytics/model/lanalytics.model.stmt_resource.js.coffee
|
|
7
|
+
//= require ./lanalytics/model/lanalytics.model.stmt_verb.js.coffee
|
|
8
|
+
//= require ./lanalytics/model/lanalytics.model.stmt_user.js.coffee
|
|
9
|
+
//= require ./lanalytics/model/lanalytics.model.exp_api_statement.js.coffee
|
|
10
|
+
//= require ./lanalytics/lanalytics.framework.js.coffee
|
|
11
|
+
//= require_directory ./lanalytics/plugins
|
|
12
|
+
|
|
13
|
+
// Files that we do not want to release
|
|
14
|
+
//= stub ./lanalytics/plugins/lanalytics.plugins.newplugintemplate.js.coffee
|
|
15
|
+
//= stub ./lanalytics/plugins/lanalytics.plugins.example.html5videoplayer.js.coffee
|
|
16
|
+
|
|
17
|
+
lanalytics = new Lanalytics.Framework();
|
|
@@ -0,0 +1,128 @@
|
|
|
1
|
+
# Turning on debug mode for development
|
|
2
|
+
# DEBUG = true if typeof DEBUG is "undefined"
|
|
3
|
+
# Turning off debug mode for development
|
|
4
|
+
DEBUG = false if typeof DEBUG is "undefined"
|
|
5
|
+
|
|
6
|
+
window.Lanalytics or= {};
|
|
7
|
+
|
|
8
|
+
class window.Lanalytics.Framework
|
|
9
|
+
|
|
10
|
+
constructor: ->
|
|
11
|
+
@eventQueue = [];
|
|
12
|
+
@plugins = []
|
|
13
|
+
|
|
14
|
+
addPlugin: (plugin) ->
|
|
15
|
+
# if plugin instanceof throw "Plugin is not a Lanalytics.Plugin
|
|
16
|
+
@plugins.push(plugin)
|
|
17
|
+
|
|
18
|
+
currentUser: ->
|
|
19
|
+
if gon?.lanalytics?.current_user?
|
|
20
|
+
return new Lanalytics.Model.StmtUser(gon.lanalytics.current_user.id)
|
|
21
|
+
else
|
|
22
|
+
return new Lanalytics.Model.AnonymousUser()
|
|
23
|
+
|
|
24
|
+
track: (user, verb, resource, withResult = {}, inContext = {}) ->
|
|
25
|
+
|
|
26
|
+
# If a verb is key, we will replace it with the verb that we need to transmit
|
|
27
|
+
verb = Lanalytics.VerbDictionary.getVerb(verb) if typeof verb is "string"
|
|
28
|
+
now = new Date()
|
|
29
|
+
|
|
30
|
+
experienceStmt = new Lanalytics.Model.ExpApiStatement(user, verb, resource, now, withResult, inContext)
|
|
31
|
+
|
|
32
|
+
@eventQueue.push(experienceStmt)
|
|
33
|
+
|
|
34
|
+
@processEventQueue()
|
|
35
|
+
|
|
36
|
+
console.debug("New event was tracked:", experienceStmt) if (DEBUG)
|
|
37
|
+
|
|
38
|
+
# Verb can a key or an js object
|
|
39
|
+
# Resource should be an object that contains the resource type and the resource key
|
|
40
|
+
trackCurrentUserDoing: (verb, resource, withResult = {}, inContext = {}) ->
|
|
41
|
+
|
|
42
|
+
user = @currentUser()
|
|
43
|
+
@track(user, verb, resource, withResult, inContext)
|
|
44
|
+
|
|
45
|
+
processEventQueue: ->
|
|
46
|
+
|
|
47
|
+
# if eventQueue < 10
|
|
48
|
+
|
|
49
|
+
experienceStatement = @eventQueue.shift()
|
|
50
|
+
|
|
51
|
+
$.ajax("/lanalytics/log", {
|
|
52
|
+
type: 'POST',
|
|
53
|
+
cache: false,
|
|
54
|
+
dataType: 'JSON',
|
|
55
|
+
data: experienceStatement.params() ,
|
|
56
|
+
success: (response_data, text_status, jqXHR) ->
|
|
57
|
+
# Do nothing for now
|
|
58
|
+
error: (jqXHR, textStatus, errorThrown) =>
|
|
59
|
+
@eventQueue.push(experienceStatement)
|
|
60
|
+
})
|
|
61
|
+
|
|
62
|
+
|
|
63
|
+
class window.Lanalytics.VerbDictionary
|
|
64
|
+
|
|
65
|
+
@_verbDict = {
|
|
66
|
+
"video-play": {
|
|
67
|
+
verb_key: "video_play",
|
|
68
|
+
verb_id: "http://lanalytics.open.hpi.de/expapi/verbs/video-play"
|
|
69
|
+
},
|
|
70
|
+
"video-pause": {
|
|
71
|
+
verb_key: "video_pause",
|
|
72
|
+
verb_id: "http://lanalytics.open.hpi.de/expapi/verbs/video-stop"
|
|
73
|
+
},
|
|
74
|
+
"video-seek": {
|
|
75
|
+
verb_key: "video_seek",
|
|
76
|
+
verb_id: 'http://lanalytics.open.hpi.de/expapi/verbs/quiz-submitted'
|
|
77
|
+
},
|
|
78
|
+
"video-change-speed": {
|
|
79
|
+
verb_key: "video_change_speed",
|
|
80
|
+
verb_id: 'http://lanalytics.open.hpi.de/expapi/verbs/video-change-speed'
|
|
81
|
+
},
|
|
82
|
+
"quiz-submitted": {
|
|
83
|
+
verb_key: "quiz_submitted",
|
|
84
|
+
verb_id: 'http://lanalytics.open.hpi.de/expapi/verbs/quiz-submitted'
|
|
85
|
+
},
|
|
86
|
+
"video-change-size": {
|
|
87
|
+
verb_key: "video_change_size",
|
|
88
|
+
verb_id: 'http://lanalytics.open.hpi.de/expapi/verbs/video-change-size'
|
|
89
|
+
},
|
|
90
|
+
"video-fullscreen": {
|
|
91
|
+
verb_key: "video_fullscreen",
|
|
92
|
+
verb_id: 'http://lanalytics.open.hpi.de/expapi/verbs/video-fullscreen'
|
|
93
|
+
}
|
|
94
|
+
|
|
95
|
+
}
|
|
96
|
+
|
|
97
|
+
@_undefinedVerbTemplate = {
|
|
98
|
+
verb_key: "undefined",
|
|
99
|
+
id: "http://lanalytics.open.hpi.de/expapi/verbs/undefined"
|
|
100
|
+
}
|
|
101
|
+
|
|
102
|
+
@getVerb: (id) ->
|
|
103
|
+
|
|
104
|
+
if VerbDictionary._verbDict[id]?
|
|
105
|
+
return new Lanalytics.Model.StmtVerb(VerbDictionary._verbDict[id].verb_key)
|
|
106
|
+
else
|
|
107
|
+
return new Lanalytics.Model.StmtVerb(id)
|
|
108
|
+
|
|
109
|
+
|
|
110
|
+
|
|
111
|
+
class window.Lanalytics.Plugin
|
|
112
|
+
constructor: (@lanalytics) ->
|
|
113
|
+
|
|
114
|
+
@newInstance: (lanalyticsTracker) ->
|
|
115
|
+
throw "This function has to be implemented in the subclass."
|
|
116
|
+
|
|
117
|
+
# The plugin are supposed to be defined under this namesspace
|
|
118
|
+
window.Lanalytics.Plugins or= {};
|
|
119
|
+
|
|
120
|
+
$ ->
|
|
121
|
+
for pluginClassName in Object.keys(Lanalytics.Plugins)
|
|
122
|
+
try
|
|
123
|
+
plugin = Lanalytics.Plugins[pluginClassName].newInstance(lanalytics)
|
|
124
|
+
lanalytics.addPlugin(plugin)
|
|
125
|
+
console.log("Lanalytics.Plugins.#{pluginClassName} found, created and added") if (DEBUG)
|
|
126
|
+
catch error
|
|
127
|
+
console.log("Lanalytics.Plugins.#{pluginClassName} found, but could not be instantiated") if (DEBUG)
|
|
128
|
+
console.log(error.stack) if (DEBUG)
|
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
window.Lanalytics or= {};
|
|
2
|
+
window.Lanalytics.Model or= {};
|
|
3
|
+
|
|
4
|
+
class window.Lanalytics.Model.ExpApiStatement
|
|
5
|
+
|
|
6
|
+
constructor: (user, verb, resource, timestamp = new Date(), @with_result = {}, @in_context = {}) ->
|
|
7
|
+
# ::TODO Some assertions to ensure the datamodel
|
|
8
|
+
throw "'user' argument cannot be nil and should be Lanalytics::Model::StmtUser" unless user instanceof Lanalytics.Model.StmtUser
|
|
9
|
+
@user = user
|
|
10
|
+
|
|
11
|
+
throw "'verb' argument cannot be nil and should be Lanalytics::Model::StmtVerb" unless verb instanceof Lanalytics.Model.StmtVerb
|
|
12
|
+
@verb = verb
|
|
13
|
+
|
|
14
|
+
throw "'resource' argument cannot be nil and should be Lanalytics::Model::StmtResource" unless resource instanceof Lanalytics.Model.StmtResource
|
|
15
|
+
@resource = resource
|
|
16
|
+
|
|
17
|
+
timestamp ||= DateTime.now
|
|
18
|
+
throw "'timestamp' argument should be DateTime or String" unless timestamp instanceof Date or timestamp instanceof String
|
|
19
|
+
timestamp = new Date(timestamp) if timestamp instanceof String
|
|
20
|
+
@timestamp = timestamp
|
|
21
|
+
|
|
22
|
+
|
|
23
|
+
# This is the serialization
|
|
24
|
+
serialize: ->
|
|
25
|
+
return JSON.stringify(@params)
|
|
26
|
+
|
|
27
|
+
params: ->
|
|
28
|
+
return {
|
|
29
|
+
user: @user.params(),
|
|
30
|
+
verb: @verb.params(),
|
|
31
|
+
resource: @resource.params(),
|
|
32
|
+
timestamp: @timestamp,
|
|
33
|
+
with_result: @with_result,
|
|
34
|
+
in_context: @in_context
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
|
|
38
|
+
|
|
39
|
+
|
|
40
|
+
|
|
41
|
+
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
window.Lanalytics or= {};
|
|
2
|
+
window.Lanalytics.Model or= {};
|
|
3
|
+
|
|
4
|
+
class window.Lanalytics.Model.StmtResource extends Lanalytics.Model.StmtComponent
|
|
5
|
+
|
|
6
|
+
constructor: (type, uuid) ->
|
|
7
|
+
super(type)
|
|
8
|
+
|
|
9
|
+
throw "'uuid' argument cannot be nil or empty" if !uuid? || !uuid.trim().length
|
|
10
|
+
@uuid = uuid.toString()
|
|
11
|
+
|
|
12
|
+
params: ->
|
|
13
|
+
return {
|
|
14
|
+
type: @type,
|
|
15
|
+
uuid: @uuid
|
|
16
|
+
}
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
window.Lanalytics or= {};
|
|
2
|
+
window.Lanalytics.Model or= {};
|
|
3
|
+
|
|
4
|
+
class window.Lanalytics.Model.StmtUser extends window.Lanalytics.Model.StmtResource
|
|
5
|
+
|
|
6
|
+
constructor: (uuid) ->
|
|
7
|
+
super("User", uuid)
|
|
8
|
+
|
|
9
|
+
|
|
10
|
+
|
|
11
|
+
class window.Lanalytics.Model.AnonymousUser extends window.Lanalytics.Model.StmtUser
|
|
12
|
+
|
|
13
|
+
constructor: ->
|
|
14
|
+
super("User", "ANONYMOUS")
|
data/app/assets/javascripts/lanalytics/plugins/lanalytics.plugins.example.html5videoplayer.js.coffee
ADDED
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
# This plugin was created for the xikolo-web application in order to track the events from the (custom) video player
|
|
2
|
+
# This is exactly the situation for which a olugin is designed for ...
|
|
3
|
+
class window.Lanalytics.Plugins.Html5VideoPlayerTracker extends Lanalytics.Plugin
|
|
4
|
+
|
|
5
|
+
# This is the interface method expected by Lanalytics
|
|
6
|
+
# Should return a valid instance of the plugin
|
|
7
|
+
@newInstance: (lanalytics) ->
|
|
8
|
+
return new Lanalytics.Plugins.Html5VideoPlayerTracker(lanalytics)
|
|
9
|
+
|
|
10
|
+
constructor: (lanalytics) ->
|
|
11
|
+
super(lanalytics)
|
|
12
|
+
this._init()
|
|
13
|
+
|
|
14
|
+
_init: ->
|
|
15
|
+
$(document).on("video-play", @trackVideoPlay)
|
|
16
|
+
$(document).on("video-pause", @trackVideoPause)
|
|
17
|
+
|
|
18
|
+
# It is important to use '=>' because then 'this' will be binded to StaticHtmlEventTracker instance (in order to access lanalytics)
|
|
19
|
+
trackVideoPlay: (event, videoPlayerData) =>
|
|
20
|
+
stmtResource = new Lanalytics.Model.StmtResource("Item", videoPlayerData.resource)
|
|
21
|
+
@lanalytics.track("video-play", stmtResource)
|
|
22
|
+
|
|
23
|
+
trackVideoPause: (event, videoPlayerData) =>
|
|
24
|
+
stmtResource = new Lanalytics.Model.StmtResource("Item", videoPlayerData.resource)
|
|
25
|
+
@lanalytics.trackCurrentUserDoing("video-pause", stmtResource)
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
|
|
2
|
+
class window.Lanalytics.Plugins.NewLanalyticsPlugin extends Lanalytics.Plugin
|
|
3
|
+
|
|
4
|
+
# This is the interface method expected by Lanalytics
|
|
5
|
+
# Should return a valid instance of the plugin
|
|
6
|
+
@newInstance: (lanalytics) ->
|
|
7
|
+
return new Lanalytics.Plugins.NewLanalyticsPlugin(lanalytics)
|
|
8
|
+
|
|
9
|
+
constructor: (lanalytics) ->
|
|
10
|
+
super(lanalytics)
|
|
11
|
+
this._init()
|
|
12
|
+
|
|
13
|
+
_init: ->
|
|
14
|
+
# Do something
|
|
15
|
+
# Register to some events in the DOM, e.g. $(document).on("video-play", @trackVideoPlay)
|
|
16
|
+
$(document).on("video-pause", @trackVideoPause)
|
|
17
|
+
|
|
18
|
+
# Handler for the event in the DOM
|
|
19
|
+
# It is important to use '=>' because then 'this' will be binded to NewLanalyticsPlugin instance (in order to access lanalytics)
|
|
20
|
+
# trackVideoPlay: (event, videoPlayerData) =>
|
|
21
|
+
# @lanalytics.trackCurrentUserDoing("video-play", {
|
|
22
|
+
# resource_id: videoPlayerData.resource
|
|
23
|
+
# })
|
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
|
|
2
|
+
class window.Lanalytics.Plugins.PageViewPlugin extends Lanalytics.Plugin
|
|
3
|
+
|
|
4
|
+
# This is the interface method expected by Lanalytics
|
|
5
|
+
# Should return a valid instance of the plugin
|
|
6
|
+
@newInstance: (lanalytics) ->
|
|
7
|
+
return new Lanalytics.Plugins.PageViewPlugin(lanalytics)
|
|
8
|
+
|
|
9
|
+
constructor: (lanalytics) ->
|
|
10
|
+
super(lanalytics)
|
|
11
|
+
this._init()
|
|
12
|
+
@windowLoadTimestamp = undefined
|
|
13
|
+
|
|
14
|
+
_init: ->
|
|
15
|
+
$(window).load(@enterPage);
|
|
16
|
+
|
|
17
|
+
# $(window).unload(@leavePage);
|
|
18
|
+
|
|
19
|
+
enterPage: (event, data) =>
|
|
20
|
+
@windowLoadTimestamp = @currentTime()
|
|
21
|
+
|
|
22
|
+
# Do nothing if there is no user logged in
|
|
23
|
+
return if @lanalytics.currentUser() instanceof Lanalytics.Model.AnonymousUser
|
|
24
|
+
|
|
25
|
+
inContext =
|
|
26
|
+
user_os: navigator?.platform
|
|
27
|
+
user_agent: navigator?.userAgent
|
|
28
|
+
user_app_version: navigator?.appVersion
|
|
29
|
+
|
|
30
|
+
urlPathLocation = window?.location?.pathname
|
|
31
|
+
stmtResource = new Lanalytics.Model.StmtResource("PAGE", urlPathLocation)
|
|
32
|
+
@lanalytics.trackCurrentUserDoing("viewed_page", stmtResource, {}, inContext)
|
|
33
|
+
|
|
34
|
+
|
|
35
|
+
# leavePage: (event, videoPlayerData) =>
|
|
36
|
+
# @windowLoadTimestamp
|
|
37
|
+
# timeOnPage = @currentTime() - @windowLoadTimestamp
|
|
38
|
+
# console.log(data)
|
|
39
|
+
# @lanalytics.trackCurrentUserDoing("observed", stmtResource)
|
|
40
|
+
|
|
41
|
+
currentTime: ->
|
|
42
|
+
return new Date().getTime()
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
|
|
2
|
+
|
|
3
|
+
class window.Lanalytics.Plugins.StaticHtmlEventTracker extends Lanalytics.Plugin
|
|
4
|
+
|
|
5
|
+
# This is the interface method expected by Lanalytics
|
|
6
|
+
# Should return a valid instance of the plugin
|
|
7
|
+
@newInstance: (lanalytics) ->
|
|
8
|
+
return new Lanalytics.Plugins.StaticHtmlEventTracker(lanalytics)
|
|
9
|
+
|
|
10
|
+
constructor: (lanalytics) ->
|
|
11
|
+
super(lanalytics)
|
|
12
|
+
this._init()
|
|
13
|
+
|
|
14
|
+
_init: ->
|
|
15
|
+
$("*[data-lanalytics-event]").on("click", @processStaticHtmlEvent)
|
|
16
|
+
|
|
17
|
+
# It is important to use '=>' because then 'this' will be binded to StaticHtmlEventTracker instance (in order to access lanalytics)
|
|
18
|
+
processStaticHtmlEvent: (event) =>
|
|
19
|
+
|
|
20
|
+
clickedElement = event.target
|
|
21
|
+
lanalyticsParentsOfElement = $(clickedElement).parents("[data-lanalytics-resource]")
|
|
22
|
+
if lanalyticsParentsOfElement.length == 0
|
|
23
|
+
throw "No 'data-lanalytics-resource' field could be found in the parents of #{$(clickedElement).html().trim()}."
|
|
24
|
+
|
|
25
|
+
eventData = $(clickedElement).data("lanalytics-event")
|
|
26
|
+
stmtVerb = new Lanalytics.Model.StmtVerb(eventData['verb'])
|
|
27
|
+
|
|
28
|
+
eventResourceData = lanalyticsParentsOfElement.first().data("lanalytics-resource");
|
|
29
|
+
stmtResource = new Lanalytics.Model.StmtResource(eventResourceData['type'], eventResourceData['uuid'])
|
|
30
|
+
|
|
31
|
+
@lanalytics.trackCurrentUserDoing(stmtVerb, stmtResource)
|