Package: django-analytics
A basic Django app facilitating tracking of certain elementary metrics and statistics -
generally just metrics which can be measured in terms of counts and cumulative counts.This app could be useful for keeping track of registrations, page impressions, sessions,
and so on. By default, it allows for tracking of registrations. Adding more metrics
is a relatively straightforward task, as explained further on.ContentsQuick InstallationCreating a mod_analytics ScriptGeckoboard Integration and CSV DumpsMetrics ExplainedCommand Line ReferenceInner WorkingsAbstract MetricsTodoVersion HistoryQuick InstallationSave a copy of thedjango-analyticsapp in your Python path.Add it to yourINSTALLED_APPSlist in your Django project settings.Create amod_analytics.pyfile for each of your apps that require some sort
of tracking. See theCreating a mod_analytics Scriptsection below.Run the following from the command line in order to install the various metrics
and automatically make them active:> python manage.py metrics --installRun the following from the command line to update the daily, weekly and monthly
statistics for each of the active metrics:> python manage.py metrics --calculate=ALLBy default,django-analyticscomes with aregistrationsmetric which counts
the number of users in the system based on theirdate_joinedtimestamp.Creating a mod_analytics ScriptIf, for example, you have an app calledcommentswith the followingmodels.pyfile:from django.db import models
from django.contrib.auth.models import User

class Comment(models.Model):
    user = models.ForeignKey(User, related_name='comments')
    timestamp = models.DateTimeField(auto_now_add=True)
    comment = models.CharField(max_length=300)and you would like to track the total number of comments, you could
create amod_analytics.pyscript (in the same directory as your app’s models)
looking like the following:from analytics.basemetric import BaseMetric
from models import Comment

class TotalComments(BaseMetric):
    uid   = "totalcomments"
    title = "Total comments"

    def calculate(self, start_datetime, end_datetime):
        return Comment.objects.filter(timestamp__gte=start_datetime,
            timestamp__lt=end_datetime).count()

    def get_earliest_timestamp(self):
        try:
            return Comment.objects.all().order_by('timestamp')[0].timestamp
        except IndexError:
            return NoneGeckoboard Integration and CSV DumpsIn order to allow forGeckoboardintegration to allow for
visualisation of your statistics, as well as simple CSV dumping of statistics,
in your project’surls.py, add the following line:urlpatterns = patterns('',
    # ...

    (r'^analytics/', include('analytics.urls')),

    # ...
)Note that this project makes use ofdjango-geckoboard(http://pypi.python.org/pypi/django-geckoboard),
so all of the defaultdjango-geckoboardsettings apply.Geckboard ChartsThis will automatically add the following Geckoboard-related URLs to your project:analytics/geckoboard/numbersAnumbers widget.
Supported GET variable parameters:uid,daysback,cumulative,frequency.daysbackdefault: 7.analytics/geckoboard/ragARAG widget.
Supported GET variable parameters:uids,daysback,cumulative,frequency.analytics/geckoboard/pieApie chart widget.
Supported GET variable parameters:uids,daysback,cumulative,frequency.analytics/geckoboard/lineAline chart widget.
Note that this can only plot a single metric per chart.
Supported GET variable parameters:uid,daysback,cumulative,frequency.daysbackdefault: 7.analytics/geckoboard/geckometerAgeck-o-meter widget.
Supported GET variable parameters:uid,frequency,cumulative,min,max.analytics/geckoboard/funnelAfunnel chart widget.
Supported GET variable parameters:uids,frequency,cumulative,type,percentage,sort.Geckoboard GET Variable ParametersuidThe UID of the metric to display, if a single metric is to be displayed.uidsThe UIDs of the metrics to display, if multiple metrics are to be
displayed.daysbackThe numbers Geckoboard widget shows a single count, and the percentage
change from a previous count. This view returns the most recent count
or cumulative count, as well as the count or cumulative count fromdays_backdays ago.cumulativeA boolean value (eithertorf) indicating whether the period
count is to be returned, or the cumulative count. Default:t.frequencyThe frequency of the statistics to be returned. Can bed,wormfor daily, weekly or monthly, respectively. Default:d.minThe minimum value of a particular metric - usually for pie charts.
Default: 0.maxThe maximum value of a particular metric - usually for pie charts.
Default: 100.typeChart type - only applicable to the funnel chart. See the Geckoboard
API for more details. Default:standard.percentageWhether or not to show a percentage - only applicable to the funnel
chart. See the Geckoboard API for more details. Default:show.sortA boolean value (eithertorf) indicating whether or not to
sort the statistics - only applicable to the funnel chart. See the
Geckoboard API for more details. Default:f.CSV DumpIt will also add the following CSV-related URLs to your project:analytics/csv/<uid>A simple view requiring the UID of the metric as its parameter, returning
a CSV dump of all of the statistics for the given metric. By default, this returns
thedailystatistics for the metric.CSV Dump GET Variable ParametersfrequencyThe frequency of the statistics to be returned. Can bed,wormfor daily, weekly or monthly, respectively. Default:d.
For example,analytics/csv/registrations?frequency=wwill return all
of the weekly registrations over all time as a CSV dump.Metrics ExplainedThedjango-analyticsmodule createsMetricobjects for each type of metric that
needs to be tracked, such as registrations, page impressions, etc. Each metric needs to
have a globally unique identifier (UID) so that it can be referenced from the command line
by name, and a title to provide a little more of a description of what that metric
is.Each metric has a number ofStatisticobjects associated with it, eachStatisticonly being a simple combination of date/time, a count for that date/time, a cumulative
count, and frequency.The frequency can currently only bedaily,weeklyormonthly, and by default, each metric’s statistics are calculated for all of those
frequencies (so a single metric can have multiple frequencies’ statistics).In general, the cumulative count is automatically calculated for you, and is simply the
previous day’s/week’s/month’s cumulative count, added to the current day’s/week’s/month’s
count.Command Line ReferenceThe following options are available from the command line for themetricsmanagement
command:-l,--listLists all of the available metrics, along with some basic information about each.-i,--installScans the project for available metrics and creates or updates them where necessary.-a,--activateActivates the metric with the specified UID, e.g.--activate=registrations.
If you want to activate all metrics,
simply specify--activate=ALLon the command line. Only active metrics will
be included in a--calculate=ALLexecution.-d,--deactivateDeactivates the metric with the specified UID. Again, you can specify--deactivate=ALLto deactivate all metrics.-c,--calculateCalculates the specified metric, e.g.--calculate=registrations. Can
specify--calculate=ALLto calculate all active metrics.-f,--frequencyIf the--calculatecommand is specified, this will allow one to force a particular
frequency’s statistics to be calculated. Possible values are:d(daily),w(weekly),m(monthly) anda(all). Default isall.--resetDeletes all of theStatisticobjects associated with the specified metric.
Can specify--reset=ALLto delete all statistics for all metrics, regardless
of whether they are active or not.--drop-metricDeletes the actualMetricwith the specified UID. Use--drop-metric=ALLto drop all metrics (and their statistics) from the database.Inner WorkingsWhen running themanage.py metrics--installcommand, the following happens:The script searches through all the installed apps for your project and
attempts to first find amod_analyticsmodule which it can import.It then searches through all of the classes in eachmod_analyticsmodule
it encounters, and then attempts to find classes derived from theanalytics.basemetric.BaseMetricclass (an abstract class).For each valid class found which derives from theBaseMetricclass, the script
makes sure it has two functions:calculate, andget_earliest_timestamp.
It also makes sure the class has two properties:uidandtitle.If the class has these two functions, the script creates aMetricinstance
whose unique identifier and title are set to theuidandtitlevalues
of the discovered class.Thecalculatefunction takes two parameters:start_datetimeandend_datetime,
and must simply return a count of the relevant metric between those two given dates. You can
perform any calculations you need in this function to get to this final count value.To understand the reasoning here, theanalyticsapp has three broad calculation time periods
which it attempts to calculate:daily,weeklyandmonthly. For a daily calculation,
for example, thestart_datetimeparameter supplied will resemble something likedatetime(2011, 5, 1)and theend_datetimeparameter will resemble something likedatetime(2011, 5, 2). Thecalculatefunction must then return a count of the relevant
metric for the time period starting at 2011/05/01 00:00 and ending at 2011/05/02 00:00.NOTE: You should always return counts starting at exactly the givenstart_datetimevalue (i.e. greater-than-equal-to), butjust beforetheend_datetimevalue (i.e.
less-than).Theget_earliest_timestampfunction must simply return adatetime.datetimeobject
indicating the earliest data’s associated date/time, so that the analytics calculation routine
knows the date at which to start calculating. If there are no entries yet, this function must
returnNone.Abstract MetricsIf you want to create abstract metrics, simply create a separate Python file somewhere
which will contain your “abstract” metrics. For example, create anabstract_metrics.pyfile which looks as follows:from analytics import BaseMetric
from django.contrib.auth.models import User

class UserBaseMetric(BaseMetric):
    def calculate(self, start_datetime, end_datetime):
        return User.objects.filter(date_joined__gte=start_datetime,
            date_joined__lt=end_datetime).count()

    def get_earliest_timestamp(self):
        try:
            return User.objects.all().order_by('date_joined')[0].date_joined
        except IndexError:
            return NoneThen, in yourmod_analytics.pyfile, just import yourabstract_metricsmodule.Note: Do not import theUserBaseMetric, just import theabstract_metricsmodule,
as follows:from analytics import BaseMetric
import myapp.abstract_metrics

class UserMetric(abstract_metrics.UserBaseMetric):
    uid   = "users"
    title = "Users"TodoThe following features are planned for future versions ofdjango-analytics:Custom visualisation integrated into Django admin back-end.Hourly statistics.More complex statistics, such as frequency plots/histograms.Version HistoryVersionDescription0.0.1First version