Rory McCann avatar Rory McCann committed 4848f24 Merge

merge from main django-lean branch (I think)

Comments (0)

Files changed (6)

 recipe = djangorecipe
 version = 1.1.1
 project = experiments
-projectegg = django-lean
 settings = testsettings
 test = experiments
 eggs = ${buildout:eggs}

experiments/models.py

         anonymous_id = experiment_user.get_anonymous_id()
         if anonymous_id:
             anonymous_visitor = AnonymousVisitor.objects.get(id=anonymous_id)
-            try:
+            if getattr(settings, 'LEAN_AUTOCREATE_GOAL_TYPES', False):
+                (goal_type, created) = GoalType.objects.get_or_create(name=goal_name)
+            else:
                 goal_type = GoalType.objects.get(name=goal_name)
-            except ObjectDoesNotExist:
-                goal_type = GoalType(name=goal_name)
-                goal_type.save()
 
             GoalRecord(goal_type=goal_type,
                        anonymous_visitor=anonymous_visitor).save()

experiments/tests/test_management.py

 # -*- coding: utf-8 -*-
+from __future__ import with_statement
 import logging
 l = logging.getLogger(__name__)
 
 from datetime import timedelta
 
+from django.conf import settings
 from django.core.management.base import CommandError
 from django.test import TestCase
 
                                 DailyConversionReport)
 from experiments.management.commands import update_experiment_reports
 
+from experiments.tests.utils import patch
 
 class TestManagement(TestCase):
     def setUp(self):
                                       timedelta(days=5))
         self.experiment.save()
     
-    def testManageCommand(self):
-        #make sure the manage.py command that generates daily stats work
-        
-        #Running with arguments should raise Exception
-        self.assertRaises(CommandError,
-            update_experiment_reports.Command().handle,
-            "some", "args")
-        
-        #This is what manage.py will call
-        self.runner = update_experiment_reports.Command().run_from_argv
-        #Run the reports
-        self.runner(['manage.py', 'update_experiment_reports'])
-        
-        #Make sure they were generated
-        self.assertEquals(5, DailyEngagementReport.objects.filter(
-                experiment=self.experiment).count())
-        self.assertEquals(5, DailyConversionReport.objects.filter(
-                experiment=self.experiment).count())
+    def testManageCommand(self):        
+        with patch(settings, 'LEAN_ENGAGEMENT_CALCULATOR',
+                'experiments.testsettings.SimpleEngagementCalculator'): 
+            #make sure the manage.py command that generates daily stats work
+            
+            #Running with arguments should raise Exception
+            self.assertRaises(CommandError,
+                update_experiment_reports.Command().handle,
+                "some", "args")
+            
+            #This is what manage.py will call
+            self.runner = update_experiment_reports.Command().run_from_argv
+            #Run the reports
+            self.runner(['manage.py', 'update_experiment_reports'])
+            
+            #Make sure they were generated
+            self.assertEquals(5, DailyEngagementReport.objects.filter(
+                    experiment=self.experiment).count())
+            self.assertEquals(5, DailyConversionReport.objects.filter(
+                    experiment=self.experiment).count())
     

experiments/tests/test_models.py

 # -*- coding: utf-8 -*-
+from __future__ import with_statement
 from datetime import datetime
 
+from django.conf import settings
 from django.test import TestCase
 from django.contrib.auth.models import User
 from experiments.models import (Experiment, Participant, AnonymousVisitor,
                                       GoalType, GoalRecord)
-from experiments.tests.utils import TestUser
+from experiments.tests.utils import TestUser, patch
 
 
 class TestExperimentModels(TestCase):
         self.assert_(num_control2 > 400)
         self.assert_(num_test1 > 400)
         self.assert_(num_test2 > 400)
-    
+
+    def testMissingGoalType(self):
+        anonymous_visitor = AnonymousVisitor()
+        anonymous_visitor.save()
+
+        goal_type = GoalType(name="existing-goal")
+        goal_type.save()
+        
+        nb_types = GoalType.objects.all().count()
+        nb_records = GoalRecord.objects.all().count()
+
+        GoalRecord.record('existing-goal', TestUser(anonymous_visitor=anonymous_visitor))
+        self.assertEquals(nb_records + 1, GoalRecord.objects.all().count())
+        self.assertEqual(nb_types, GoalType.objects.all().count())
+
+        with patch(settings, 'LEAN_AUTOCREATE_GOAL_TYPES', False):
+            GoalRecord.record('inexistant-goal', TestUser(anonymous_visitor=anonymous_visitor))
+            self.assertEquals(nb_records + 1, GoalRecord.objects.all().count())
+            self.assertEqual(nb_types, GoalType.objects.all().count())
+
+        with patch(settings, 'LEAN_AUTOCREATE_GOAL_TYPES', NotImplemented):
+            GoalRecord.record('inexistant-goal', TestUser(anonymous_visitor=anonymous_visitor))
+            self.assertEquals(nb_records + 1, GoalRecord.objects.all().count())
+            self.assertEqual(nb_types, GoalType.objects.all().count())
+            
+        with patch(settings, 'LEAN_AUTOCREATE_GOAL_TYPES', True):
+            GoalRecord.record('inexistant-goal',
+                              TestUser(anonymous_visitor=anonymous_visitor))
+            self.assertEquals(nb_records + 2, GoalRecord.objects.all().count())
+            self.assertEqual(nb_types + 1, GoalType.objects.all().count())
+        
+
     def testGoals(self):
         anonymous_visitor = AnonymousVisitor()
         anonymous_visitor.save()

experiments/tests/utils.py

 import logging
 l = logging.getLogger(__name__)
 
+from contextlib import contextmanager
+
 from django.contrib.auth.models import User
 from django.test import TestCase as DjangoTestCase
+from django.utils.functional import LazyObject
 
 from experiments.loader import ExperimentLoader
 from experiments.models import Participant
         else:
             return added_enrollments.get(experiment_name)
     
+@contextmanager
+def patch(namespace, name, value):
+    """Patches `namespace`.`name` with `value`."""
+    if isinstance(namespace, LazyObject):
+        namespace._setup()
+        namespace = namespace._wrapped
+
+    try:
+        original = getattr(namespace, name)
+    except AttributeError:
+        original = NotImplemented
+    try:
+        if value is NotImplemented:
+            if original is not NotImplemented:
+                delattr(namespace, name)
+        else:
+            setattr(namespace, name, value)
+        yield
+    finally:
+        if original is NotImplemented:
+            if value is not NotImplemented:
+                delattr(namespace, name)
+        else:
+            setattr(namespace, name, original) 

experiments/testsettings.py

 	return 0
 
 ROOT_URLCONF=None
-LEAN_ENGAGEMENT_CALCULATOR= 'experiments.testsettings.SimpleEngagementCalculator'
 DATABASE_ENGINE='sqlite3'
 DATABASE_NAME=':memory:'
 DATABASE_SUPPORTS_TRANSACTIONS=False
Tip: Filter by directory path e.g. /media app.js to search for public/media/app.js.
Tip: Use camelCasing e.g. ProjME to search for ProjectModifiedEvent.java.
Tip: Filter by extension type e.g. /repo .js to search for all .js files in the /repo directory.
Tip: Separate your search with spaces e.g. /ssh pom.xml to search for src/ssh/pom.xml.
Tip: Use ↑ and ↓ arrow keys to navigate and return to view the file.
Tip: You can also navigate files with Ctrl+j (next) and Ctrl+k (previous) and view the file with Ctrl+o.
Tip: You can also navigate files with Alt+j (next) and Alt+k (previous) and view the file with Alt+o.