Esempio n. 1
0
 def test_incomplete_last_month(self):
     dates = month_periods(
         from_date=date(year=2014, month=1, day=9))
     self.assertTrue(len(dates) == 13)
     self.assertTrue(
         dates[0] == datetime(year=2013, month=2, day=1, tzinfo=utc))
     self.assertTrue(
         dates[1] == datetime(year=2013, month=3, day=1, tzinfo=utc))
     self.assertTrue(
         dates[2] == datetime(year=2013, month=4, day=1, tzinfo=utc))
     self.assertTrue(
         dates[3] == datetime(year=2013, month=5, day=1, tzinfo=utc))
     self.assertTrue(
         dates[4] == datetime(year=2013, month=6, day=1, tzinfo=utc))
     self.assertTrue(
         dates[5] == datetime(year=2013, month=7, day=1, tzinfo=utc))
     self.assertTrue(
         dates[6] == datetime(year=2013, month=8, day=1, tzinfo=utc))
     self.assertTrue(
         dates[7] == datetime(year=2013, month=9, day=1, tzinfo=utc))
     self.assertTrue(
         dates[8] == datetime(year=2013, month=10, day=1, tzinfo=utc))
     self.assertTrue(
         dates[9] == datetime(year=2013, month=11, day=1, tzinfo=utc))
     self.assertTrue(
         dates[10] == datetime(year=2013, month=12, day=1, tzinfo=utc))
     self.assertTrue(
         dates[11] == datetime(year=2014, month=1, day=1, tzinfo=utc))
     self.assertTrue(
         dates[12] == datetime(year=2014, month=1, day=9, tzinfo=utc))
Esempio n. 2
0
 def get(self, request, *args, **kwargs): #pylint: disable=unused-argument
     self.cache_fields(request)
     response = HttpResponse(content_type='text/csv')
     response['Content-Disposition'] = ('attachment; filename="%s.csv"'
         % self.queryname)
     writer = csv.writer(response)
     # column headers
     values = ['name']
     for end_period in month_periods(from_date=self.ends_at):
         values += [end_period]
     writer.writerow(values)
     # rows
     for key in Transaction.objects.distinct_accounts():
         values = [key] + [item[1] for item in monthly_balances(
             self.organization, key, self.ends_at)]
         writer.writerow(values)
     return response
Esempio n. 3
0
 def get(self, request, *args, **kwargs):  #pylint: disable=unused-argument
     self.cache_fields(request)
     response = HttpResponse(content_type='text/csv')
     response['Content-Disposition'] = ('attachment; filename="%s.csv"' %
                                        self.queryname)
     writer = csv.writer(response)
     # column headers
     values = ['name']
     for end_period in month_periods(from_date=self.ends_at):
         values += [end_period]
     writer.writerow(values)
     # rows
     for key in Transaction.objects.distinct_accounts():
         values = [key] + [
             item[1] for item in monthly_balances(self.organization, key,
                                                  self.ends_at)
         ]
         writer.writerow(values)
     return response
Esempio n. 4
0
 def test_month_periods_pos_offset(self):
     """
     Test datetime with positive timeoffset and no timezone
     """
     results = month_periods(from_date="2018-04-18T00:00:00+03:00")
     results = [str(res) for res in results]
     self.assertEqual(results, [
         '2017-05-01 00:00:00+03:00',
         '2017-06-01 00:00:00+03:00',
         '2017-07-01 00:00:00+03:00',
         '2017-08-01 00:00:00+03:00',
         '2017-09-01 00:00:00+03:00',
         '2017-10-01 00:00:00+03:00',
         '2017-11-01 00:00:00+03:00',
         '2017-12-01 00:00:00+03:00',
         '2018-01-01 00:00:00+03:00',
         '2018-02-01 00:00:00+03:00',
         '2018-03-01 00:00:00+03:00',
         '2018-04-01 00:00:00+03:00',
         '2018-04-18 00:00:00+03:00'])
Esempio n. 5
0
 def test_month_periods_utc(self):
     """
     Test UTC datetime with no timezone
     """
     results = month_periods(from_date="2018-04-18T00:00:00+00:00")
     results = [str(res) for res in results]
     self.assertEqual(results, [
         '2017-05-01 00:00:00+00:00',
         '2017-06-01 00:00:00+00:00',
         '2017-07-01 00:00:00+00:00',
         '2017-08-01 00:00:00+00:00',
         '2017-09-01 00:00:00+00:00',
         '2017-10-01 00:00:00+00:00',
         '2017-11-01 00:00:00+00:00',
         '2017-12-01 00:00:00+00:00',
         '2018-01-01 00:00:00+00:00',
         '2018-02-01 00:00:00+00:00',
         '2018-03-01 00:00:00+00:00',
         '2018-04-01 00:00:00+00:00',
         '2018-04-18 00:00:00+00:00'])
Esempio n. 6
0
 def test_month_periods_timezone(self):
     """
     Test datetime with a timezone
     """
     results = month_periods(from_date="2018-04-18T00:00:00-04:00",
         tz="US/Eastern")
     results = [str(res) for res in results]
     self.assertEqual(results, [
         '2017-05-01 00:00:00-04:00',
         '2017-06-01 00:00:00-04:00',
         '2017-07-01 00:00:00-04:00',
         '2017-08-01 00:00:00-04:00',
         '2017-09-01 00:00:00-04:00',
         '2017-10-01 00:00:00-04:00',
         '2017-11-01 00:00:00-04:00',
         '2017-12-01 00:00:00-05:00',
         '2018-01-01 00:00:00-05:00',
         '2018-02-01 00:00:00-05:00',
         '2018-03-01 00:00:00-05:00',
         '2018-04-01 00:00:00-04:00',
         '2018-04-18 00:00:00-04:00'])
    def _handle(self, *args, **options):
        #pylint: disable=too-many-locals,too-many-statements
        from saas.managers.metrics import month_periods  # avoid import loop
        from saas.models import (Charge, ChargeItem, Organization, Plan,
                                 Subscription)

        if 'database' in options:
            db_name = options['database']
            set_current_site(get_site_model().objects.get(
                slug=options['provider'], db_name=db_name),
                             path_prefix='')
        else:
            db_name = 'default'
        now = datetime.datetime.utcnow().replace(tzinfo=utc)
        from_date = now
        from_date = datetime.datetime(year=from_date.year,
                                      month=from_date.month,
                                      day=1)
        if args:
            from_date = datetime.datetime.strptime(args[0], '%Y-%m-%d')
        # Create Income transactions that represents a growing bussiness.
        provider = Organization.objects.get(slug=options['provider'])
        processor = Organization.objects.get(pk=PROCESSOR_ID)
        for end_period in month_periods(from_date=from_date):
            nb_new_customers = random.randint(0, 9)
            for _ in range(nb_new_customers):
                queryset = Plan.objects.filter(organization=provider,
                                               period_amount__gt=0)
                plan = queryset[random.randint(0, queryset.count() - 1)]
                created = False
                trials = 0
                while not created:
                    try:
                        first_name = self.FIRST_NAMES[random.randint(
                            0,
                            len(self.FIRST_NAMES) - 1)]
                        last_name = self.LAST_NAMES[random.randint(
                            0,
                            len(self.LAST_NAMES) - 1)]
                        full_name = '%s %s' % (first_name, last_name)
                        slug = slugify('demo%d' % random.randint(1, 1000))
                        customer, created = Organization.objects.get_or_create(
                            slug=slug, full_name=full_name)
                    #pylint: disable=catching-non-exception
                    except IntegrityError:
                        trials = trials + 1
                        if trials > 10:
                            raise RuntimeError(
                                'impossible to create a new customer after 10 trials.'
                            )
                Organization.objects.filter(pk=customer.id).update(
                    created_at=end_period)
                subscription = Subscription.objects.create(
                    organization=customer,
                    plan=plan,
                    ends_at=now + datetime.timedelta(days=31))
                Subscription.objects.filter(pk=subscription.id).update(
                    created_at=end_period)
            # Insert some churn in %
            churn_rate = 2
            all_subscriptions = Subscription.objects.filter(
                plan__organization=provider)
            nb_churn_customers = (all_subscriptions.count() * churn_rate //
                                  100)
            subscriptions = random.sample(
                list(all_subscriptions),
                all_subscriptions.count() - nb_churn_customers)
            for subscription in subscriptions:
                nb_periods = random.randint(1, 6)
                transaction_item = Transaction.objects.new_subscription_order(
                    subscription,
                    nb_natural_periods=nb_periods,
                    created_at=end_period)
                if transaction_item.dest_amount < 50:
                    continue
                transaction_item.orig_amount = transaction_item.dest_amount
                transaction_item.orig_unit = transaction_item.dest_unit
                transaction_item.save()
                charge = Charge.objects.create(
                    created_at=transaction_item.created_at,
                    amount=transaction_item.dest_amount,
                    customer=subscription.organization,
                    description='Charge for %d periods' % nb_periods,
                    last4=1241,
                    exp_date=datetime_or_now(),
                    processor=processor,
                    processor_key=transaction_item.pk,
                    # XXX We can't do that yet because of
                    # ``processor_backend.charge_distribution(self)``
                    #                    unit=transaction_item.dest_unit,
                    state=Charge.CREATED)
                charge.created_at = transaction_item.created_at
                charge.save()
                ChargeItem.objects.create(invoiced=transaction_item,
                                          charge=charge)
                charge.payment_successful()
            churned = all_subscriptions.exclude(
                pk__in=[subscription.pk for subscription in subscriptions])
            for subscription in churned:
                subscription.ends_at = end_period
                subscription.save()
            self.stdout.write(
                "%d new and %d churned customers at %s\n" %
                (nb_new_customers, nb_churn_customers, end_period))
    def handle(self, *args, **options):
        #pylint: disable=too-many-locals,too-many-statements
        from saas.managers.metrics import month_periods # avoid import loop
        from saas.models import (Charge, ChargeItem, Organization, Plan,
            Subscription)

        now = datetime.datetime.utcnow().replace(tzinfo=utc)
        from_date = now
        from_date = datetime.datetime(
            year=from_date.year, month=from_date.month, day=1)
        if len(args) > 0:
            from_date = datetime.datetime.strptime(
                args[0], '%Y-%m-%d')
        # Create Income transactions that represents a growing bussiness.
        provider = Organization.objects.get(pk=2)
        processor = Organization.objects.get(pk=PROCESSOR_ID)
        for end_period in month_periods(from_date=from_date):
            nb_new_customers = random.randint(0, 9)
            for _ in range(nb_new_customers):
                queryset = Plan.objects.filter(
                    organization=provider, period_amount__gt=0)
                plan = queryset[random.randint(0, queryset.count() - 1)]
                created = False
                trials = 0
                while not created:
                    try:
                        first_name = self.FIRST_NAMES[random.randint(
                            0, len(self.FIRST_NAMES)-1)]
                        last_name = self.LAST_NAMES[random.randint(
                            0, len(self.LAST_NAMES)-1)]
                        full_name = '%s %s' % (first_name, last_name)
                        slug = slugify('demo%d' % random.randint(1, 1000))
                        customer, created = Organization.objects.get_or_create(
                                slug=slug, full_name=full_name)
                    #pylint: disable=catching-non-exception
                    except IntegrityError:
                        trials = trials + 1
                        if trials > 10:
                            raise RuntimeError(
                         'impossible to create a new customer after 10 trials.')
                Organization.objects.filter(pk=customer.id).update(
                    created_at=end_period)
                subscription = Subscription.objects.new_instance(
                    customer, plan, ends_at=now + datetime.timedelta(days=31))
                subscription.save()
                Subscription.objects.filter(
                    pk=subscription.id).update(created_at=end_period)
            # Insert some churn in %
            churn_rate = 2
            all_subscriptions = Subscription.objects.filter(
                plan__organization=provider)
            nb_churn_customers = (all_subscriptions.count()
                * churn_rate / 100)
            subscriptions = random.sample(all_subscriptions,
                all_subscriptions.count() - nb_churn_customers)
            for subscription in subscriptions:
                nb_periods = random.randint(1, 6)
                transaction_item = Transaction.objects.new_subscription_order(
                    subscription, nb_natural_periods=nb_periods,
                    created_at=end_period)
                transaction_item.orig_amount = transaction_item.dest_amount
                transaction_item.orig_unit = transaction_item.dest_unit
                transaction_item.save()
                charge = Charge.objects.create(
                    created_at=transaction_item.created_at,
                    amount=transaction_item.dest_amount,
                    customer=subscription.organization,
                    description='Charge for %d periods' % nb_periods,
                    last4=1241,
                    exp_date=datetime_or_now(),
                    processor=processor,
                    processor_key=transaction_item.pk,
# XXX We can't do that yet because of
# ``PROCESSOR_BACKEND.charge_distribution(self)``
#                    unit=transaction_item.dest_unit,
                    state=Charge.CREATED)
                charge.created_at = transaction_item.created_at
                charge.save()
                ChargeItem.objects.create(
                    invoiced=transaction_item, charge=charge)
                charge.payment_successful()
            churned = all_subscriptions.exclude(
                pk__in=[subscription.pk for subscription in subscriptions])
            for subscription in churned:
                subscription.ends_at = end_period
                subscription.save()
            print "%d new and %d churned customers at %s" % (
                nb_new_customers, nb_churn_customers, end_period)
Esempio n. 9
0
 def generate_transactions(self, provider, processor, from_date, ends_at):
     """
     Create Income transactions that represents a growing bussiness.
     """
     #pylint: disable=too-many-locals
     from saas.managers.metrics import month_periods  # avoid import loop
     for end_period in month_periods(from_date=from_date):
         nb_new_customers = random.randint(0, 9)
         for _ in range(nb_new_customers):
             queryset = Plan.objects.filter(organization=provider,
                                            period_amount__gt=0)
             plan = queryset[random.randint(0, queryset.count() - 1)]
             created = False
             trials = 0
             while not created:
                 try:
                     first_name = self.FIRST_NAMES[random.randint(
                         0,
                         len(self.FIRST_NAMES) - 1)]
                     last_name = self.LAST_NAMES[random.randint(
                         0,
                         len(self.LAST_NAMES) - 1)]
                     full_name = '%s %s' % (first_name, last_name)
                     slug = slugify('demo%d' % random.randint(1, 1000))
                     customer, created = Organization.objects.get_or_create(
                         slug=slug, full_name=full_name)
                 #pylint: disable=catching-non-exception
                 except IntegrityError:
                     trials = trials + 1
                     if trials > 10:
                         raise RuntimeError(
                             'impossible to create a new customer after 10 trials.'
                         )
             Organization.objects.filter(pk=customer.id).update(
                 created_at=end_period)
             subscription = Subscription.objects.create(
                 organization=customer,
                 plan=plan,
                 ends_at=ends_at + datetime.timedelta(days=31))
             Subscription.objects.filter(pk=subscription.id).update(
                 created_at=end_period)
         # Insert some churn in %
         churn_rate = 2
         all_subscriptions = Subscription.objects.filter(
             plan__organization=provider)
         nb_churn_customers = (all_subscriptions.count() * churn_rate //
                               100)
         subscriptions = random.sample(
             list(all_subscriptions),
             all_subscriptions.count() - nb_churn_customers)
         for subscription in subscriptions:
             nb_periods = random.randint(1, 6)
             subscription.ends_at = subscription.plan.end_of_period(
                 subscription.ends_at, nb_periods=nb_periods)
             transaction_item = Transaction.objects.new_subscription_order(
                 subscription,
                 amount=subscription.plan.period_amount * nb_periods,
                 descr=humanize.describe_buy_periods(
                     subscription.plan, subscription.ends_at, nb_periods),
                 created_at=end_period)
             if transaction_item.dest_amount < 50:
                 continue
             subscription.save()
             transaction_item.orig_amount = transaction_item.dest_amount
             transaction_item.orig_unit = transaction_item.dest_unit
             transaction_item.save()
             charge = Charge.objects.create(
                 created_at=transaction_item.created_at,
                 amount=transaction_item.dest_amount,
                 customer=subscription.organization,
                 description='Charge for %d periods' % nb_periods,
                 last4=1241,
                 exp_date=datetime_or_now(),
                 processor=processor,
                 processor_key=transaction_item.pk,
                 # XXX We can't do that yet because of
                 # ``processor_backend.charge_distribution(self)``
                 #                    unit=transaction_item.dest_unit,
                 state=Charge.CREATED)
             charge.created_at = transaction_item.created_at
             charge.save()
             ChargeItem.objects.create(invoiced=transaction_item,
                                       charge=charge)
             charge.payment_successful()
         churned = all_subscriptions.exclude(
             pk__in=[subscription.pk for subscription in subscriptions])
         for subscription in churned:
             subscription.ends_at = end_period
             subscription.save()
         self.stdout.write(
             "%d new and %d churned customers at %s\n" %
             (nb_new_customers, nb_churn_customers, end_period))
Esempio n. 10
0
 def get_headings(self):
     return ['name'] + [
         end_period for end_period in month_periods(from_date=self.ends_at)]
Esempio n. 11
0
 def get_headings(self):
     return ['name'] + [
         end_period for end_period in month_periods(from_date=self.ends_at)]
Esempio n. 12
0
    def generate_transactions(self, provider, processor, from_date, ends_at,
                              fake=None, profile_pictures_dir=None):
        """
        Create Income transactions that represents a growing bussiness.
        """
        #pylint: disable=too-many-locals
        from saas.managers.metrics import month_periods # avoid import loop
        if not fake:
            fake = Faker()
        user_model = get_user_model()
        # Load list of profile pcitures
        profile_pictures_males = []
        profile_pictures_females = []
        if profile_pictures_dir:
            for picture_name in os.listdir(profile_pictures_dir):
                if picture_name.startswith("1"):
                    profile_pictures_males += [
                        "/media/livedemo/profiles/%s" % picture_name]
                else:
                    profile_pictures_females += [
                        "/media/livedemo/profiles/%s" % picture_name]
        for end_period in month_periods(from_date=from_date):
            nb_new_customers = random.randint(0, 9)
            for _ in range(nb_new_customers):
                queryset = Plan.objects.filter(
                    organization=provider, period_amount__gt=0)
                plan = queryset[random.randint(0, queryset.count() - 1)]
                created = False
                trials = 0
                while not created:
                    try:
                        picture = None
                        if random.randint(0, 1):
                            full_name = fake.name_male()
                            if profile_pictures_males:
                                picture = profile_pictures_males[
                                    random.randint(
                                        0, len(profile_pictures_males) - 1)]
                        else:
                            full_name = fake.name_female()
                            if profile_pictures_females:
                                picture = profile_pictures_females[
                                    random.randint(
                                        0, len(profile_pictures_females) - 1)]
                        slug = slugify('demo%d' % random.randint(1, 1000))
                        email = "%s@%s" % (slug, fake.domain_name())
                        first_name, mid_name, last_name = \
                            full_name_natural_split(full_name)
                        customer, created = Organization.objects.get_or_create(
                            slug=slug,
                            full_name=full_name,
                            email=email,
                            phone=fake.phone_number(),
                            street_address=fake.street_address(),
                            locality=fake.city(),
                            postal_code=fake.postcode(),
                            region=fake.state_abbr(),
                            country=fake.country_code(),
                            picture=picture)
                        user, created = user_model.objects.get_or_create(
                            username=slug,
                            email=email,
                            first_name=first_name,
                            last_name=last_name)
                        customer.add_manager(user, at_time=end_period)
                    #pylint: disable=catching-non-exception
                    except IntegrityError:
                        trials = trials + 1
                        if trials > 10:
                            raise RuntimeError(
                         'impossible to create a new customer after 10 trials.')
                Organization.objects.filter(pk=customer.id).update(
                    created_at=end_period)
                subscription = Subscription.objects.create(
                    organization=customer, plan=plan,
                    ends_at=ends_at + datetime.timedelta(days=31))
                Subscription.objects.filter(
                    pk=subscription.id).update(created_at=end_period)
            # Insert some churn in %
            churn_rate = 2
            all_subscriptions = Subscription.objects.filter(
                plan__organization=provider)
            nb_churn_customers = (all_subscriptions.count()
                * churn_rate // 100)
            subscriptions = random.sample(list(all_subscriptions),
                all_subscriptions.count() - nb_churn_customers)
            for subscription in subscriptions:
                nb_periods = random.randint(1, 6)
                subscription.ends_at = subscription.plan.end_of_period(
                    subscription.ends_at,
                    nb_periods=nb_periods)
                transaction_item = Transaction.objects.new_subscription_order(
                    subscription,
                    amount=subscription.plan.period_amount * nb_periods,
                    descr=humanize.describe_buy_periods(
                        subscription.plan, subscription.ends_at, nb_periods),
                    created_at=end_period)
                if transaction_item.dest_amount < 50:
                    continue
                subscription.save()
                transaction_item.orig_amount = transaction_item.dest_amount
                transaction_item.orig_unit = transaction_item.dest_unit
                transaction_item.save()
                charge = Charge.objects.create(
                    created_at=transaction_item.created_at,
                    amount=transaction_item.dest_amount,
                    customer=subscription.organization,
                    description=humanize.DESCRIBE_CHARGED_CARD % {
                        'charge': generate_random_slug(prefix='ch_'),
                        'organization': subscription.organization
                    },
                    last4=1241,
                    exp_date=datetime_or_now(),
                    processor=processor,
                    processor_key=transaction_item.pk,
# XXX We can't do that yet because of
# ``processor_backend.charge_distribution(self)``
#                    unit=transaction_item.dest_unit,
                    state=Charge.CREATED)
                charge.created_at = transaction_item.created_at
                charge.save()
                ChargeItem.objects.create(
                    invoiced=transaction_item, charge=charge)
                charge.payment_successful()
            churned = all_subscriptions.exclude(
                pk__in=[subscription.pk for subscription in subscriptions])
            for subscription in churned:
                subscription.ends_at = end_period
                subscription.save()
            self.stdout.write("%d new and %d churned customers at %s\n" % (
                nb_new_customers, nb_churn_customers, end_period))
    def handle(self, *args, **options):
        #pylint: disable=too-many-locals,too-many-statements
        from saas.managers.metrics import month_periods  # avoid import loop

        RazorpayBackend.bypass_api = True

        now = datetime.datetime.utcnow().replace(tzinfo=utc)
        from_date = now
        from_date = datetime.datetime(year=from_date.year,
                                      month=from_date.month,
                                      day=1)
        if args:
            from_date = datetime.datetime.strptime(args[0], '%Y-%m-%d')
        # Create a set of 3 plans
        broker = get_broker()
        plan, _ = Plan.objects.get_or_create(slug='basic',
                                             defaults={
                                                 'title': "Basic",
                                                 'description': "Basic Plan",
                                                 'period_amount': 24900,
                                                 'broker_fee_percent': 0,
                                                 'period_type': 4,
                                                 'organization': broker,
                                                 'is_active': True
                                             })
        advance_discount = AdvanceDiscount.objects.get_or_create(
            plan=plan,
            discount_type=AdvanceDiscount.PERCENTAGE,
            amount=1000,
            length=12)
        Plan.objects.get_or_create(slug='medium',
                                   defaults={
                                       'title': "Medium",
                                       'description': "Medium Plan",
                                       'period_amount': 24900,
                                       'broker_fee_percent': 0,
                                       'period_type': 4,
                                       'organization': broker,
                                       'is_active': True
                                   })
        plan, _ = Plan.objects.get_or_create(slug='premium',
                                             defaults={
                                                 'title': "Premium",
                                                 'description': "Premium Plan",
                                                 'period_amount': 18900,
                                                 'broker_fee_percent': 0,
                                                 'period_type': 4,
                                                 'organization': broker,
                                                 'is_active': True
                                             })
        advance_discount = AdvanceDiscount.objects.get_or_create(
            plan=plan,
            discount_type=AdvanceDiscount.PERCENTAGE,
            amount=81,
            length=12)
        # Create Income transactions that represents a growing bussiness.
        provider = Organization.objects.get(slug=options['provider'])
        processor = Organization.objects.get(pk=PROCESSOR_ID)
        for end_period in month_periods(from_date=from_date):
            nb_new_customers = random.randint(0, 9)
            for _ in range(nb_new_customers):
                queryset = Plan.objects.filter(organization=provider,
                                               period_amount__gt=0)
                plan = queryset[random.randint(0, queryset.count() - 1)]
                created = False
                trials = 0
                while not created:
                    try:
                        first_name = self.FIRST_NAMES[random.randint(
                            0,
                            len(self.FIRST_NAMES) - 1)]
                        last_name = self.LAST_NAMES[random.randint(
                            0,
                            len(self.LAST_NAMES) - 1)]
                        full_name = '%s %s' % (first_name, last_name)
                        slug = slugify('demo%d' % random.randint(1, 1000))
                        customer, created = Organization.objects.get_or_create(
                            slug=slug, full_name=full_name)
                    #pylint: disable=catching-non-exception
                    except IntegrityError:
                        trials = trials + 1
                        if trials > 10:
                            raise RuntimeError(
                                'impossible to create a new customer after 10 trials.'
                            )
                Organization.objects.filter(pk=customer.id).update(
                    created_at=end_period)
                subscription = Subscription.objects.create(
                    organization=customer,
                    plan=plan,
                    ends_at=now + datetime.timedelta(days=31))
                Subscription.objects.filter(pk=subscription.id).update(
                    created_at=end_period)
            # Insert some churn in %
            churn_rate = 2
            all_subscriptions = Subscription.objects.filter(
                plan__organization=provider)
            nb_churn_customers = (all_subscriptions.count() * churn_rate //
                                  100)
            subscriptions = random.sample(
                list(all_subscriptions),
                all_subscriptions.count() - nb_churn_customers)
            for subscription in subscriptions:
                nb_periods = random.randint(1, 6)
                amount = nb_periods * subscription.plan.period_amount
                ends_at = subscription.plan.end_of_period(
                    subscription.ends_at, nb_periods)
                transaction_item = Transaction.objects.new_subscription_order(
                    subscription,
                    amount=amount,
                    descr=humanize.describe_buy_periods(
                        subscription.plan, ends_at, nb_periods),
                    created_at=end_period)
                if transaction_item.dest_amount < 50:
                    continue
                transaction_item.orig_amount = transaction_item.dest_amount
                transaction_item.orig_unit = transaction_item.dest_unit
                transaction_item.save()
                charge = Charge.objects.create(
                    created_at=transaction_item.created_at,
                    amount=transaction_item.dest_amount,
                    customer=subscription.organization,
                    description='Charge for %d periods' % nb_periods,
                    last4=1241,
                    exp_date=datetime_or_now(),
                    processor=processor,
                    processor_key=str(transaction_item.pk),
                    # XXX We can't do that yet because of
                    # ``PROCESSOR_BACKEND.charge_distribution(self)``
                    #                    unit=transaction_item.dest_unit,
                    state=Charge.CREATED)
                charge.created_at = transaction_item.created_at
                charge.save()
                ChargeItem.objects.create(invoiced=transaction_item,
                                          charge=charge)
                charge.payment_successful()
            churned = all_subscriptions.exclude(
                pk__in=[subscription.pk for subscription in subscriptions])
            for subscription in churned:
                subscription.ends_at = end_period
                subscription.save()
            self.stdout.write(
                "%d new and %d churned customers at %s" %
                (nb_new_customers, nb_churn_customers, end_period))