Skip to content

Commit 0608209

Browse files
mkp6781neiljp
authored andcommitted
api_types/model/boxes/views: Use 24-hour time preferences from server.
Initial time format preferences are fetched during the initial register call. An event handler enables update of this setting as events are received from the server. Tests added & updated. Fixes #770. Minor test updates by neiljp.
1 parent 54d8fac commit 0608209

File tree

6 files changed

+64
-4
lines changed

6 files changed

+64
-4
lines changed

tests/conftest.py

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -539,6 +539,7 @@ def initial_data(logged_on_user, users_fixture, streams_fixture):
539539
}
540540
}
541541
},
542+
'twenty_four_hour_time': True,
542543
'last_event_id': -1,
543544
'muted_topics': [],
544545
'realm_user_groups': [],

tests/model/test_model.py

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -91,6 +91,8 @@ def test_init(self, model, initial_data, user_profile,
9191
assert model.active_emoji_data['joker']['type'] == 'realm_emoji'
9292
# zulip_extra_emoji replaces all other emoji types for 'zulip' emoji.
9393
assert model.active_emoji_data['zulip']['type'] == 'zulip_extra_emoji'
94+
assert (model.twenty_four_hr_format
95+
== initial_data['twenty_four_hour_time'])
9496

9597
@pytest.mark.parametrize(['server_response', 'locally_processed_data',
9698
'zulip_feature_level'], [
@@ -179,6 +181,7 @@ def test_register_initial_desired_events(self, mocker, initial_data):
179181
'subscription',
180182
'typing',
181183
'update_message_flags',
184+
'update_display_settings',
182185
]
183186
fetch_event_types = [
184187
'realm',
@@ -189,6 +192,7 @@ def test_register_initial_desired_events(self, mocker, initial_data):
189192
'muted_topics',
190193
'realm_user',
191194
'realm_user_groups',
195+
'update_display_settings',
192196
'zulip_version',
193197
]
194198
model.client.register.assert_called_once_with(
@@ -1940,6 +1944,30 @@ def test__handle_subscription_event_subscribers_one_user_multiple_streams(
19401944
new_subscribers = model.stream_dict[stream_id]['subscribers']
19411945
assert new_subscribers == expected_subscribers
19421946

1947+
@pytest.mark.parametrize('setting', [True, False])
1948+
def test_update_twenty_four_hour_format(self, mocker, model, setting):
1949+
event = {
1950+
'type': 'update_display_settings',
1951+
'setting_name': 'twenty_four_hour_time',
1952+
'setting': setting,
1953+
}
1954+
first_msg_w = mocker.Mock()
1955+
second_msg_w = mocker.Mock()
1956+
first_msg_w.original_widget.message = {'id': 1}
1957+
second_msg_w.original_widget.message = {'id': 2}
1958+
self.controller.view.message_view = mocker.Mock(
1959+
log=[first_msg_w, second_msg_w])
1960+
create_msg_box_list = mocker.patch('zulipterminal.model.'
1961+
'create_msg_box_list')
1962+
model.twenty_four_hr_format = None # initial value is not True/False
1963+
1964+
model._handle_update_display_settings_event(event)
1965+
1966+
assert model.twenty_four_hr_format == event['setting']
1967+
assert create_msg_box_list.call_count == len(
1968+
self.controller.view.message_view.log)
1969+
assert model.controller.update_screen.called
1970+
19431971
@pytest.mark.parametrize('muted_streams, stream_id, is_muted', [
19441972
({1}, 1, True),
19451973
({1}, 2, False),

zulipterminal/api_types.py

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -106,11 +106,18 @@ class UpdateMessageFlagsEvent(TypedDict):
106106
all: bool
107107

108108

109+
class UpdateDisplaySettings(TypedDict):
110+
type: Literal['update_display_settings']
111+
setting_name: str
112+
setting: bool
113+
114+
109115
Event = Union[
110116
MessageEvent,
111117
UpdateMessageEvent,
112118
ReactionEvent,
113119
SubscriptionEvent,
114120
TypingEvent,
115121
UpdateMessageFlagsEvent,
122+
UpdateDisplaySettings,
116123
]

zulipterminal/model.py

Lines changed: 25 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -96,6 +96,8 @@ def __init__(self, controller: Any) -> None:
9696
('typing', self._handle_typing_event),
9797
('update_message_flags',
9898
self._handle_update_message_flags_event),
99+
('update_display_settings',
100+
self._handle_update_display_settings_event),
99101
])
100102
)
101103

@@ -149,6 +151,7 @@ def __init__(self, controller: Any) -> None:
149151
self.active_emoji_data = OrderedDict(sorted(all_emoji_data,
150152
key=lambda e: e[0]))
151153

154+
self.twenty_four_hr_format = self.initial_data['twenty_four_hour_time']
152155
self.new_user_input = True
153156
self._start_presence_updates()
154157

@@ -1170,8 +1173,10 @@ def formatted_local_time(
11701173
format_codes = (
11711174
"%a %b %d "
11721175
f"{'%Y ' if show_year else ''}"
1173-
"%H:%M"
1176+
f"{'%H:' if self.twenty_four_hr_format else '%I:'}"
1177+
"%M"
11741178
f"{':%S' if show_seconds else ''}"
1179+
f"{'' if self.twenty_four_hr_format else ' %p'}"
11751180
)
11761181
return local_time.strftime(format_codes)
11771182

@@ -1222,6 +1227,24 @@ def _update_rendered_view(self, msg_id: int) -> None:
12221227
self.controller.update_screen()
12231228
return
12241229

1230+
def _handle_update_display_settings_event(self, event: Event) -> None:
1231+
"""
1232+
Handle change to user display setting (Eg: Time format)
1233+
"""
1234+
assert event['type'] == "update_display_settings"
1235+
view = self.controller.view
1236+
if event['setting_name'] == 'twenty_four_hour_time':
1237+
self.twenty_four_hr_format = event['setting']
1238+
for msg_w in view.message_view.log:
1239+
msg_box = msg_w.original_widget
1240+
msg_id = msg_box.message['id']
1241+
last_msg = msg_box.last_message
1242+
msg_pos = view.message_view.log.index(msg_w)
1243+
msg_w_list = create_msg_box_list(self, [msg_id],
1244+
last_message=last_msg)
1245+
view.message_view.log[msg_pos] = msg_w_list[0]
1246+
self.controller.update_screen()
1247+
12251248
def _register_desired_events(self, *, fetch_data: bool=False) -> str:
12261249
fetch_types = None if not fetch_data else [
12271250
'realm',
@@ -1232,6 +1255,7 @@ def _register_desired_events(self, *, fetch_data: bool=False) -> str:
12321255
'muted_topics',
12331256
'realm_user', # Enables cross_realm_bots
12341257
'realm_user_groups',
1258+
'update_display_settings',
12351259
# zulip_version and zulip_feature_level are always returned in
12361260
# POST /register from Feature level 3.
12371261
'zulip_version',

zulipterminal/ui_tools/boxes.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1204,7 +1204,7 @@ def main_view(self) -> List[Any]:
12041204

12051205
content_header = urwid.Columns([
12061206
('weight', 10, urwid.Text(text['author'])),
1207-
(23, urwid.Text(text['time'], align='right')),
1207+
(26, urwid.Text(text['time'], align='right')),
12081208
(1, urwid.Text(text['star'], align='right')),
12091209
], dividechars=1)
12101210
else:

zulipterminal/ui_tools/views.py

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1392,8 +1392,8 @@ def _make_edit_block(self, snapshot: Dict[str, Any],
13921392
]
13931393
subheader = [
13941394
urwid.Text(('edit_author', author)),
1395-
# 19 = len(timestamp).
1396-
(19, urwid.Text(('edit_time', date_and_time), align='right')),
1395+
# 22 = len(timestamp).
1396+
(22, urwid.Text(('edit_time', date_and_time), align='right')),
13971397
]
13981398

13991399
edit_block = [

0 commit comments

Comments
 (0)