We start caching MessageListData objects for the narrows which
user has visited. We restore the cached objects if the filters
match. Also, the cached objects are updated based on events. One
major piece is update path the is pending implementation is the
message move code path.
This param allows clients to specify how much presence history they want
to fetch. Previously, the server always returned 14 days of history.
With the recent migration of the presence API to the much more efficient
system relying on incremental fetches via the last_update_id param added
in #29999, we can now afford to provide much more history to clients
that request it - as all that historical data will only be fetched once.
There are three endpoints involved:
- `/register` - this is the main useful endpoint for this, used by API
clients to fetch initial data and register an events queue. Clients can
pass the `presence_history_limit_days` param here.
- `/users/me/presence` - this endpoint is currently used by clients to
update their presence status and fetch incremental data, making the new
functionality not particularly useful here. However, we still add the
new `history_limit_days` param here, in case in the future clients
transition to using this also for the initial presence data fetch.
- `/` - used when opening the webapp. Naturally, params aren't passed
here, so the server just assumes a value from
`settings.PRESENCE_HISTORY_LIMIT_DAYS_FOR_WEB_APP` and returns
information about this default value in page_params.
This commit makes small refactoring to place all the user-privacy
settings code in 'server_events_dispatch.js' at one place and use
a common function 'settings_account.update_privacy_settings_box' to
update the UI.
This also helps in early return instead of executing a lot
of `if` statements related to user-preferences settings.
Previously, on narrowing to a direct message using the `with`
operator, we used to end up at the last message rather than
the last unread message.
This was because while correcting the narrow using the `with`
operand, we used to consider all the users of `display_recipient`.
This would also include the `current_user`. This is not right because
the unread messages for direct messages are bucketed with a
`user_ids_string`, that does not include the user id of the current
user. Hence, when looked up for the last unread id by the `with`
operator, it used to return undefined.
This is fixed by removing the current user's user id from the user ids
string if current user is not the only display recipient to the
direct message.
Previously the empty view banner for DM with any recipients
contained "Why not start the conversation".
For deactivated users/bots, we are now not displaying it.
Earlier when compose box was opened or narrowed to pm, the recipient
pills were sorted according to user email strings instead of their
full names which was inconsistent with compose box placeholder text,
recipient row and message header.
This commit fixes the behaviour by introducing a `sort_email`
function to sort emails according to their full names and display
sorted pills.
Fixes: zulip#27375.
Co-authored-by: richardshaju <richardshaju66@gmail.com>
Earlier in drafts overlay, the order of pm recipients for the draft
was sorted differently to that of the pm group title.
This commit fixes the behaviour by sorting the drafts pm recipients
using `make_strcmp`.
Fixes part of zulip#27375.
Co-authored-by: richardshaju <richardshaju66@gmail.com>
Earlier, when narrowed to a group direct message, the header title
was sorted with respect to its email instead of their names. This
would result in message header and recipient row having different
order of recipients.
This commit fixes the behaviour by changing the order of the names
passed for the group message header using `make_strcmp`.
Fixes part of zulip#27375.
We're going to need to be able to build the message list view
in pieces and put it all together in the end, instead of assigning
values directly to a half-formed object (which is hard to type).
This is part of the work towards that.
This commit adds '*' as a keyboard shortcut to navigate to the starred messages view and the shortcut is documented in various required locations accordingly.
Fixes#31397.
This commit updates code to live update the groups UI if
realm or group level setting to manage groups is changed.
This commit also does some refactoring to better organize the
code in different functions.
And also, the code to hide/disable the UI if the user does not
have permission to manage the group in JS such that the same code
is used for live-updating as well.
Earlier there was only a realm level setting for configuring
who can edit user groups. A new group level setting is also added
for configuring who can manage that particular group.
Now, a user group can be edited by a user if it is allowed from
realm level setting or group level setting.
This commit make changes in frontend to also use group level setting
in determining whether a group can be edited by user or not and disables
changing the group settings when group cannot be edited by user.
Earlier in frontend there was a single function to determine whether
user can create and edit user groups.
This commit adds a separate function for determining group creation
permissions.
This commit make changes in code to include can_manage_group
field to UserGroup objects passed with response of various endpoints
including "/register" endpoint and also in the group object
send with user group creation event.
The message feed can take long enough to render that
users are locked out of clicking things for a second
or so. This has become especially an issue since we
updated the search bar logic to refresh the message
feed as search terms are added to the search bar.
More details on CZO here:
https://chat.zulip.org/#narrow/stream/101-design/topic/search.20narrow.20live.20update
Show user card popover for scheduled messages overlay, compose box
preview, message edit preview, message edit history.
`.messagebox` was chosen as the selector since that was the nearest
parent class that was common for all of the above.
`@all` does not have a popover and that's why it will have the same
pointer as its parent element. We also introduce a new class called
`.user-mention-all` for managing css rules specific to that mention.
We plan to remove the 'tutorial_status' field from UserProfile
table as it is no longer used to show tutorial.
The field is also used to narrow a new user in DM with
welcome bot on the first load.
This prep commit updates the logic to use a new OnboardingStep
for the narrowing behaviour on the first load. This will help
in removing the 'tutorial_status' field.
This commit extracts the "waiting_for_id" and "waiting_for_ack"
data structures of "echo.js" into a separate module in "echo_state".
This is a preparatory commit so as to be able to use them for
"stream_topic_history" module, without causing import cycles.
This commit updates the stale logic in 'toggle_topic_visibility_policy'
function. It was not updated after the addition of 'follow' visibility
policy resulting in buggy behavior.
Earlier, 'Shift + M' hotkey was working in unsubscribed channels.
This commit updates the logic to make it non-functional. This
helps to keep the UI consistent as we don't offer a way to
change visibility_policy in unsubscribed channels via
recipient_bar_controls or other UI elements.
Note: We don't implement this restriction in server because
we don't delete the user-topic states in db when a channel is
unsubscribed as it helps to retain those states when re-subscribed.
And implementing this restriction at server level can create
a confusion of why such states exists in db when API doesn't allow.
This parameter is unused for Zulip avatars, and results in a smaller
(pixel-wise) Gravatar than we use for Zulip "small" avatars. Omitting
the `s=50` parameter results in a 80x80 image, which is closer to the
100x100 image that Zulip thumbnails avatars to. Ironically, using the
default (larger) Gravatar dimensions also results in _smaller_
responses (in bytes) from Gravatar.
We are using `.val` to set compose box content which is very fast vs
`setFieldText` which is very slow due to it doing a lot of
forced repaints. The major downside of using `val` here is that
user will not able to perform `undo` operation on this which doesn't
seem something user would want to do here.
Note that this effects compose content restored from drafts,
scheduled messages and on reload.
This commit refactors the common function used for test in
such a way that we can test more cases for a group setting
along with the ones tested by the common function.
This commit is part of a bigger project to remove custom logic in
the input_pill module. This commit move us away from a world where
we have a `display_value` that's used as identifying information
for a pill as well as for what we display to the user. Now individual
widgets can configure how they come up with a display value based
on the data of that type of pill.
Note: The change in the stream pill test for setting subscribers
for denmark is fixing an issue that wasn't discoverable before.
There always should have been three subscribers.
Because the compose-box resize logic is tied to the size of the
textarea, it's possible when resizing in preview mode that the
state of the compose box is not properly tracked. That's because
the height logic in `autosize_message_content` assumes a visible
textarea.
However, because both the textarea and the message preview area
occupy the same named grid area (`message-content`), and because
the preview area comes after the textarea in the DOM, when visible,
the preview area will automatically cover (and be sized to) the
textarea. And because the textarea remains observable in the DOM,
the compose box will obey the same expansion logic in preview mode
as it does in edit mode.
We want to use render_and_show_preview in message_edit, but that will
cause a dependency cycle because of message_events. In order to avoid
the dependency cycle, the function has been moved to compose_ui and
relevant types have been added.
This commit does not audit the existing function for improvements, just
moves it around and adds types.
The `msg` and `result` are same as the other files (e.g.
activity.test.js) with success responses.
Previously animated images were automatically played in the
message feed of the web app.
Now that we have still thumbnails available for them, we can add a new
personal setting, "web_animate_image_previews", which controls how the
animated images would be played in the web app message feed -- always
played, on hover, or only in the image viewer.
Fixes#31016.
After navigating to a `near` narrow, user is likely to press back
to go back to previous selected message. To support this, we have
to select `then_select_id` without rerender, if we can.
Tested by using breakpoints with `near` links to check if the
correct code is being executed.
This adds the "New direct message" button back in the closed compose UI
for DMs view, to make the closed compose UI consistent across the app.
Since the closed compose UI is always visible, and one that is likely
to be used frequently, it makes sense to have the same UI across all
the views to avoid the mental overhead of figuring out how to compose
a message in different views.
We change the code to update the visibility of information
density setting inputs only on successful completion of
request and not on receiving events.
Visibility of inputs is not being live updated on receiving
events because that leads to flashing of inputs when deselecting
the "Compact mode" checkbox due to the data being sent in
different events and data with the client being different for
time till the all events are received.
Fixes part of #30918.
We don't need `align-self: baseline;` for `fa-envelope` set in
`message_view_header` since this is a different icon and it appears
better without it like other icons.
We also don't need the explicit font-size for switching b/w 14px and
16px mode since `zulip-icon` class takes care of that by default.
Earlier, on sending a new message in a search view it didn't
appear in that view for the sender.
This was because the message event received by the sender
was processed by 'msg_list.view.rerender_messages' which
effectively did nothing because the message is not
rendered in the first place during local echo in that
message list view.
We can't determine locally if the message should be added
to the search narrow. So, we use maybe_add_narrowed_messages
when narrowed to such views.
This fixes the bug and the message appears in the search view.
Previously, while using "with" operator, even when the narrow
was not updated by the operator, hash change requests were
made.
This commit introduces a new variable - "narrow_requires_hash_change"
which determines whether the narrow was updated and thus
requires a hash change or not.
Fixes#30862
This commit updates "filter.is_conversation_view" to be true for
"with" operator. This is important because essentially, the "with"
operator lands you in the same view as the channel-topic narrow
or the "dm" narrow i.e., the last unread message of the narrow.
Hence, the "with" narrow should be handled in a similar way
while determining whether to allow automatically marking
messages as read, or displaying the unread banner, etc.
Fixes#30863
In an interleaved view when composing a message we fade messages
which the user is not replying to, to reduce the chance they send
a message to a recipient they didn't intend to.
Also, it reduces the visual/cognitive processing required
to figure out where their message is going to go.
But, it's not necessarily clear to users that what the
fading means, so this commit adds a one-time compose banner
to explain what's going on the first time this comes up.
Fixes part of #29076.
In a non interleaved view when composing a message to another
conversation we fade messages which the user is not replying to,
to reduce the chance they send a message to a recipient they didn't
intend to. Also, it reduces the visual/cognitive processing required
to figure out where their message is going to go.
But, it's not necessarily clear to users that what the
fading means, so this commit adds a one-time compose banner
to explain what's going on the first time this comes up.
Fixes part of #29076.
Earlier in search suggestion, has: operator returned two different
suggestion string which were `messages with one or more links` and
`messages that contain links`.
This commit changes this to a consistent suggestion string.
Fixes: zulip#30908
Previously, when "adjusted_terms_if_moved" was called for non stream
messages, it used to return "null" for adjusted terms. This is true
for some extent since the non stream messages can not be moved.
However, in case of narrow containing "with" operator, this would
be buggy since there, we want the narrow terms to be adjusted
according to the "with" operand to point to the current narrow,
rather than returning null.
This commit updates the method to return null only if the "raw_terms"
dont contain "with" operator. Else, adjust the "raw_terms" according
to the message.
Before this, settings_tab.hbs was being used to test the `{{#tr}}`
syntax for tagging strings for translation. That was introduced in
82b5d9304b, when the template in question
was small enough to mock.
There are smaller templates than `user_notification_settings` but since
none of them are used as a partial in another template, we can't use
them for this test. This is because we can't test partial block
handling part of the tr tag in templates.js with those templates. Since
`user_notification_settings` has only 1 partial, it will atleast make it
easier for us to know which arguments to pass to the template; in
comparison to `settings_template` where it was hard to determine which
arguments were supposed to be passed to the template.
I've also renamed the test to not say `tr_tag` since it confused me with
the HTML <tr> tag when trying to read the test.
Fixes https://github.com/zulip/zulip/pull/30824#discussion_r1677204395
We used to just drop moved messages from the list of messages to
update if we didn't have them cached. So, if the user is in the
narrow where messages were moved to, user will not see the moved
message if they were not cached locally.
To fix this, we re-render the narrow after fetching messages from
the server.
We don't want to use `fast_track_current_msg_list_to_anchor` here
since that function assumes that current rendered state of the
message list is correct which is not the case here.
We've renamed `get_all_preferences` to
`information_section_checkbox_group`. We've also converted it from a
function into a dictionary since it doesn't contain any page_params
variables anymore. This is a preparatory commit for adding a new
`Information section` as part of a layout change for this page.
Adds server and web app support for processing the new `with`
search operator.
Fixes part of #21505.
Co-authored-by: roanster007 <rohan.gudimetla07@gmail.com>
Co-authored-by: Tim Abbott <tabbott@zulip.com>
While using the pill in `stream_create`, it was noticed that deactivated
users were also part of the user_ids returned by the user_group_pill,
which we do not want to do.
This pill is used in two areas: compose box and stream create/edit.
This commit will only affect stream create/edit since compose box was
just using the typeahead data from user_group_pill and nothing else.
Stream and user pill handle inactive users already, so no change is
needed there.
For system groups, the directive is that we should use the description
as the display name. But in case of `role:everyone`, the description is
`Admins, moderators, members and guests`, while for the
`user_group_pill`, we want to display a simpler and succinct message:
`Everyone`. We've only hardcoded this for user_group_pill since we don't
want to display the name as `Everyone` anywhere else yet.
We've also exposed a method called `get_display_group_name` which will
be used in later commits to get the group display name.
While the support to include all members of a subgroup is needed only in
the `stream_create` context for now, we have added the support for
subgroups to `user_group_pill` for all cases. We have done this because
that is still going to be the correct behaviour if we add similar
support to other pill inputs.
In terms of calculating and populating the recursive member list, it was
decided not to do it when initializing the user_groups data. One reason
for that was it would introduce a lot more complexity when adding or
removing members from any of the subgroups to keep the recursive member
list updated. Keeping in line with the general pattern of calculating
recursive subgroups on the fly too, it was decided to calculate the
recursive list of members on the fly too.
Also changes the `get_group_ids` tests to make sure that subgroup ids
are not part of the result of `get_group_ids`. Since it is used to
calculated taken_groups, we don't want to filter out subgroups as part
of taken_groups and their typeahead should still be visible.
This function goes through all subgroups recursively and returns the
resultant set of the members of those subgroups in addition to the
members of our target_group.
This function is required in order to add the `everyone` pill to create
channel flow.
For the tests written in this commit, it uses the same pattern as the
`get_recursive_subgroups` test.
`is_user_in_group` could have been technically refactored to use
`get_recursive_group_members`, but since the former returns early for
direct members, I've let it be for now.
Transforming valid stream/topic urls to the #**stream>topic**
syntax.
- A valid url contains a stream and optionally a topic
but nothing else, and in that order.
It must belong to the same origin as the Zulip server.
The stream id present in the pasted url should
correspond to an actual stream in the current
server.
- `near` links are not transformed.
- Use-mention distinction is respected by
not transforming a valid url if pasted using
`Ctrl+Shift+V`.
- No transformation occurs inside a code block.
- On pressing `Ctrl+Z` after pasting,
the actual pasted link is restored.
- No transformation occurs if the url is pasted over an
existing url in a markdown link syntax.
- No transformation occurs if the stream or topic name
contained in the pasted url is known to produce broken
stream/topic syntax links (as per #30071).
Fixes#29136
To increase the number of options available for the user to pick from,
we increase the limit of options shown to 50 for all typeaheads, and
make the menu scrollable. The max height is set to original height of
the composebox typeahead menu, which fit 8 options or to 95% of the
window height, whichever is smaller.
Fixes: #20620.
Three events i.e. 'stream create', 'subscription add', and
'message' event are received by client on channel creation.
Earlier, we were narrowing to channel while processing the
'stream create' event. This was resulting in fetching messages
for that narrow even before adding subscription. This resulted
in a bug where "You subscribed to" bookend was visible in the
message feed after the "channel events" message.
This commit updates the logic to narrow ONLY after adding
subscription i.e. while processing "subscription add" event.
Note: A channel creator who is not going to subscribe to the
channel themselves is NOT narrowed to the channel view.
This fixes the incorrect behavior.
User circles indicating their presence are now synced across
all the places they appear, except for:
- navbar_personal_menu_popover - since the status
there will never change.
- typeahead_ist_item - because it is short-lived.
Fixes#30536
This commit hides invalid terms, since we don't want to be suggesting
invalid options to the user. We had already hidden invalid has and is
in the past, but this will also hide things like invalid channels or
user suggestions.
In the future it would be helpful to do two followups:
(1) Update the text for invalid is and has in search_description.hbs
since it looks a bit strange (though not introduced here). This
only shows up if you typed an invalid is/has and then start
typing a term beside it, so it's not very likely to happen.
(2) Don't auto-highlight the first typeahead result when there are
no valid suggestions for the last text term. This seems hard
to implement, so I'm leaving that out for now.