Now that a customer discount may require a particular plan tier to
be applied, update the billing code to check the plan tier when
getting the customer default_discount field/information for a new
plan.
For billing schedule changes and displaying billing information for
current plans, we explicitly use the discount set on the current,
active plan and do not check the customer object for these actions.
This will be used to set a required plan tier value to be used with
the default discount that is set on the Customer object or with a
fixed price set on a CustomerPlan object.
Rename and restructure these comparison variables such that we don't
have a possibly impossible case for presence.last_connected_time being
None.
Fixes#25498.
For compose state variables `last_focused_compose_type_input` and
`message_type` that are assigned non-boolean values on user interaction,
`undefined` is the semantically better choice than `false` for
initialisation, to avoid incorrect boolean implications.
This prep commit adds logic to calculate discount based
on flat_discount and flat_discounted_months. Creates
a stripe invoice item for the discount.
This will be used by remote realm/server billing system
while invoicing via cron job.
This commit renames the variable 'realm_user_count' to
'server_user_count' in 'test_upgrade_user_to_monthly_basic_plan'.
The variable was incorrectly named earlier as it stores
the user count of the whole server.
When pasting any code without any newlines, whether from a code block or
a code span, it will always be pasted as inline code.
That is, a line of code copied from within a code span will retain code
span formatting on paste, and a line of code copied from within a code
block will be pasted as inline code, instead of a 1 line code block.
This commit refactors the original mark_all_as_read in unread_ops to
bulk_mark_mesages_as_read to include marking stream/topic as read.
The unread_ops API reamins the same to mark stream/topic as read but the
underlying implementation now uses a different endpoint. A new function
mark_all_as_read has been added so that the unread_ops API remains the
same.
Fixes#27372.
We only update the url hash in one place, i.e. in callback for
toggler, so there is no need to have a separate function and it
also prevents in someone using that function incorrectly in future.
We now make the right panel empty if the URL hash is changed to
"#streams/all" or "#streams/subscribed" either manually or by
using the browser back button.
We call the function to make the right panel empty in change_state
and not in the callback function for toggler.goto because the right
panel empty becomes empty due to change in hash and not due to
toggling between subscribed and all streams.
We handle showing the correct section in right panel by calling
set_up_right_panel_section from show_settings_for, so there is
no need to call stream_edit_toggler.goto from switch_to_stream_row.
This commit refactors code to not try to update the hash multiple
times.
We now update the url hash only in the callback function for
toggler.goto and remove the call to setup_subscriptions_stream_hash
in open_edit_panel_for_row. This change works as the hash depends
on the section being opened in right panel, so it seems better to
handle the hash update while toggling to the correct section.
A couple of more changes we need to do to make this work correctly
are -
- We extract the code to call "toggler.goto" for the correct section
outside the update_toggler_for_sub to a new function
set_up_right_panel_section. This is changed as update_toggler_for_sub
returns early without doing anything if the url hash is not the one
we have when settings panel for a particular stream is opened and
now the hash is updated after that check as a callback from
toggler.goto.
- set_up_right_panel_section uses stream_edit_toggler.select_tab
to toggle to the correct section in right panel so we now need
to set stream_edit_toggler.select_tab in change_state.
This commit fixes the bug of tab in right side being changed to
"general" when navigating between streams through keyboard instead
of opening the tab which was opened for previous stream.
Fixes#28422.
We don't want to process the key if `suppressKeyPressRepeat`
is true, but we always want to check to see if we should
stop propagation, or else characters typed into the input
field can be processed as hotkeys.
The search bar input is about to get more complicated,
and an upcoming commit will be switching the element
from `input` to a contenteditable div, which means
we'll be accessing the text with text() instead of
val(). To make that change easier, and reduce future
bugs of using the wrong text/val, this commit
makes setter and getter functions so that the text/val
is isolated to one spot.
Earlier, the tests for compose formatting were verbose, hard to read as
well as extend, and overly granular, without even having the ability to
test the final text selection or the cursor position.
Now, new test helpers, `init_textarea_state` and `get_textarea_state`,
have been added, enabling the tests to be more concise and readable,
while also being more powerful. A representative string alone now
describes the textarea state (the text and the selection / cursor),
making each test case as easy as defining the initial state as a string
and comparing the expected state post formatting with another string.
These new tests helped surface a couple bugs which have been fixed in
preceding commits.
In cases where either the description or the URL, or both were empty,
there would be an unneeded space, originally intended to space out the
description and URL, lingering even when the description and/or URL was
missing. The resulting highlight would also be off at times.
Now we only add in a space if both the description and URL are present,
and the highlight too is as intended.
Earlier, when a selection not starting at the beginning of a line was
formatted as a spoiler, the spoiler would not start on a new line, and
so would not be rendered as a spoiler. The `Header` highlighting too
was off by one character.
Now, the spoiler starts on a new line, and the `Header` highlighting
works as expected too.
This was a bug from 4715a058b0 where this
was just incorrectly called. get_realms_info_for_push_bouncer() is a
function meant to be called on a self-hosted server - and this
handle_... call happens on the bouncer. Therefore this returns all
zulipchat realms in product.
With the way, handle_... is being called right now, there's no reason
for it to have an argument for passing a list of realms. It should just
fetch the relevant RemoteRealm entries by itself, given the server arg.
The bug was that a user could do the first part of the flow twice,
receiving two confirmation links, before finishing signup. Then they
could use the first link, followed by the second, which would case an
IntegrityError due to trying to create the RemoteRealmBillingUser
for the second time.
When the second link gets clicked, we should just transparently redirect
the user further into the flow so that they can proceed.
We previously created the connection to the outgoing email server when
the EmailSendingWorker was first created. Since creating the
connection can fail (e.g. because of firewalls or typos in the
hostname), this can cause the `QueueProcessingWorker` creation to
raise an exception. In multi-threaded mode, exceptions in the worker
threads which are _not_ during the handling of a specific event
percolate out to `log_and_exit_if_exception` and trigger the
termination of the entire process -- stopping all worker threads from
making forward progress.
Contain the blast radius of misconfigured email servers by deferring
the opening of the connection until it is first needed. This will not
cause any overall performance change, since it only affects the
latency of the very first email after startup.
Creating the QueueProcessingWorker objects when the ThreadedWorker is
created can lead to a race which caused confusing error messages:
1. A thread tries to call `self.worker = get_worker()`
2. This call raises an exception, which is caught by
`log_and_exit_if_exception`
3. `log_and_exit_if_exception` sends our process a SIGUSR1, _but
otherwise swallows the error_.
4. The thread's `.run()` is called, which tries to access
`self.worker`, which was never set, and throws another exception.
5. The process handles the SIGUSR1, restarting.
Move the creation of the worker to when it is started, so the worker
object does not need to be stored, and possibly have a decoupled
failure.
This commit fixes "Automatically follow topics where I'm mentioned"
setting label click functionality so that the setting is toggled
on clicking the label.