def _downgrades_plus_churn_count(start, end): bucket_func = attrgetter(request.args.get('bucketed', 'quarter')) downgrade = query_downgrades(start, end) tb_downgrades = bucket_func(Timebucket(downgrade, 'updated'))() churn = query_lostbiz(start, end) tb_churn = bucket_func(Timebucket(churn, 'updated'))() bucketed_lists = OrderedDict(( ('churn', tb_churn), ('downgrade', tb_downgrades), )) def counts(alist): return sum(1 for entry in alist) # Make all bucketed list contain a single value summation of their rate change for bl in bucketed_lists.values(): bl.period_map(counts) # Zero out any bucketed timeperiod that does not have a key that the other bucketed periods do pset = BucketedList.period_set(*(bucketed_lists.values())) map(lambda bl: bl.fill_missing_periods(pset), bucketed_lists.values()) series = [] for name, bl in bucketed_lists.items(): series.append({ 'key': name, 'values': [(key, bl[key]) for key in sorted(bl)], }) return series
def _paid_account_count(start, end): bucket_func = attrgetter(request.args.get('bucketed', 'quarter')) std = query_std_count(start, end) tb_std = bucket_func(Timebucket(std, 'updated'))() pro = query_pro_count(start, end) tb_pro = bucket_func(Timebucket(pro, 'updated'))() bucketed_lists = OrderedDict(( ('standard', tb_std), ('pro', tb_pro), )) def counts(alist): return sum(1 for entry in alist) # Make all bucketed list contain a single value summation of their rate change for bl in bucketed_lists.values(): bl.period_map(counts) # Zero out any bucketed timeperiod that does not have a key that the other bucketed periods do pset = BucketedList.period_set(*(bucketed_lists.values())) map(lambda bl: bl.fill_missing_periods(pset), bucketed_lists.values()) series = [] for name, bl in bucketed_lists.items(): series.append({ 'key': name, 'values': [(key, bl[key]) for key in sorted(bl)], }) return series
def _new_biz_plus_upsell(start, end): bucket_func = attrgetter(request.args.get('bucketed', 'quarter')) newbiz = query_upsell(start, end) sum_newbiz = bucket_func(Timebucket(newbiz, 'updated'))() upsell = query_newbiz(start, end) sum_upsell = bucket_func(Timebucket(upsell, 'updated'))() bucketed_lists = OrderedDict(( ('newbiz', sum_newbiz), ('upsell', sum_upsell), )) # Make all bucketed list contain a single value summation of their rate change for bl in bucketed_lists.values(): bl.period_map(sum_rate_change) # Zero out any bucketed timeperiod that does not have a key that the other bucketed periods do pset = BucketedList.period_set(*(bucketed_lists.values())) map(lambda bl: bl.fill_missing_periods(pset), bucketed_lists.values()) series = [] for name, bl in bucketed_lists.items(): series.append({ 'key': name, 'values': [(key, bl[key]) for key in sorted(bl)], }) return series
def test_week( self ): rows = [ DatedItem( 2, datetime(2014, 6, 9) ), ] bucketer = Timebucket( rows, 'created' ) week = bucketer.week() self.assertEqual( week['2014-W24'], [ DatedItem( 2, datetime( 2014, 6, 9 ) ) ] )
def test_quarter( self ): rows = [ DatedItem( 2, datetime(2014, 6, 9) ), ] bucketer = Timebucket( rows, 'created' ) quartered = bucketer.quarter() self.assertEqual( quartered['2014-Q1'], [] ) self.assertEqual( quartered['2014-Q2'], [ DatedItem( 2, datetime( 2014, 6, 9 ) ) ] ) self.assertEqual( quartered['2014-Q3'], [] ) self.assertEqual( quartered['2014-Q4'], [] ) rows = [ DatedItem( 1, datetime(2014, 2, 12) ), DatedItem( 2, datetime(2014, 6, 9) ), DatedItem( 3, datetime(2014, 8, 10) ), DatedItem( 4, datetime(2014, 12, 31, 23, 59, 59) ), ] bucketer = Timebucket( rows, 'created' ) quartered = bucketer.quarter() self.assertEqual( quartered['2014-Q1'], [ DatedItem( 1, datetime( 2014, 2, 12 ) ) ] ) self.assertEqual( quartered['2014-Q2'], [ DatedItem( 2, datetime( 2014, 6, 9 ) ) ] ) self.assertEqual( quartered['2014-Q3'], [ DatedItem( 3, datetime( 2014, 8, 10 ) ) ] ) self.assertEqual( quartered['2014-Q4'], [ DatedItem( 4, datetime( 2014, 12, 31, 23, 59, 59 ) ) ] ) rows = [ DatedItem( 1, datetime(2010, 8, 12) ), DatedItem( 2, datetime(2012, 1, 1) ), DatedItem( 3, datetime(2012, 3, 31) ), DatedItem( 4, datetime(2014, 12, 31) ), ] bucketer = Timebucket( rows, 'created' ) quartered = bucketer.quarter() self.assertEqual( quartered['2010-Q1'], [] ) self.assertEqual( quartered['2010-Q2'], [] ) self.assertEqual( quartered['2010-Q3'], [ DatedItem( 1, datetime( 2010, 8, 12 ) ) ] ) self.assertEqual( quartered['2010-Q4'], [] ) self.assertEqual( quartered['2011-Q1'], [] ) self.assertEqual( quartered['2011-Q2'], [] ) self.assertEqual( quartered['2011-Q3'], [] ) self.assertEqual( quartered['2011-Q4'], [] ) self.assertEqual( quartered['2012-Q1'], [ DatedItem( 2, datetime( 2012, 1, 1 ) ), DatedItem( 3, datetime( 2012, 3, 31 ) ) ] ) self.assertEqual( quartered['2012-Q2'], [] ) self.assertEqual( quartered['2012-Q3'], [] ) self.assertEqual( quartered['2012-Q4'], [] ) self.assertEqual( quartered['2013-Q1'], [] ) self.assertEqual( quartered['2013-Q2'], [] ) self.assertEqual( quartered['2013-Q3'], [] ) self.assertEqual( quartered['2013-Q4'], [] ) self.assertEqual( quartered['2014-Q1'], [] ) self.assertEqual( quartered['2014-Q2'], [] ) self.assertEqual( quartered['2014-Q3'], [] ) self.assertEqual( quartered['2014-Q4'], [ DatedItem( 4, datetime( 2014, 12, 31 ) ) ] )
def test_month( self ): rows = [ DatedItem( 2, datetime(2014, 6, 9) ), ] bucketer = Timebucket( rows, 'created' ) monthed = bucketer.month() self.assertEqual( monthed['2014-06'], [ DatedItem( 2, datetime( 2014, 6, 9 ) ) ] ) rows = [ DatedItem( 2, datetime(2014, 6, 9) ), DatedItem( 2, datetime(2014, 2, 28) ), ] bucketer = Timebucket( rows, 'created' ) monthed = bucketer.month() self.assertEqual( monthed['2014-02'], [ DatedItem( 2, datetime( 2014, 2, 28 ) ) ] ) self.assertEqual( monthed['2014-03'], [] ) self.assertEqual( monthed['2014-04'], [] ) self.assertEqual( monthed['2014-05'], [] ) self.assertEqual( monthed['2014-06'], [ DatedItem( 2, datetime( 2014, 6, 9 ) ) ] ) rows = [ DatedItem( 1, datetime(2013, 1, 1) ), DatedItem( 2, datetime(2014, 2, 28) ), DatedItem( 3, datetime(2014, 2, 10) ), DatedItem( 4, datetime(2014, 12, 31, 23, 59, 59) ), ] bucketer = Timebucket( rows, 'created' ) monthed = bucketer.month() self.assertEqual( monthed['2013-01'], [ DatedItem( 1, datetime( 2013, 1, 1 ) ) ] ) self.assertEqual( monthed['2013-02'], [] ) self.assertEqual( monthed['2013-03'], [] ) self.assertEqual( monthed['2013-04'], [] ) self.assertEqual( monthed['2013-05'], [] ) self.assertEqual( monthed['2013-06'], [] ) self.assertEqual( monthed['2013-07'], [] ) self.assertEqual( monthed['2013-08'], [] ) self.assertEqual( monthed['2013-09'], [] ) self.assertEqual( monthed['2013-10'], [] ) self.assertEqual( monthed['2013-11'], [] ) self.assertEqual( monthed['2013-12'], [] ) self.assertEqual( monthed['2014-02'], [ DatedItem( 3, datetime( 2014, 2, 10 ) ), DatedItem( 2, datetime( 2014, 2, 28 ) ) ] ) self.assertEqual( monthed['2014-03'], [] ) self.assertEqual( monthed['2014-04'], [] ) self.assertEqual( monthed['2014-05'], [] ) self.assertEqual( monthed['2014-06'], [] ) self.assertEqual( monthed['2014-07'], [] ) self.assertEqual( monthed['2014-08'], [] ) self.assertEqual( monthed['2014-09'], [] ) self.assertEqual( monthed['2014-10'], [] ) self.assertEqual( monthed['2014-11'], [] ) self.assertEqual( monthed['2014-12'], [ DatedItem( 4, datetime( 2014, 12, 31, 23, 59, 59 ) ) ] )
def bucketed(self, bucket): bucket_func = attrgetter(bucket) owners = self.owners for name in owners: owners[name] = bucket_func(Timebucket(owners[name], 'updated'))() return owners
def _product_average_deal_size(start, end): bucket_func = attrgetter(request.args.get('bucketed', 'quarter')) std = query_std(start, end) avg_std = bucket_func(Timebucket(std, 'updated'))() pro = query_pro(start, end) avg_pro = bucket_func(Timebucket(pro, 'updated'))() bucketed_lists = OrderedDict(( ('avg standard', avg_std), ('avg pro', avg_pro), )) # Zero out any bucketed timeperiod that does not have a key that the other bucketed periods do pset = BucketedList.period_set(*(bucketed_lists.values())) map(lambda bl: bl.fill_missing_periods(pset), bucketed_lists.values()) def average(alist): # Make sure that there is at least some kind of positive movement culled_list = [item for item in alist if item.rate_delta > 0] num_items = len(culled_list) if num_items != 0: avg = reduce(lambda acc, val: acc + val.rate_delta, culled_list, 0) / float(num_items) else: avg = 0 return avg # Caluculate the average deal size and mutate each bucket for bl in bucketed_lists.values(): bl.period_map(average) series = [] for name, bl in bucketed_lists.items(): series.append({ 'key': name, 'values': [(key, bl[key]) for key in sorted(bl)], }) return series
def test_year( self ): rows = [ DatedItem( 2, datetime(2014, 6, 9) ), ] bucketer = Timebucket( rows, 'created' ) yearly = bucketer.year() self.assertEqual( yearly['2014'], [ DatedItem( 2, datetime( 2014, 6, 9 ) ) ] ) rows = [ DatedItem( 2, datetime(2014, 6, 9) ), DatedItem( 3, datetime(2014, 12, 31) ), DatedItem( 1, datetime(2014, 1, 1) ), ] bucketer = Timebucket( rows, 'created' ) yearly = bucketer.year() self.assertEqual( yearly['2014'], [ DatedItem( 1, datetime( 2014, 1, 1 ) ), DatedItem( 2, datetime( 2014, 6, 9 ) ), DatedItem( 3, datetime( 2014, 12, 31 ) ) ] ) rows = [ DatedItem( 1, datetime(2010, 6, 9) ), DatedItem( 4, datetime(2014, 12, 31) ), DatedItem( 2, datetime(2012, 12, 31) ), DatedItem( 3, datetime(2014, 1, 1) ), ] bucketer = Timebucket( rows, 'created' ) yearly = bucketer.year() self.assertEqual( yearly['2010'], [ DatedItem( 1, datetime( 2010, 6, 9 ) )] ) self.assertEqual( yearly['2011'], [] ) self.assertEqual( yearly['2012'], [ DatedItem( 2, datetime( 2012, 12, 31 ) )] ) self.assertEqual( yearly['2013'], [] ) self.assertEqual( yearly['2014'], [ DatedItem( 3, datetime( 2014, 1, 1 ) ), DatedItem( 4, datetime( 2014, 12, 31 ) ), ] )
def test_properties( self ): rows = [ DatedItem( 2, datetime(2014, 6, 9) ), DatedItem( 1, datetime(2010, 2, 12) ), DatedItem( 3, datetime(2011, 8, 10) ), DatedItem( 4, datetime(2014, 12, 31) ), ] bucketer = Timebucket( rows, 'created' ) self.assertEqual( bucketer.start, datetime( 2010, 2, 12 ) ) self.assertEqual( bucketer.end, datetime( 2014, 12, 31 ) ) self.assertEqual( bucketer.rows, [ DatedItem( 1, datetime(2010, 2, 12) ), DatedItem( 3, datetime(2011, 8, 10) ), DatedItem( 2, datetime(2014, 6, 9) ), DatedItem( 4, datetime(2014, 12, 31) ) ])
def _net_value(start, end): bucket_func = attrgetter(request.args.get('bucketed', 'quarter')) prev = query_state(['CTP', '%WP', '%WD', '%WU', '%WF'], datetime(2008, 1, 1), start, g2only=True) prev_acc = reduce(lambda pacc, val: pacc + val.rate_delta, prev, 0) value = query_state(['CTP', '%WP', '%WD', '%WU', '%WF'], start, end) net_value = bucket_func(Timebucket(value, 'updated'))() bucketed_lists = OrderedDict((('net value', net_value), )) def accumulated_net(bl, accumulated=0): period_keys = sorted(bl.periods) for period in period_keys: bl[period] = reduce(lambda pacc, val: pacc + val.rate_delta, bl[period], accumulated) accumulated = bl[period] # Mutate the bucketedlist componenets for bl in bucketed_lists.values(): accumulated_net(bl, accumulated=prev_acc) pset = BucketedList.period_set(*(bucketed_lists.values())) map(lambda bl: bl.fill_missing_periods(pset), bucketed_lists.values()) series = [] for name, bl in bucketed_lists.items(): series.append({ 'key': name, 'values': [(key, bl[key]) for key in sorted(bl)], }) return series
def _conversion_rate(start, end): bucket_func = attrgetter(request.args.get('bucketed', 'quarter')) trials = query_state(['SUT'], start, end) bl_trials = bucket_func(Timebucket(trials, 'updated'))() converted = query_state(['TWP', 'FWP'], start, end) bl_converted = bucket_func(Timebucket(converted, 'updated'))() # Segment by Standard/Pro dev_conv = query_product_state(['TWP', 'FWP'], ['development'], start, end) bl_dev_conv = bucket_func(Timebucket(dev_conv, 'updated'))() pro_conv = query_product_state(['TWP', 'FWP'], ['production'], start, end) bl_pro_conv = bucket_func(Timebucket(pro_conv, 'updated'))() bucketed_lists = OrderedDict(( ('trial', bl_trials), ('conversions', bl_converted), ('dev conversion', bl_dev_conv), ('pro conversion', bl_pro_conv), )) pset = BucketedList.period_set(*(bucketed_lists.values())) map(lambda bl: bl.fill_missing_periods(pset), bucketed_lists.values()) def counts(alist): return sum(1 for entry in alist) # Mutate the bucketedlist componenets for bl in bucketed_lists.values(): bl.period_map(counts) series = [] series.append({ 'key': 'trials', 'values': [{ 'x': i, 'y': bl_trials[key] } for i, key in enumerate(sorted(bl_trials))], 'labels': [key for key in sorted(bl)], 'bar': True, }) for name, bl in OrderedDict(bucketed_lists.items()[-3:]).items(): # Calculate the conversion rate for key in bl: if bl_trials[key]: bl[key] = float(bl.get(key, 0)) / bl_trials[key] else: bl[key] = float(bl.get(key, 0)) series.append({ 'key': name, 'values': [{ 'x': i, 'y': bl[key] } for i, key in enumerate(sorted(bl))], 'labels': [key for key in sorted(bl)], }) return series