mirror of
https://github.com/zulip/zulip.git
synced 2025-10-23 04:52:12 +00:00
compose_setup: Convert module to typescript.
This commit is contained in:
@@ -230,10 +230,10 @@ export let complete_starting_tasks = (opts: ComposeActionsOpts): void => {
|
||||
if (is_new_topic_triggered) {
|
||||
compose_recipient.set_high_attention_recipient_row();
|
||||
}
|
||||
// We explicitly call this function here apart from compose_setup.js
|
||||
// We explicitly call this function here apart from compose_setup.ts
|
||||
// as this helps to show banner when responding in an interleaved view.
|
||||
// While responding, the compose box opens before fading resulting in
|
||||
// the function call in compose_setup.js not displaying banner.
|
||||
// the function call in compose_setup.ts not displaying banner.
|
||||
if (!narrow_state.narrowed_by_reply()) {
|
||||
compose_notifications.maybe_show_one_time_interleaved_view_messages_fading_banner();
|
||||
}
|
||||
|
@@ -79,7 +79,7 @@ export let update_recipient_row_attention_level = (): void => {
|
||||
// row is focused, that puts users outside the low-attention
|
||||
// recipient-row state--including the `c` hotkey or the
|
||||
// Start new conversation button being clicked. But that
|
||||
// logic is handled via the event handlers in compose_setup.js
|
||||
// logic is handled via the event handlers in compose_setup.ts
|
||||
// that call set_high_attention_recipient_row().
|
||||
if (
|
||||
(composing_to_current_topic_narrow() ||
|
||||
|
@@ -1,5 +1,7 @@
|
||||
import $ from "jquery";
|
||||
import _ from "lodash";
|
||||
import assert from "minimalistic-assert";
|
||||
import * as z from "zod/mini";
|
||||
|
||||
import {unresolve_name} from "../shared/src/resolved_topic.ts";
|
||||
import render_add_poll_modal from "../templates/add_poll_modal.hbs";
|
||||
@@ -41,11 +43,11 @@ import * as user_topics from "./user_topics.ts";
|
||||
import * as util from "./util.ts";
|
||||
import * as widget_modal from "./widget_modal.ts";
|
||||
|
||||
export function abort_xhr() {
|
||||
export function abort_xhr(): void {
|
||||
upload.compose_upload_cancel();
|
||||
}
|
||||
|
||||
function setup_compose_actions_hooks() {
|
||||
function setup_compose_actions_hooks(): void {
|
||||
compose_actions.register_compose_box_clear_hook(compose.clear_invites);
|
||||
compose_actions.register_compose_box_clear_hook(compose.clear_private_stream_alert);
|
||||
compose_actions.register_compose_box_clear_hook(compose.clear_preview_area);
|
||||
@@ -54,7 +56,7 @@ function setup_compose_actions_hooks() {
|
||||
compose_actions.register_compose_cancel_hook(compose_call.abort_video_callbacks);
|
||||
}
|
||||
|
||||
export function initialize() {
|
||||
export function initialize(): void {
|
||||
// Register hooks for compose_actions.
|
||||
setup_compose_actions_hooks();
|
||||
|
||||
@@ -66,10 +68,16 @@ export function initialize() {
|
||||
);
|
||||
|
||||
$("textarea#compose-textarea").on("keydown", (event) => {
|
||||
compose_ui.handle_keydown(event, $("textarea#compose-textarea").expectOne());
|
||||
compose_ui.handle_keydown(
|
||||
event,
|
||||
$<HTMLTextAreaElement>("textarea#compose-textarea").expectOne(),
|
||||
);
|
||||
});
|
||||
$("textarea#compose-textarea").on("keyup", (event) => {
|
||||
compose_ui.handle_keyup(event, $("textarea#compose-textarea").expectOne());
|
||||
compose_ui.handle_keyup(
|
||||
event,
|
||||
$<HTMLTextAreaElement>("textarea#compose-textarea").expectOne(),
|
||||
);
|
||||
});
|
||||
|
||||
$("textarea#compose-textarea").on("input", () => {
|
||||
@@ -116,9 +124,12 @@ export function initialize() {
|
||||
resize.reset_compose_message_max_height();
|
||||
});
|
||||
});
|
||||
update_compose_max_height.observe(document.querySelector("#compose"));
|
||||
update_compose_max_height.observe(document.querySelector("#compose")!);
|
||||
|
||||
function get_input_info(event) {
|
||||
function get_input_info(event: JQuery.ClickEvent): {
|
||||
is_edit_input: boolean;
|
||||
$banner_container: JQuery;
|
||||
} {
|
||||
const $edit_banners_container = $(event.target).closest(".edit_form_banners");
|
||||
const is_edit_input = $edit_banners_container.length > 0;
|
||||
const $banner_container = is_edit_input ? $edit_banners_container : $("#compose_banners");
|
||||
@@ -133,11 +144,12 @@ export function initialize() {
|
||||
(event) => {
|
||||
event.preventDefault();
|
||||
const {$banner_container, is_edit_input} = get_input_info(event);
|
||||
assert(event.target instanceof HTMLElement);
|
||||
const $row = $(event.target).closest(".message_row");
|
||||
compose_validate.clear_stream_wildcard_warnings($banner_container);
|
||||
compose_validate.set_user_acknowledged_stream_wildcard_flag(true);
|
||||
if (is_edit_input) {
|
||||
message_edit.save_message_row_edit($row);
|
||||
void message_edit.save_message_row_edit($row);
|
||||
} else if (event.target.dataset.validationTrigger === "schedule") {
|
||||
compose_send_menu_popover.open_schedule_message_menu(
|
||||
undefined,
|
||||
@@ -168,6 +180,7 @@ export function initialize() {
|
||||
return;
|
||||
}
|
||||
const sub = stream_data.get_sub_by_id(stream_id);
|
||||
assert(sub !== undefined);
|
||||
stream_settings_components.sub_or_unsub(sub);
|
||||
$(user_not_subscribed_selector).remove();
|
||||
},
|
||||
@@ -180,8 +193,8 @@ export function initialize() {
|
||||
event.preventDefault();
|
||||
|
||||
const $target = $(event.target).parents(".main-view-banner");
|
||||
const stream_id = Number.parseInt($target.attr("data-stream-id"), 10);
|
||||
const topic_name = $target.attr("data-topic-name");
|
||||
const stream_id = Number.parseInt($target.attr("data-stream-id")!, 10);
|
||||
const topic_name = $target.attr("data-topic-name")!;
|
||||
|
||||
message_edit.with_first_message_id(stream_id, topic_name, (message_id) => {
|
||||
if (message_id === undefined) {
|
||||
@@ -214,7 +227,7 @@ export function initialize() {
|
||||
} else {
|
||||
message_edit.toggle_resolve_topic(message_id, topic_name, true);
|
||||
}
|
||||
compose_validate.clear_topic_resolved_warning(true);
|
||||
compose_validate.clear_topic_resolved_warning();
|
||||
});
|
||||
},
|
||||
);
|
||||
@@ -228,8 +241,8 @@ export function initialize() {
|
||||
event.preventDefault();
|
||||
|
||||
const $target = $(event.target).parents(".main-view-banner");
|
||||
const stream_id = Number.parseInt($target.attr("data-stream-id"), 10);
|
||||
const topic_name = $target.attr("data-topic-name");
|
||||
const stream_id = Number.parseInt($target.attr("data-stream-id")!, 10);
|
||||
const topic_name = $target.attr("data-topic-name")!;
|
||||
|
||||
user_topics.set_user_topic_visibility_policy(
|
||||
stream_id,
|
||||
@@ -248,9 +261,7 @@ export function initialize() {
|
||||
(event) => {
|
||||
event.preventDefault();
|
||||
if ($(event.target).attr("data-action") === "mark-as-read") {
|
||||
$(event.target)
|
||||
.parents(`${automatic_new_visibility_policy_banner_selector}`)
|
||||
.remove();
|
||||
$(event.target).parents(automatic_new_visibility_policy_banner_selector).remove();
|
||||
onboarding_steps.post_onboarding_step_as_read("visibility_policy_banner");
|
||||
return;
|
||||
}
|
||||
@@ -266,6 +277,10 @@ export function initialize() {
|
||||
(event) => {
|
||||
event.preventDefault();
|
||||
const send_at_timestamp = scheduled_messages.get_selected_send_later_timestamp();
|
||||
// When clicking the button to reschedule, the send later timestamp from the
|
||||
// recently unscheduled message is saved in `selected_send_later_timestamp` and
|
||||
// won't be undefined.
|
||||
assert(send_at_timestamp !== undefined);
|
||||
compose_send_menu_popover.do_schedule_message(send_at_timestamp);
|
||||
},
|
||||
);
|
||||
@@ -283,14 +298,15 @@ export function initialize() {
|
||||
const user_id = Number($invite_row.attr("data-user-id"));
|
||||
const stream_id = Number($invite_row.attr("data-stream-id"));
|
||||
|
||||
function success() {
|
||||
function success(): void {
|
||||
$invite_row.remove();
|
||||
}
|
||||
|
||||
function xhr_failure(xhr) {
|
||||
function xhr_failure(xhr: JQuery.jqXHR<unknown>): void {
|
||||
let error_message = "Failed to subscribe user!";
|
||||
if (xhr.responseJSON?.msg) {
|
||||
error_message = xhr.responseJSON.msg;
|
||||
const parsed = z.object({msg: z.string()}).safeParse(xhr.responseJSON);
|
||||
if (parsed.success) {
|
||||
error_message = parsed.data.msg;
|
||||
}
|
||||
compose.clear_invites();
|
||||
compose_banner.show_error_message(
|
||||
@@ -303,6 +319,7 @@ export function initialize() {
|
||||
}
|
||||
|
||||
const sub = sub_store.get(stream_id);
|
||||
assert(sub !== undefined);
|
||||
|
||||
subscriber_api.add_user_ids_to_stream([user_id], sub, true, success, xhr_failure);
|
||||
},
|
||||
@@ -323,7 +340,7 @@ export function initialize() {
|
||||
`${jump_to_conversation_banner_selector} .main-view-banner-action-button`,
|
||||
(event) => {
|
||||
event.preventDefault();
|
||||
$(event.target).parents(`${jump_to_conversation_banner_selector}`).remove();
|
||||
$(event.target).parents(jump_to_conversation_banner_selector).remove();
|
||||
onboarding_steps.post_onboarding_step_as_read("jump_to_conversation_banner");
|
||||
},
|
||||
);
|
||||
@@ -334,9 +351,7 @@ export function initialize() {
|
||||
`${non_interleaved_view_messages_fading_banner_selector} .main-view-banner-action-button`,
|
||||
(event) => {
|
||||
event.preventDefault();
|
||||
$(event.target)
|
||||
.parents(`${non_interleaved_view_messages_fading_banner_selector}`)
|
||||
.remove();
|
||||
$(event.target).parents(non_interleaved_view_messages_fading_banner_selector).remove();
|
||||
onboarding_steps.post_onboarding_step_as_read("non_interleaved_view_messages_fading");
|
||||
},
|
||||
);
|
||||
@@ -347,7 +362,7 @@ export function initialize() {
|
||||
`${interleaved_view_messages_fading_banner_selector} .main-view-banner-action-button`,
|
||||
(event) => {
|
||||
event.preventDefault();
|
||||
$(event.target).parents(`${interleaved_view_messages_fading_banner_selector}`).remove();
|
||||
$(event.target).parents(interleaved_view_messages_fading_banner_selector).remove();
|
||||
onboarding_steps.post_onboarding_step_as_read("interleaved_view_messages_fading");
|
||||
},
|
||||
);
|
||||
@@ -370,7 +385,7 @@ export function initialize() {
|
||||
$("#compose .file_input").trigger("click");
|
||||
});
|
||||
|
||||
$("body").on("click", ".video_link", (e) => {
|
||||
$("body").on("click", ".video_link", function (this: HTMLElement, e): void {
|
||||
e.preventDefault();
|
||||
e.stopPropagation();
|
||||
|
||||
@@ -380,10 +395,10 @@ export function initialize() {
|
||||
return;
|
||||
}
|
||||
|
||||
compose_call_ui.generate_and_insert_audio_or_video_call_link($(e.target), false);
|
||||
compose_call_ui.generate_and_insert_audio_or_video_call_link($(this), false);
|
||||
});
|
||||
|
||||
$("body").on("click", ".audio_link", (e) => {
|
||||
$("body").on("click", ".audio_link", function (this: HTMLElement, e): void {
|
||||
e.preventDefault();
|
||||
e.stopPropagation();
|
||||
|
||||
@@ -393,31 +408,34 @@ export function initialize() {
|
||||
return;
|
||||
}
|
||||
|
||||
compose_call_ui.generate_and_insert_audio_or_video_call_link($(e.target), true);
|
||||
compose_call_ui.generate_and_insert_audio_or_video_call_link($(this), true);
|
||||
});
|
||||
|
||||
$("body").on("click", ".time_pick", function (e) {
|
||||
$("body").on("click", ".time_pick", function (this: HTMLElement, e) {
|
||||
e.preventDefault();
|
||||
e.stopPropagation();
|
||||
|
||||
let $target_textarea;
|
||||
let edit_message_id;
|
||||
const $compose_click_target = $(this);
|
||||
if ($compose_click_target.parents(".message_edit_form").length === 1) {
|
||||
edit_message_id = rows.id($compose_click_target.parents(".message_row"));
|
||||
$target_textarea = $(`#edit_form_${CSS.escape(edit_message_id)} .message_edit_content`);
|
||||
const edit_message_id = rows.id($compose_click_target.parents(".message_row"));
|
||||
$target_textarea = $<HTMLTextAreaElement>(
|
||||
`#edit_form_${edit_message_id} textarea.message_edit_content`,
|
||||
);
|
||||
} else {
|
||||
$target_textarea = $compose_click_target.closest("form").find("textarea");
|
||||
$target_textarea = $compose_click_target
|
||||
.closest("form")
|
||||
.find<HTMLTextAreaElement>("textarea");
|
||||
}
|
||||
|
||||
if (!flatpickr.is_open()) {
|
||||
const on_timestamp_selection = (val) => {
|
||||
const timestr = `<time:${val}> `;
|
||||
const on_timestamp_selection = (time: string): void => {
|
||||
const timestr = `<time:${time}> `;
|
||||
compose_ui.insert_syntax_and_focus(timestr, $target_textarea);
|
||||
};
|
||||
|
||||
flatpickr.show_flatpickr(
|
||||
$compose_click_target[0],
|
||||
util.the($compose_click_target),
|
||||
on_timestamp_selection,
|
||||
get_timestamp_for_flatpickr(),
|
||||
{
|
||||
@@ -425,7 +443,7 @@ export function initialize() {
|
||||
position: "auto center",
|
||||
// Since we want to handle close of flatpickr manually, we don't want
|
||||
// flatpickr to hide automatically on clicking its trigger element.
|
||||
ignoredFocusElements: [e.currentTarget],
|
||||
ignoredFocusElements: [this],
|
||||
},
|
||||
);
|
||||
} else {
|
||||
@@ -437,8 +455,8 @@ export function initialize() {
|
||||
e.preventDefault();
|
||||
e.stopPropagation();
|
||||
|
||||
function validate_input() {
|
||||
const question = $("#poll-question-input").val().trim();
|
||||
function validate_input(): boolean {
|
||||
const question = $<HTMLInputElement>("#poll-question-input").val()!.trim();
|
||||
|
||||
if (question === "") {
|
||||
ui_report.error(
|
||||
@@ -494,7 +512,7 @@ export function initialize() {
|
||||
e.preventDefault();
|
||||
e.stopPropagation();
|
||||
|
||||
function validate_input(e) {
|
||||
function validate_input(e: JQuery.ClickEvent): boolean {
|
||||
let is_valid = true;
|
||||
e.preventDefault();
|
||||
e.stopPropagation();
|
||||
@@ -584,7 +602,7 @@ export function initialize() {
|
||||
// input is blurred, we immediately update the topic's
|
||||
// displayed text and compose-area placeholder when the
|
||||
// compose textarea is focused.
|
||||
const $input = $("input#stream_message_recipient_topic");
|
||||
const $input = $<HTMLInputElement>("input#stream_message_recipient_topic");
|
||||
compose_recipient.update_topic_displayed_text($input.val());
|
||||
compose_recipient.update_compose_area_placeholder_text();
|
||||
compose_fade.do_update_all();
|
||||
@@ -597,7 +615,7 @@ export function initialize() {
|
||||
|
||||
$(".compose-scrollable-buttons").on(
|
||||
"scroll",
|
||||
_.throttle((e) => {
|
||||
_.throttle((e: JQuery.ScrollEvent) => {
|
||||
compose_ui.handle_scrolling_formatting_buttons(e);
|
||||
}, 150),
|
||||
);
|
||||
@@ -618,14 +636,14 @@ export function initialize() {
|
||||
// To track delayed effects originating from the "blur" event
|
||||
// and its use of setTimeout, we need to set up a variable to
|
||||
// reference the timeout's ID across events.
|
||||
let recipient_focused_timeout;
|
||||
let recipient_focused_timeout: ReturnType<typeof setTimeout>;
|
||||
$("input#stream_message_recipient_topic").on("focus", () => {
|
||||
// We don't want the `recently-focused` class removed via
|
||||
// a setTimeout from the "blur" event, if we're suddenly
|
||||
// focused again.
|
||||
clearTimeout(recipient_focused_timeout);
|
||||
const $compose_recipient = $("#compose-recipient");
|
||||
const $input = $("input#stream_message_recipient_topic");
|
||||
const $input = $<HTMLInputElement>("input#stream_message_recipient_topic");
|
||||
compose_recipient.update_topic_displayed_text($input.val(), true);
|
||||
compose_recipient.update_compose_area_placeholder_text();
|
||||
// When the topic input is focused, we no longer treat
|
||||
@@ -657,7 +675,7 @@ export function initialize() {
|
||||
|
||||
$("input#stream_message_recipient_topic, #private_message_recipient").on("blur", () => {
|
||||
const $compose_recipient = $("#compose-recipient");
|
||||
const $input = $("input#stream_message_recipient_topic");
|
||||
const $input = $<HTMLInputElement>("input#stream_message_recipient_topic");
|
||||
// To correct for an edge case when clearing the topic box
|
||||
// via the left sidebar, we do the following actions after a
|
||||
// delay; these will not have an effect for DMs, and so can
|
||||
@@ -683,7 +701,7 @@ export function initialize() {
|
||||
$("body").on("click", ".formatting_button", function (e) {
|
||||
const $compose_click_target = $(this);
|
||||
const $textarea = $compose_click_target.closest("form").find("textarea");
|
||||
const format_type = $(this).attr("data-format-type");
|
||||
const format_type = $(this).attr("data-format-type")!;
|
||||
compose_ui.format_text($textarea, format_type);
|
||||
popovers.hide_all();
|
||||
$textarea.trigger("focus");
|
@@ -73,7 +73,7 @@ export type DialogWidgetConfig = {
|
||||
id?: string;
|
||||
single_footer_button?: boolean;
|
||||
form_id?: string;
|
||||
validate_input?: (e: unknown) => boolean;
|
||||
validate_input?: (e: JQuery.ClickEvent) => boolean;
|
||||
on_show?: () => void;
|
||||
on_shown?: () => void;
|
||||
on_hide?: () => void;
|
||||
@@ -247,7 +247,7 @@ export function launch(conf: DialogWidgetConfig): string {
|
||||
}
|
||||
|
||||
// Set up handlers.
|
||||
$submit_button.on("click", (e) => {
|
||||
$submit_button.on("click", (e: JQuery.ClickEvent) => {
|
||||
e.preventDefault();
|
||||
|
||||
if (conf.validate_input && !conf.validate_input(e)) {
|
||||
|
@@ -34,7 +34,7 @@ import * as compose_pm_pill from "./compose_pm_pill.ts";
|
||||
import * as compose_recipient from "./compose_recipient.ts";
|
||||
import * as compose_reply from "./compose_reply.ts";
|
||||
import * as compose_send_menu_popover from "./compose_send_menu_popover.ts";
|
||||
import * as compose_setup from "./compose_setup.js";
|
||||
import * as compose_setup from "./compose_setup.ts";
|
||||
import * as compose_textarea from "./compose_textarea.ts";
|
||||
import * as compose_tooltips from "./compose_tooltips.ts";
|
||||
import * as compose_validate from "./compose_validate.ts";
|
||||
|
@@ -113,9 +113,6 @@ test("videos", ({override}) => {
|
||||
const ev = {
|
||||
preventDefault() {},
|
||||
stopPropagation() {},
|
||||
target: {
|
||||
to_$: () => $textarea,
|
||||
},
|
||||
};
|
||||
|
||||
override(compose_ui, "insert_syntax_and_focus", (syntax) => {
|
||||
@@ -139,7 +136,7 @@ test("videos", ({override}) => {
|
||||
|
||||
override(realm, "realm_jitsi_server_url", null);
|
||||
override(realm, "server_jitsi_server_url", "https://server.example.com");
|
||||
handler(ev);
|
||||
handler.call($textarea, ev);
|
||||
// video link ids consist of 15 random digits
|
||||
let video_link_regex =
|
||||
/\[translated: Join video call\.]\(https:\/\/server.example.com\/\d{15}#config.startWithVideoMuted=false\)/;
|
||||
@@ -148,7 +145,7 @@ test("videos", ({override}) => {
|
||||
|
||||
override(realm, "realm_jitsi_server_url", "https://realm.example.com");
|
||||
override(realm, "server_jitsi_server_url", null);
|
||||
handler(ev);
|
||||
handler.call($textarea, ev);
|
||||
video_link_regex =
|
||||
/\[translated: Join video call\.]\(https:\/\/realm.example.com\/\d{15}#config.startWithVideoMuted=false\)/;
|
||||
assert.ok(called);
|
||||
@@ -156,7 +153,7 @@ test("videos", ({override}) => {
|
||||
|
||||
override(realm, "realm_jitsi_server_url", "https://realm.example.com");
|
||||
override(realm, "server_jitsi_server_url", "https://server.example.com");
|
||||
handler(ev);
|
||||
handler.call($textarea, ev);
|
||||
video_link_regex =
|
||||
/\[translated: Join video call\.]\(https:\/\/realm.example.com\/\d{15}#config.startWithVideoMuted=false\)/;
|
||||
assert.ok(called);
|
||||
@@ -173,9 +170,6 @@ test("videos", ({override}) => {
|
||||
const ev = {
|
||||
preventDefault() {},
|
||||
stopPropagation() {},
|
||||
target: {
|
||||
to_$: () => $textarea,
|
||||
},
|
||||
};
|
||||
|
||||
override(compose_ui, "insert_syntax_and_focus", (syntax) => {
|
||||
@@ -206,14 +200,14 @@ test("videos", ({override}) => {
|
||||
|
||||
$("textarea#compose-textarea").val("");
|
||||
const video_handler = $("body").get_on_handler("click", ".video_link");
|
||||
video_handler(ev);
|
||||
video_handler.call($textarea, ev);
|
||||
const video_link_regex = /\[translated: Join video call\.]\(example\.zoom\.com\)/;
|
||||
assert.ok(called);
|
||||
assert.match(syntax_to_insert, video_link_regex);
|
||||
|
||||
$("textarea#compose-textarea").val("");
|
||||
const audio_handler = $("body").get_on_handler("click", ".audio_link");
|
||||
audio_handler(ev);
|
||||
audio_handler.call($textarea, ev);
|
||||
const audio_link_regex = /\[translated: Join voice call\.]\(example\.zoom\.com\)/;
|
||||
assert.ok(called);
|
||||
assert.match(syntax_to_insert, audio_link_regex);
|
||||
@@ -229,9 +223,6 @@ test("videos", ({override}) => {
|
||||
const ev = {
|
||||
preventDefault() {},
|
||||
stopPropagation() {},
|
||||
target: {
|
||||
to_$: () => $textarea,
|
||||
},
|
||||
};
|
||||
|
||||
override(compose_ui, "insert_syntax_and_focus", (syntax) => {
|
||||
@@ -265,14 +256,14 @@ test("videos", ({override}) => {
|
||||
$("textarea#compose-textarea").val("");
|
||||
|
||||
const video_handler = $("body").get_on_handler("click", ".video_link");
|
||||
video_handler(ev);
|
||||
video_handler.call($textarea, ev);
|
||||
const video_link_regex =
|
||||
/\[translated: Join video call\.]\(\/calls\/bigbluebutton\/join\?meeting_id=%22zulip-1%22&moderator=%22AAAAAAAAAA%22&lock_settings_disable_cam=false&checksum=%2232702220bff2a22a44aee72e96cfdb4c4091752e%22\)/;
|
||||
assert.ok(called);
|
||||
assert.match(syntax_to_insert, video_link_regex);
|
||||
|
||||
const audio_handler = $("body").get_on_handler("click", ".audio_link");
|
||||
audio_handler(ev);
|
||||
audio_handler.call($textarea, ev);
|
||||
const audio_link_regex =
|
||||
/\[translated: Join voice call\.]\(\/calls\/bigbluebutton\/join\?meeting_id=%22zulip-1%22&moderator=%22AAAAAAAAAA%22&lock_settings_disable_cam=true&checksum=%2232702220bff2a22a44aee72e96cfdb4c4091752e%22\)/;
|
||||
assert.ok(called);
|
||||
|
Reference in New Issue
Block a user