analytics: Change Number of Users chart to use realm_active_humans::day.

Previously we showed the total number of users with an active account. This
changes it to show only the number of users that have logged in in the past
two weeks.
This commit is contained in:
Rishi Gupta 2017-04-25 14:54:30 -07:00 committed by Tim Abbott
parent b43385ec34
commit f595f4f7f2
3 changed files with 21 additions and 22 deletions

View File

@ -37,15 +37,15 @@ class Command(BaseCommand):
return user
def generate_fixture_data(self, stat, business_hours_base, non_business_hours_base,
growth, autocorrelation, spikiness, holiday_rate=0):
# type: (CountStat, float, float, float, float, float, float) -> List[int]
growth, autocorrelation, spikiness, holiday_rate=0,
partial_sum=False):
# type: (CountStat, float, float, float, float, float, float, bool) -> List[int]
self.random_seed += 1
return generate_time_series_data(
days=self.DAYS_OF_DATA, business_hours_base=business_hours_base,
non_business_hours_base=non_business_hours_base, growth=growth,
autocorrelation=autocorrelation, spikiness=spikiness, holiday_rate=holiday_rate,
frequency=stat.frequency, partial_sum=(stat.interval > timedelta(days=1000)),
random_seed=self.random_seed)
frequency=stat.frequency, partial_sum=partial_sum, random_seed=self.random_seed)
def handle(self, *args, **options):
# type: (*Any, **Any) -> None
@ -73,10 +73,9 @@ class Command(BaseCommand):
value=value, **id_args)
for end_time, value in zip(end_times, values) if value != 0])
stat = COUNT_STATS['active_users:is_bot:day']
stat = COUNT_STATS['realm_active_humans::day']
realm_data = {
'false': self.generate_fixture_data(stat, .1, .03, 3, .5, 3),
'true': self.generate_fixture_data(stat, .01, 0, 1, 0, 1)
None: self.generate_fixture_data(stat, .1, .03, 3, .5, 3, partial_sum=True),
} # type: Dict[Optional[str], List[int]]
insert_fixture_data(stat, realm_data, RealmCount)
FillState.objects.create(property=stat.property, end_time=last_end_time,

View File

@ -67,8 +67,8 @@ class TestGetChartData(ZulipTestCase):
def test_number_of_humans(self):
# type: () -> None
stat = COUNT_STATS['active_users:is_bot:day']
self.insert_data(stat, ['true', 'false'], [])
stat = COUNT_STATS['realm_active_humans::day']
self.insert_data(stat, [None], [])
result = self.client_get('/json/analytics/chart_data',
{'chart_name': 'number_of_humans'})
self.assert_json_success(result)
@ -77,7 +77,7 @@ class TestGetChartData(ZulipTestCase):
'msg': '',
'end_times': [datetime_to_timestamp(dt) for dt in self.end_times_day],
'frequency': CountStat.DAY,
'realm': {'bot': self.data(100), 'human': self.data(101)},
'realm': {'human': self.data(100)},
'display_order': None,
'result': 'success',
})
@ -148,12 +148,12 @@ class TestGetChartData(ZulipTestCase):
def test_include_empty_subgroups(self):
# type: () -> None
FillState.objects.create(
property='active_users:is_bot:day', end_time=self.end_times_day[0], state=FillState.DONE)
property='realm_active_humans::day', end_time=self.end_times_day[0], state=FillState.DONE)
result = self.client_get('/json/analytics/chart_data',
{'chart_name': 'number_of_humans'})
self.assert_json_success(result)
data = ujson.loads(result.content)
self.assertEqual(data['realm'], {'human': [0], 'bot': [0]})
self.assertEqual(data['realm'], {'human': [0]})
self.assertFalse('user' in data)
FillState.objects.create(
@ -187,8 +187,8 @@ class TestGetChartData(ZulipTestCase):
def test_start_and_end(self):
# type: () -> None
stat = COUNT_STATS['active_users:is_bot:day']
self.insert_data(stat, ['true', 'false'], [])
stat = COUNT_STATS['realm_active_humans::day']
self.insert_data(stat, [None], [])
end_time_timestamps = [datetime_to_timestamp(dt) for dt in self.end_times_day]
# valid start and end
@ -199,7 +199,7 @@ class TestGetChartData(ZulipTestCase):
self.assert_json_success(result)
data = ujson.loads(result.content)
self.assertEqual(data['end_times'], end_time_timestamps[1:3])
self.assertEqual(data['realm'], {'bot': [0, 100], 'human': [0, 101]})
self.assertEqual(data['realm'], {'human': [0, 100]})
# start later then end
result = self.client_get('/json/analytics/chart_data',
@ -210,8 +210,8 @@ class TestGetChartData(ZulipTestCase):
def test_min_length(self):
# type: () -> None
stat = COUNT_STATS['active_users:is_bot:day']
self.insert_data(stat, ['true', 'false'], [])
stat = COUNT_STATS['realm_active_humans::day']
self.insert_data(stat, [None], [])
# test min_length is too short to change anything
result = self.client_get('/json/analytics/chart_data',
{'chart_name': 'number_of_humans',
@ -219,7 +219,7 @@ class TestGetChartData(ZulipTestCase):
self.assert_json_success(result)
data = ujson.loads(result.content)
self.assertEqual(data['end_times'], [datetime_to_timestamp(dt) for dt in self.end_times_day])
self.assertEqual(data['realm'], {'bot': self.data(100), 'human': self.data(101)})
self.assertEqual(data['realm'], {'human': self.data(100)})
# test min_length larger than filled data
result = self.client_get('/json/analytics/chart_data',
{'chart_name': 'number_of_humans',
@ -228,7 +228,7 @@ class TestGetChartData(ZulipTestCase):
data = ujson.loads(result.content)
end_times = [ceiling_to_day(self.realm.date_created) + timedelta(days=i) for i in range(-1, 4)]
self.assertEqual(data['end_times'], [datetime_to_timestamp(dt) for dt in end_times])
self.assertEqual(data['realm'], {'bot': [0]+self.data(100), 'human': [0]+self.data(101)})
self.assertEqual(data['realm'], {'human': [0]+self.data(100)})
def test_non_existent_chart(self):
# type: () -> None

View File

@ -52,9 +52,9 @@ def get_chart_data(request, user_profile, chart_name=REQ(),
end=REQ(converter=to_utc_datetime, default=None)):
# type: (HttpRequest, UserProfile, Text, Optional[int], Optional[datetime], Optional[datetime]) -> HttpResponse
if chart_name == 'number_of_humans':
stat = COUNT_STATS['active_users:is_bot:day']
stat = COUNT_STATS['realm_active_humans::day']
tables = [RealmCount]
subgroup_to_label = {'false': 'human', 'true': 'bot'}
subgroup_to_label = {None: 'human'} # type: Dict[Optional[str], str]
labels_sort_function = None
include_empty_subgroups = True
elif chart_name == 'messages_sent_over_time':
@ -185,7 +185,7 @@ def rewrite_client_arrays(value_arrays):
return mapped_arrays
def get_time_series_by_subgroup(stat, table, key_id, end_times, subgroup_to_label, include_empty_subgroups):
# type: (CountStat, Type[BaseCount], Optional[int], List[datetime], Dict[str, str], bool) -> Dict[str, List[int]]
# type: (CountStat, Type[BaseCount], Optional[int], List[datetime], Dict[Optional[str], str], bool) -> Dict[str, List[int]]
queryset = table_filtered_to_id(table, key_id).filter(property=stat.property) \
.values_list('subgroup', 'end_time', 'value')
value_dicts = defaultdict(lambda: defaultdict(int)) # type: Dict[Optional[str], Dict[datetime, int]]