2011-04-04 12:50:18 +02:00
|
|
|
import logging
|
|
|
|
import urllib
|
2011-04-05 16:28:27 +02:00
|
|
|
from paste.deploy.converters import asbool
|
2011-04-04 12:50:18 +02:00
|
|
|
from genshi.filters import Transformer
|
|
|
|
from genshi import HTML
|
2011-12-19 10:51:25 +01:00
|
|
|
from genshi.core import START, TEXT
|
2011-04-05 11:38:25 +02:00
|
|
|
from genshi.filters.transform import INSIDE, EXIT
|
2012-07-11 17:40:17 +02:00
|
|
|
import pylons
|
2012-07-11 15:34:18 +02:00
|
|
|
import ckan.lib.helpers as h
|
2012-07-11 11:38:47 +02:00
|
|
|
import ckan.plugins as p
|
|
|
|
import gasnippet
|
|
|
|
import commands
|
2011-04-04 18:44:39 +02:00
|
|
|
import dbutil
|
|
|
|
|
|
|
|
log = logging.getLogger('ckanext.googleanalytics')
|
2011-04-04 12:50:18 +02:00
|
|
|
|
|
|
|
|
|
|
|
class GoogleAnalyticsException(Exception):
|
|
|
|
pass
|
|
|
|
|
|
|
|
|
2012-07-11 11:38:47 +02:00
|
|
|
class GoogleAnalyticsPlugin(p.SingletonPlugin):
|
|
|
|
p.implements(p.IConfigurable, inherit=True)
|
|
|
|
p.implements(p.IGenshiStreamFilter, inherit=True)
|
|
|
|
p.implements(p.IRoutes, inherit=True)
|
|
|
|
p.implements(p.IConfigurer, inherit=True)
|
2011-04-04 12:50:18 +02:00
|
|
|
|
|
|
|
def configure(self, config):
|
|
|
|
if (not 'googleanalytics.id' in config):
|
|
|
|
msg = "Missing googleanalytics.id in config"
|
|
|
|
raise GoogleAnalyticsException(msg)
|
|
|
|
|
2012-07-11 15:34:18 +02:00
|
|
|
ga_id = config['googleanalytics.id']
|
|
|
|
ga_domain = config.get('googleanalytics.domain', 'auto')
|
|
|
|
js_url = h.url_for_static('/scripts/ckanext-googleanalytics.js')
|
|
|
|
self.resource_url = config.get('googleanalytics.resource_prefix',
|
|
|
|
commands.DEFAULT_RESOURCE_URL_TAG)
|
|
|
|
self.show_downloads = asbool(
|
|
|
|
config.get('googleanalytics.show_downloads', True)
|
|
|
|
)
|
|
|
|
self.track_events = asbool(
|
|
|
|
config.get('googleanalytics.track_events', False)
|
|
|
|
)
|
|
|
|
|
|
|
|
self.header_code = HTML(gasnippet.header_code % (ga_id, ga_domain))
|
|
|
|
self.footer_code = HTML(gasnippet.footer_code % js_url)
|
|
|
|
|
2012-07-11 11:38:47 +02:00
|
|
|
def update_config(self, config):
|
|
|
|
p.toolkit.add_template_directory(config, 'templates')
|
2012-07-11 15:34:18 +02:00
|
|
|
p.toolkit.add_public_directory(config, 'public')
|
2012-07-11 11:38:47 +02:00
|
|
|
|
|
|
|
def after_map(self, map):
|
|
|
|
map.redirect("/analytics/package/top", "/analytics/dataset/top")
|
2012-07-11 15:34:18 +02:00
|
|
|
map.connect(
|
|
|
|
'analytics', '/analytics/dataset/top',
|
|
|
|
controller='ckanext.googleanalytics.controller:GAController',
|
|
|
|
action='view'
|
|
|
|
)
|
2012-07-11 11:38:47 +02:00
|
|
|
return map
|
|
|
|
|
2011-04-04 12:50:18 +02:00
|
|
|
def filter(self, stream):
|
2012-07-11 15:34:18 +02:00
|
|
|
log.info("Inserting Google Analytics code into template")
|
|
|
|
|
|
|
|
stream = stream | Transformer('head').append(self.header_code)
|
|
|
|
|
|
|
|
if self.track_events:
|
|
|
|
stream = stream | Transformer('body/div[@id="scripts"]')\
|
|
|
|
.append(self.footer_code)
|
2011-04-04 12:50:18 +02:00
|
|
|
|
2012-07-11 17:40:17 +02:00
|
|
|
routes = pylons.request.environ.get('pylons.routes_dict')
|
2012-07-11 11:38:47 +02:00
|
|
|
action = routes.get('action')
|
2012-04-05 19:12:25 +02:00
|
|
|
controller = routes.get('controller')
|
2012-07-11 15:34:18 +02:00
|
|
|
|
2012-04-05 19:12:25 +02:00
|
|
|
if (controller == 'package' and \
|
|
|
|
action in ['search', 'read', 'resource_read']) or \
|
|
|
|
(controller == 'group' and action == 'read'):
|
2011-12-20 11:56:05 +01:00
|
|
|
|
|
|
|
log.info("Tracking of resource downloads")
|
2012-07-11 11:38:47 +02:00
|
|
|
|
2011-11-29 18:39:49 +01:00
|
|
|
# add download tracking link
|
|
|
|
def js_attr(name, event):
|
|
|
|
attrs = event[1][1]
|
|
|
|
href = attrs.get('href').encode('utf-8')
|
2012-07-11 15:34:18 +02:00
|
|
|
link = '%s%s' % (self.resource_url, urllib.quote(href))
|
2011-11-29 18:39:49 +01:00
|
|
|
js = "javascript: _gaq.push(['_trackPageview', '%s']);" % link
|
|
|
|
return js
|
|
|
|
|
|
|
|
# add some stats
|
|
|
|
def download_adder(stream):
|
2011-12-19 10:51:25 +01:00
|
|
|
download_html = '''<span class="downloads-count">
|
2011-12-20 11:56:05 +01:00
|
|
|
[downloaded %s times]</span>'''
|
2011-11-29 18:39:49 +01:00
|
|
|
count = None
|
|
|
|
for mark, (kind, data, pos) in stream:
|
|
|
|
if mark and kind == START:
|
|
|
|
href = data[1].get('href')
|
|
|
|
if href:
|
|
|
|
count = dbutil.get_resource_visits_for_url(href)
|
|
|
|
if count and mark is EXIT:
|
|
|
|
# emit count
|
|
|
|
yield INSIDE, (TEXT, HTML(download_html % count), pos)
|
|
|
|
yield mark, (kind, data, pos)
|
|
|
|
|
|
|
|
# perform the stream transform
|
2011-12-20 11:56:05 +01:00
|
|
|
stream = stream | Transformer('//a[contains(@class, "resource-url-analytics")]')\
|
2011-11-29 18:39:49 +01:00
|
|
|
.attr('onclick', js_attr)
|
|
|
|
|
2012-07-11 15:34:18 +02:00
|
|
|
if (self.show_downloads and action == 'read' and
|
|
|
|
controller == 'package'):
|
2011-12-20 11:56:05 +01:00
|
|
|
stream = stream | Transformer('//a[contains(@class, "resource-url-analytics")]')\
|
2011-11-29 18:39:49 +01:00
|
|
|
.apply(download_adder)
|
2012-07-11 15:34:18 +02:00
|
|
|
stream = stream | Transformer('//head')\
|
|
|
|
.append(HTML(gasnippet.download_style))
|
2011-11-29 18:39:49 +01:00
|
|
|
|
2011-04-04 12:50:18 +02:00
|
|
|
return stream
|