========================= User/Interaction tracking ========================= ($Id$) >>> from cybertools.tracking.btree import TrackingStorage Let's create a tracking storage and store a few tracks in it. A track is basically an arbitrary mapping. (In the following examples we ignore the ``run`` argument and use a 0 value for it; thus we are just working with the current run of a task.) >>> tracks = TrackingStorage() >>> tracks.saveUserTrack('a001', 0, 'u1', {'somekey': 'somevalue'}) '0000001' >>> t1 = list(tracks.getUserTracks('a001', 0, 'u1')) >>> len(t1) 1 >>> t1[0].data {'somekey': 'somevalue'} >>> tracks.getUserNames('a001') ['u1'] >>> tracks.getUserNames('a002') [] >>> [str(id) for id in tracks.getTaskIds()] ['a001'] We can query the tracking storage using the tracks' metadata. These are mapped to btree indexes, so we get fast access to the resulting track data. >>> list(tracks.query(taskId='a001')) [] >>> tracks.saveUserTrack('a002', 0, 'u1', {'somekey': 'anothervalue'}) '0000002' >>> result = list(tracks.query(userName='u1')) >>> len(result) 2 By supplying a list we can also search for more than one value in one query. >>> result = list(tracks.query(taskId=('a001', 'a002'))) >>> len(result) 2 What happens if we store more than on record for one set of keys? >>> tracks.saveUserTrack('a001', 0, 'u1', {'somekey': 'newvalue'}) '0000003' >>> t2 = tracks.getUserTracks('a001', 0, 'u1') >>> [t.data for t in t2] [{'somekey': 'somevalue'}, {'somekey': 'newvalue'}] It is also possible to retrieve the last entry for a set of keys directly. >>> tracks.getLastUserTrack('a001', 0, 'u1') Instead of creating a new track object for each call one can also replace an existing one (if present). The replaced entry is always the last one for a given set of keys. >>> tracks.saveUserTrack('a001', 0, 'u1', {'somekey': 'newvalue2'}, update=True) '0000003' >>> t3 = tracks.getUserTracks('a001', 0, 'u1') >>> [t.data for t in t3] [{'somekey': 'somevalue'}, {'somekey': 'newvalue2'}] >>> tracks.saveUserTrack('a001', 0, 'u2', {'somekey': 'user2'}, update=True) '0000004' >>> t4 = list(tracks.getUserTracks('a001', 0, 'u2')) >>> [t.data for t in t4] [{'somekey': 'user2'}] The tracks of a tracking store may be reindexed: >>> tracks.reindexTracks() >>> tracks.removeTrack(t4[0]) >>> tracks.getUserTracks('a001', 0, 'u2') [] Runs ---- We may explicitly start a new run for a given task. This will also replace the task's current run. >>> tracks.startRun('a001') 3 >>> tracks.saveUserTrack('a001', 0, 'u1', {'k1': 'value1'}) '0000005' >>> tracks.getLastUserTrack('a001', 0, 'u1') We still have access to older runs. >>> tracks.getLastUserTrack('a001', 1, 'u1') We can also retrieve a run object with the run's data. >>> tracks.getRun(runId=3) We can also use the taskId for retrieving a task's current run. >>> tracks.getRun(taskId='a001') When we stop a run explicitly it is marked as ``finished``. >>> tracks.stopRun('a001') 3 >>> tracks.getRun(runId=3) >>> tracks.getRun(runId=3).finished True Stopping a run removes it from the set of current runs, so the associated task hasn't got a current run any longer: >>> tracks.getRun('a001') is None True We can also mark earlier runs by stopping them. >>> tracks.getRun(runId=2) >>> tracks.stopRun('a001', 2) 2 >>> tracks.getRun(runId=2) Tracking Views ============== >>> from cybertools.tracking.browser import TrackingStorageView Track Read Access via a Log File ================================ >>> import os >>> from cybertools.tracking.tests import testDir >>> from cybertools.tracking.logfile import Logger >>> logfile = os.path.join(testDir, 'test.log') >>> logger = Logger('test', logfile) >>> logger.log('Test message #1') >>> logger.log('Test message #2') >>> logger.doRollover() >>> logger.log('Test message #3') Fin de partie ============= >>> for fn in os.listdir(testDir): ... if '.log' in fn: ... os.unlink(os.path.join(testDir, fn))